#!/bin/sh DATE_TIME=$(date +%s) LOG_FILE="/tmp/gu_steam_deck_install_${DATE_TIME}.log" rm /tmp/gu_steam_deck_install_*.log 1>/dev/null 2>&1 exec 2>${LOG_FILE} || true set -x # Online URL URL_PREFIX="https://" DOWNLOAD_URL="router.booster.gearupportal.com/api/script/monitor?type=" UNINSTALL_DOWNLOAD_URL="router.booster.gearupportal.com/api/script/uninstall?type=" ROUTER="steam-deck-plugin" MODEL="x86_64" BASEDIR=$(dirname "$0") UNINSTALL_FILE="${BASEDIR}/uninstall.sh" INSTALL_DIR="" MONITOR_FILE="" MONITOR_CONFIG="" STEAM_DECK_PLUGIN="steam-deck-plugin" progress() { pct="$1" msg="$2" width=30 filled=$((pct * width / 100)) bar="" i=0 while [ "$i" -lt "$width" ]; do if [ "$i" -lt "$filled" ]; then bar="${bar}#" else bar="${bar}-" fi i=$((i + 1)) done printf "\r[%s] %3d%% %s\033[K" "$bar" "$pct" "$msg" if [ "$pct" -ge 100 ]; then printf "\n" fi } get_steam_deck_install_dir() { local sd_install_dir="/home/deck" if [ -d ${sd_install_dir} ] ; then echo "${sd_install_dir}/gu/" return 0 fi sd_install_dir="/home/bazzite" if [ -d ${sd_install_dir} ] ; then chmod a+xr ${sd_install_dir} echo "${sd_install_dir}/gu/" return 0 fi sd_install_dir="$(pwd)" install_dir_prefix=${str:0:6} if [ x"${install_dir_prefix}" = x"/home/" ] ; then chmod a+xr ${sd_install_dir} echo "${sd_install_dir}/gu/" return 0 fi sd_install_dir="/home/gu" chmod a+xr ${sd_install_dir} echo "${sd_install_dir}/gu/" return 0 } init_param() { local monitor_filename="guplugin_monitor.sh" INSTALL_DIR=$(get_steam_deck_install_dir) MONITOR_FILE="${INSTALL_DIR}/${monitor_filename}" MONITOR_CONFIG="${INSTALL_DIR}/guplugin_monitor.config" UNINSTALL_DOWNLOAD_URL="${URL_PREFIX}${UNINSTALL_DOWNLOAD_URL}${STEAM_DECK_PLUGIN}" MONITOR_DOWNLOAD_URL="${URL_PREFIX}${DOWNLOAD_URL}${STEAM_DECK_PLUGIN}" return 0 } # Return: 0 means success. check_dir() { if [ ! -d "${INSTALL_DIR}" ];then mkdir -p "${INSTALL_DIR}" [ "$?" != "0" ] && return 1 fi return 0 } clean_up() { [ ! -f "${UNINSTALL_FILE}" ] && return 1 chmod u+x "${UNINSTALL_FILE}" /bin/sh "${UNINSTALL_FILE}" "${ROUTER}" "${MODEL}" 1>/dev/null 2>&1 [ "$?" != "0" ] && return 1 return 0 } # Return: 0 means success. download() { local url="$1" local file="$2" local plugin_info=$(curl -s -H "Accept:text/plain" "${url}" || \ wget -q -O - "${url}&output=text" ) [ "$?" != "0" ] && return 1 [ -z "$plugin_info" ] && return 1 local plugin_url=$(echo "$plugin_info" | cut -d ',' -f 1) local plugin_md5=$(echo "$plugin_info" | cut -d ',' -f 2) [ -z "${plugin_url}" ] && return 1 [ -z "${plugin_md5}" ] && return 1 curl -s "$plugin_url" -o "${file}" >/dev/null 2>&1 || \ wget -q "$plugin_url" -O "${file}" >/dev/null 2>&1 if [ "$?" != "0" ];then [ -f "${file}" ] && rm "${file}" return 1 fi if [ -f "${file}" ];then local download_md5=$(md5sum "${file}") local download_md5=$(echo "$download_md5" | sed 's/[ ][ ]*/ /g' | cut -d' ' -f1) if [ "$download_md5" != "$plugin_md5" ];then rm "${file}" return 1 fi return 0 else return 1 fi } # Return: 0 means running. check_running() { local PID_FILE="/var/run/guplugin.pid" local PLUGIN_EXE="guplugin" for i in {1..90};do if [ -f "$PID_FILE" ];then local pid=$(cat $PID_FILE) local running_pid=$(ps | sed 's/^[ \t]*//g;s/[ \t]*$//g' | \ sed 's/[ ][ ]*/#/g' | grep "${PLUGIN_EXE}" | \ grep -v "grep" | cut -d'#' -f1 | grep -e "^${pid}$") if [ "${running_pid}" = "" ];then running_pid=$(ps -ax -o pid,cmd | sed 's/^[ \t]*//g;s/[ \t]*$//g' | \ sed 's/[ ][ ]*/#/g' | grep "${PLUGIN_EXE}" | \ grep -v "grep" | cut -d'#' -f1 | grep -e "^${pid}$") fi if [ "$pid" = "${running_pid}" ];then return 0 else sleep 1 fi else sleep 1 fi done return 1 } # Return: 0 means success. config_steam_deck_bootup() { config_steam_deck_systemd return $? } config_steam_deck_systemd() { local guplugin_service="/etc/systemd/system/guplugin.service" { echo "[Unit]" echo "Description=GU Plugin" echo "Wants=network-online.target" echo "After=network.target network-online.target" echo "" echo "[Service]" echo "Type=simple" echo "ExecStart=/bin/sh ${INSTALL_DIR}guplugin_monitor.sh" echo "ExecStop=-/bin/kill -TERM \${MAINPID}" echo "ExecStop=-/usr/bin/pkill -TERM -x guplugin" echo "ExecStop=-/bin/sh -c 'while /usr/bin/pgrep -f \"[x]uplugin-guardian\" >/dev/null 2>&1; do sleep 0.2; done'" echo "TimeoutStopSec=60" echo "" echo "[Install]" echo "WantedBy=default.target" } > "${guplugin_service}" systemctl daemon-reload systemctl enable guplugin systemctl start guplugin } # Return: 0 means success. config_bootup() { config_steam_deck_bootup return $? } create_uninstall() { local unfile=${INSTALL_DIR}/uninstall.sh if [ -f "${UNINSTALL_FILE}" ];then cp -p ${UNINSTALL_FILE} ${unfile} sed -i 's/^ROUTER=\${1:-asuswrt-merlin}$/ROUTER=\${1:-steam-deck-plugin}/g' ${unfile} else echo "uninstall file:${UNINSTALL_FILE} not exist" fi return 0 } install() { progress 0 "Starting installation..." progress 10 "Initializing parameters..." init_param [ "$?" != "0" ] && return 9 progress 30 "Checking install directory..." check_dir [ "$?" != "0" ] && return 2 progress 45 "Downloading uninstall script..." download "${UNINSTALL_DOWNLOAD_URL}" "${UNINSTALL_FILE}" [ "$?" != "0" ] && return 3 progress 55 "Cleaning up old version..." clean_up [ "$?" != "0" ] && return 4 progress 70 "Downloading daemon..." download "${MONITOR_DOWNLOAD_URL}" "${MONITOR_FILE}" if [ "$?" != "0" ];then [ -f "${MONITOR_FILE}" ] && rm "${MONITOR_FILE}" return 5 fi chmod a+x ${MONITOR_FILE} { echo "router=${ROUTER}"; echo "model=x86_64" } > ${MONITOR_CONFIG} progress 85 "Configuring boot startup..." config_bootup progress 95 "Starting plugin..." check_running create_uninstall if [ "$?" != "0" ];then #echo "Installation failed!" return 6 fi progress 100 "Installation complete..." return 0 } # Start to install. QRFILE="/tmp/gu/.steam_deck_sn_qrcode" [ -f "${QRFILE}" ] && rm "${QRFILE}" install status_code=$? if [ "${status_code}" -eq "0" ];then #watch -t -n1 cat /tmp/gu/.steam_deck_sn_qrcode < /dev/tty i=0 while [ "$i" -lt 5 ]; do echo "Installation successful, loading..." if [ -f "${QRFILE}" ]; then break fi i=$((i + 1)) sleep 1 done if [ -f ${QRFILE} ] ; then printf '\033[2J' while :; do { printf '\033[H' echo "Installation successful. Please scan this QR code with the GearUP Router App to complete binding." echo "After binding is complete, you can close Konsole (terminal)." cat ${QRFILE} printf '\033[J' } sleep 1 done [ -f "${UNINSTALL_FILE}" ] && rm "${UNINSTALL_FILE}" exit 0 else echo "Installation successful. Please use the GearUP Router App to complete LAN binding." [ -f "${UNINSTALL_FILE}" ] && rm "${UNINSTALL_FILE}" exit 0 fi fi if [ ${status_code} -gt 4 ];then if [ -f "${UNINSTALL_FILE}" ];then echo "Installation failed, cleaning up downloaded files..." clean_up fi fi [ -f "${UNINSTALL_FILE}" ] && rm "${UNINSTALL_FILE}" exit $status_code