Update hw-acceleration.sh
This commit is contained in:
		
							parent
							
								
									3d63800e65
								
							
						
					
					
						commit
						e1a7572e4e
					
				| @ -24,8 +24,6 @@ | |||||||
| #   - User group assignments (video/render) | #   - User group assignments (video/render) | ||||||
| #   - Interactive menu system via whiptail | #   - Interactive menu system via whiptail | ||||||
| 
 | 
 | ||||||
| #!/usr/bin/env bash |  | ||||||
| 
 |  | ||||||
| set -euo pipefail | set -euo pipefail | ||||||
| 
 | 
 | ||||||
| function header_info() { | function header_info() { | ||||||
| @ -42,7 +40,8 @@ EOF | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function msg() { | function msg() { | ||||||
|   local type="$1"; shift |     local type="$1" | ||||||
|  |     shift | ||||||
|     case "$type" in |     case "$type" in | ||||||
|     info) printf " \033[36m➤\033[0m %s\n" "$*" ;; |     info) printf " \033[36m➤\033[0m %s\n" "$*" ;; | ||||||
|     ok) printf " \033[32m✔\033[0m %s\n" "$*" ;; |     ok) printf " \033[32m✔\033[0m %s\n" "$*" ;; | ||||||
| @ -51,57 +50,59 @@ function msg() { | |||||||
|     esac |     esac | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function select_hw_features() { | function detect_features() { | ||||||
|   local opts |     AVAILABLE_FEATURES=() | ||||||
|   opts=$( |     [[ -e /dev/ttyUSB0 || -e /dev/ttyACM0 ]] && AVAILABLE_FEATURES+=("usb" "🖧  USB Passthrough         " OFF) | ||||||
|     whiptail --title "🔧 Hardware Integration" --checklist \ |     [[ -e /dev/dri/renderD128 ]] && AVAILABLE_FEATURES+=("intel" "🟦  Intel VAAPI GPU         " OFF) | ||||||
|     "\nSelect hardware features to passthrough:\n" 20 60 8 \ |     [[ -e /dev/nvidia0 ]] && AVAILABLE_FEATURES+=("nvidia" "🟨  NVIDIA GPU              " OFF) | ||||||
|     "usb"    "🖧  USB Passthrough         " OFF \ |     [[ -e /dev/kfd ]] && AVAILABLE_FEATURES+=("amd" "🟥  AMD GPU (ROCm)          " OFF) | ||||||
|     "intel"  "🟦  Intel VAAPI GPU         " OFF \ |  | ||||||
|     "nvidia" "🟨  NVIDIA GPU              " OFF \ |  | ||||||
|     "amd"    "🟥  AMD GPU (ROCm)          " OFF \ |  | ||||||
|     3>&1 1>&2 2>&3 |  | ||||||
|   ) || exit 1 |  | ||||||
| 
 | 
 | ||||||
|   SELECTED_FEATURES=$(echo "$opts" | tr -d '"') |     if [[ ${#AVAILABLE_FEATURES[@]} -eq 0 ]]; then | ||||||
|   if [[ -z "$SELECTED_FEATURES" ]]; then |         msg warn "No supported hardware found on host system." | ||||||
|     msg warn "No passthrough options selected" |  | ||||||
|         exit 1 |         exit 1 | ||||||
|     fi |     fi | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | function select_hw_features() { | ||||||
|  |     local opts | ||||||
|  |     opts=$(whiptail --title "🔧 Hardware Options" --checklist \ | ||||||
|  |         "\nSelect hardware features to passthrough:\n" 20 60 8 \ | ||||||
|  |         "${AVAILABLE_FEATURES[@]}" 3>&1 1>&2 2>&3) || exit 1 | ||||||
|  | 
 | ||||||
|  |     SELECTED_FEATURES=$(echo "$opts" | tr -d '"') | ||||||
|  |     if [[ -z "$SELECTED_FEATURES" ]]; then | ||||||
|  |         msg warn "No passthrough options selected." | ||||||
|  |         exit 1 | ||||||
|  |     fi | ||||||
|  | } | ||||||
| 
 | 
 | ||||||
| function select_lxc_targets() { | function select_lxc_targets() { | ||||||
|   local list; local opts=() |     local list | ||||||
|   if ! list=$(pct list | awk 'NR>1 {print $1 "|" $2}' | xargs -n1); then |     local opts=() | ||||||
|     msg err "Failed to get container list" |     list=$(pct list | awk 'NR>1 {print $1 "|" $2}') || return 1 | ||||||
|     exit 1 |  | ||||||
|   fi |  | ||||||
|     while IFS="|" read -r id name; do |     while IFS="|" read -r id name; do | ||||||
|     if [[ -f "/etc/pve/lxc/${id}.conf" ]]; then |         [[ -f "/etc/pve/lxc/${id}.conf" ]] && opts+=("$id" "$name (CTID: $id)" OFF) | ||||||
|       opts+=("$id" "${name} (${id})" "OFF") |     done <<<"$list" | ||||||
|     fi | 
 | ||||||
|   done <<< "$list" |     [[ ${#opts[@]} -eq 0 ]] && { | ||||||
|   if [[ ${#opts[@]} -eq 0 ]]; then |         msg warn "No LXC containers found." | ||||||
|     msg warn "No containers found" |  | ||||||
|         exit 1 |         exit 1 | ||||||
|   fi |     } | ||||||
|  | 
 | ||||||
|     SELECTED_CTIDS=$(whiptail --title "Select LXC Containers" --checklist \ |     SELECTED_CTIDS=$(whiptail --title "Select LXC Containers" --checklist \ | ||||||
|         "Choose container(s) to apply passthrough:" 20 60 10 \ |         "Choose container(s) to apply passthrough:" 20 60 10 \ | ||||||
|     "${opts[@]}" 3>&1 1>&2 2>&3 | tr -d '"') |         "${opts[@]}" 3>&1 1>&2 2>&3 | tr -d '"') || exit 1 | ||||||
|   if [[ -z "$SELECTED_CTIDS" ]]; then | 
 | ||||||
|     msg warn "No containers selected" |     [[ -z "$SELECTED_CTIDS" ]] && { | ||||||
|  |         msg warn "No containers selected." | ||||||
|         exit 1 |         exit 1 | ||||||
|   fi |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function apply_usb() { | function apply_usb() { | ||||||
|     local conf="$1" |     local conf="$1" | ||||||
|   if ! compgen -G "/dev/ttyUSB* /dev/ttyACM*" >/dev/null; then |     grep -q "dev/ttyUSB" <<<"$(ls /dev 2>/dev/null)" || return 1 | ||||||
|     msg warn "No USB serial devices found, skipping" |     cat <<EOF >>"$conf" | ||||||
|     return 1 |  | ||||||
|   fi |  | ||||||
|   cat <<EOF >> "$conf" |  | ||||||
| # USB Passthrough | # USB Passthrough | ||||||
| lxc.cgroup2.devices.allow: a | lxc.cgroup2.devices.allow: a | ||||||
| lxc.cap.drop: | lxc.cap.drop: | ||||||
| @ -113,16 +114,12 @@ lxc.mount.entry: /dev/ttyUSB1       dev/ttyUSB1       none bind,optional,create= | |||||||
| lxc.mount.entry: /dev/ttyACM0       dev/ttyACM0       none bind,optional,create=file | lxc.mount.entry: /dev/ttyACM0       dev/ttyACM0       none bind,optional,create=file | ||||||
| lxc.mount.entry: /dev/ttyACM1       dev/ttyACM1       none bind,optional,create=file | lxc.mount.entry: /dev/ttyACM1       dev/ttyACM1       none bind,optional,create=file | ||||||
| EOF | EOF | ||||||
|   return 0 |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function apply_intel() { | function apply_intel() { | ||||||
|     local conf="$1" |     local conf="$1" | ||||||
|   if [[ ! -e /dev/dri/renderD128 ]]; then |     [[ -e /dev/dri/renderD128 ]] || return 1 | ||||||
|     msg warn "Intel GPU not detected, skipping" |     cat <<EOF >>"$conf" | ||||||
|     return 1 |  | ||||||
|   fi |  | ||||||
|   cat <<EOF >> "$conf" |  | ||||||
| # Intel VAAPI | # Intel VAAPI | ||||||
| lxc.cgroup2.devices.allow: c 226:* rwm | lxc.cgroup2.devices.allow: c 226:* rwm | ||||||
| lxc.cgroup2.devices.allow: c 29:0 rwm | lxc.cgroup2.devices.allow: c 29:0 rwm | ||||||
| @ -130,16 +127,12 @@ lxc.mount.entry: /dev/fb0 dev/fb0 none bind,optional,create=file | |||||||
| lxc.mount.entry: /dev/dri dev/dri none bind,optional,create=dir | lxc.mount.entry: /dev/dri dev/dri none bind,optional,create=dir | ||||||
| lxc.mount.entry: /dev/dri/renderD128 dev/dri/renderD128 none bind,optional,create=file | lxc.mount.entry: /dev/dri/renderD128 dev/dri/renderD128 none bind,optional,create=file | ||||||
| EOF | EOF | ||||||
|   return 0 |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function apply_nvidia() { | function apply_nvidia() { | ||||||
|     local conf="$1" |     local conf="$1" | ||||||
|   if [[ ! -e /dev/nvidia0 ]]; then |     [[ -e /dev/nvidia0 ]] || return 1 | ||||||
|     msg warn "NVIDIA device not found, skipping" |     cat <<EOF >>"$conf" | ||||||
|     return 1 |  | ||||||
|   fi |  | ||||||
|   cat <<EOF >> "$conf" |  | ||||||
| # NVIDIA GPU | # NVIDIA GPU | ||||||
| lxc.cgroup2.devices.allow: c 195:* rwm | lxc.cgroup2.devices.allow: c 195:* rwm | ||||||
| lxc.mount.entry: /dev/nvidia0 dev/nvidia0 none bind,optional,create=file | lxc.mount.entry: /dev/nvidia0 dev/nvidia0 none bind,optional,create=file | ||||||
| @ -147,32 +140,31 @@ lxc.mount.entry: /dev/nvidiactl dev/nvidiactl none bind,optional,create=file | |||||||
| lxc.mount.entry: /dev/nvidia-uvm dev/nvidia-uvm none bind,optional,create=file | lxc.mount.entry: /dev/nvidia-uvm dev/nvidia-uvm none bind,optional,create=file | ||||||
| lxc.mount.entry: /dev/nvidia-uvm-tools dev/nvidia-uvm-tools none bind,optional,create=file | lxc.mount.entry: /dev/nvidia-uvm-tools dev/nvidia-uvm-tools none bind,optional,create=file | ||||||
| EOF | EOF | ||||||
|   return 0 |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function apply_amd() { | function apply_amd() { | ||||||
|     local conf="$1" |     local conf="$1" | ||||||
|   if [[ ! -e /dev/kfd ]]; then |     [[ -e /dev/kfd ]] || return 1 | ||||||
|     msg warn "AMD GPU not found, skipping" |     cat <<EOF >>"$conf" | ||||||
|     return 1 |  | ||||||
|   fi |  | ||||||
|   cat <<EOF >> "$conf" |  | ||||||
| # AMD ROCm GPU | # AMD ROCm GPU | ||||||
| lxc.cgroup2.devices.allow: c 226:* rwm | lxc.cgroup2.devices.allow: c 226:* rwm | ||||||
| lxc.cgroup2.devices.allow: c 238:* rwm | lxc.cgroup2.devices.allow: c 238:* rwm | ||||||
| lxc.mount.entry: /dev/kfd dev/kfd none bind,optional,create=file | lxc.mount.entry: /dev/kfd dev/kfd none bind,optional,create=file | ||||||
| lxc.mount.entry: /dev/dri dev/dri none bind,optional,create=dir | lxc.mount.entry: /dev/dri dev/dri none bind,optional,create=dir | ||||||
| EOF | EOF | ||||||
|   return 0 |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| function main() { | function main() { | ||||||
|     header_info |     header_info | ||||||
|  |     detect_features | ||||||
|     select_hw_features |     select_hw_features | ||||||
|     select_lxc_targets |     select_lxc_targets | ||||||
|  | 
 | ||||||
|  |     local updated_cts=() | ||||||
|     for ctid in $SELECTED_CTIDS; do |     for ctid in $SELECTED_CTIDS; do | ||||||
|         local conf="/etc/pve/lxc/${ctid}.conf" |         local conf="/etc/pve/lxc/${ctid}.conf" | ||||||
|         local updated=0 |         local updated=0 | ||||||
|  | 
 | ||||||
|         for opt in $SELECTED_FEATURES; do |         for opt in $SELECTED_FEATURES; do | ||||||
|             case "$opt" in |             case "$opt" in | ||||||
|             usb) apply_usb "$conf" && updated=1 ;; |             usb) apply_usb "$conf" && updated=1 ;; | ||||||
| @ -181,13 +173,27 @@ function main() { | |||||||
|             amd) apply_amd "$conf" && updated=1 ;; |             amd) apply_amd "$conf" && updated=1 ;; | ||||||
|             esac |             esac | ||||||
|         done |         done | ||||||
|  | 
 | ||||||
|         if [[ "$updated" -eq 1 ]]; then |         if [[ "$updated" -eq 1 ]]; then | ||||||
|       msg ok "Hardware passthrough updated in: $conf" |             updated_cts+=("$ctid") | ||||||
|       printf "\nRestart container %s to apply changes.\n\n" "$ctid" |  | ||||||
|     else |  | ||||||
|       msg warn "No passthrough changes applied for container $ctid" |  | ||||||
|         fi |         fi | ||||||
|     done |     done | ||||||
|  | 
 | ||||||
|  |     if [[ ${#updated_cts[@]} -gt 0 ]]; then | ||||||
|  |         msg ok "Hardware passthrough applied to: ${updated_cts[*]}" | ||||||
|  |         echo | ||||||
|  |         if whiptail --title "Restart Containers" --yesno \ | ||||||
|  |             "Restart the following containers now?\n\n${updated_cts[*]}" 12 50; then | ||||||
|  |             for ctid in "${updated_cts[@]}"; do | ||||||
|  |                 pct restart "$ctid" | ||||||
|  |             done | ||||||
|  |             msg ok "Restarted containers: ${updated_cts[*]}" | ||||||
|  |         else | ||||||
|  |             msg info "You can restart them manually later." | ||||||
|  |         fi | ||||||
|  |     else | ||||||
|  |         msg warn "No changes were applied to any container." | ||||||
|  |     fi | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| main | main | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 CanbiZ
						CanbiZ