Files
docker-steam-headless/overlay/usr/bin/sunshine-run
Josh.5 771c47d602 Fix direct execution of AppImages
Fetch a list of all child PIDs before forwarding the termination signal.
Once the main process is terminated, forward that term signal to all found children also (if they are still running)
2023-09-11 12:21:23 +12:00

118 lines
4.7 KiB
Bash
Executable File

#!/usr/bin/env bash
###
# File: sunshine-run
# Project: bin
# File Created: Tuesday, 23rd August 2023 3:28:52 pm
# Author: Josh.5 (jsunnex@gmail.com)
# -----
# Last Modified: Friday, 23rd August 2023 4:21:00 pm
# Modified By: Josh.5 (jsunnex@gmail.com)
###
set -e
exec >> >(tee -a ${USER_HOME:?}/.cache/log/sunshine_run.log) 2>&1
echo
echo "-------------------------------"
echo
date
echo
echo "-------------------------------"
echo
echo "**** Execute sunshine-run ****"
echo
# Trap SIGINT, SIGQUIT, SIGHUP, SIGTERM to forward signals to the child process
_term() {
if [ -n "${proc_pid}" ]; then
# Read all child processes of proc_pid first
child_pids=$(pgrep -P $proc_pid)
# Forward the signal proc_pid
echo " - Checking for status of main process ${proc_pid}"
if kill -0 "${proc_pid}" 2>/dev/null; then
echo " - Forwarding signal $1 to process ${proc_pid}"
kill -s "${1}" "${proc_pid}"
else
echo " - Process ${proc_pid} is already stopped. Nothing to do here."
fi
for child_pid in ${child_pids:-}; do
echo " - Checking for status of child process ${child_pid}"
if kill -0 "${child_pid}" 2>/dev/null; then
echo " - Forwarding signal $1 to process ${child_pid}"
kill -s "${1}" "${child_pid}"
else
echo " - Process ${child_pid} is already stopped. Nothing to do here."
fi
done
fi
}
trap '_term INT' SIGINT
trap '_term QUIT' SIGQUIT
trap '_term HUP' SIGHUP
trap '_term TERM' SIGTERM
# Record sunshine-run PID
echo " - Recording sunshine-run PID '$$' in /tmp/sunshine-exec-run.pid"
echo "$$" > /tmp/sunshine-exec-run.pid
# Wipe session config
echo "" > /tmp/sunshine-exec-run.conf
# Update display resolution and refresh reate if client provided the required details
if ([ "X${SUNSHINE_CLIENT_WIDTH:-}" != "X" ] && [ "X${SUNSHINE_CLIENT_HEIGHT:-}" != "X" ] && [ "X${SUNSHINE_CLIENT_FPS:-}" != "X" ]); then
# Don't fail script if something goes wrong here. Set +e in subprocess
(
set +e
echo " - Setting display resolution to ${SUNSHINE_CLIENT_WIDTH:?}x${SUNSHINE_CLIENT_HEIGHT:?} ${SUNSHINE_CLIENT_FPS:?}Hz"
# Read current display mode and extract resolution and refresh rate from the mode string
__xrandr_out="$(xrandr)"
__current_current_mode=$(echo "${__xrandr_out:?}" | awk '/\*/ {print $0}')
__current_resolution=$(echo ${__current_current_mode:?} | awk '{print $1}')
__current_refresh_rate=$(echo ${__current_current_mode:?} | awk '{sub(/\*/, "", $2); print $2}')
# Get the primary output device
__primary_output="$(echo "${__xrandr_out:?}" | grep primary | awk '{print $1}')"
# Get the modeline from cvt and extract the second line (which contains the modeline)
__client_modeline=$(cvt "${SUNSHINE_CLIENT_WIDTH:?}" "${SUNSHINE_CLIENT_HEIGHT:?}" "${SUNSHINE_CLIENT_FPS:?}" | grep Modeline | sed -e 's/Modeline //')
# Create a new mode for this. This allows us to force a set refresh rate that may not be supported by the display
__client_mode=$(echo "${__client_modeline:?}" | awk -F '"' '{print $2}')
# Check if tthis mode is alread added to the primary display
if ! echo "${__xrandr_out:?}" | grep -q "${__client_mode:?}"; then
echo " - Adding new mode '${__client_mode:?}' with new modeline '${__client_modeline:?}'"
xrandr --newmode "${__client_mode:?}" ${__client_modeline##*\"}
echo " - Adding new mode '${__client_mode:?}' to device '${__primary_output:?}'"
xrandr --addmode "${__primary_output:?}" "${__client_mode:?}"
fi
# Set the current resoultion to the new mode
echo " - Setting the display mode to '${__client_mode:?}'"
xrandr --output "${__primary_output:?}" --mode "${__client_mode:?}" --rate "${SUNSHINE_CLIENT_FPS:?}"
# Save original display settings to config file. This will be read and used to restore the original display settings when the client disconnects.
echo "primary_output='${__primary_output:?}'" >> /tmp/sunshine-exec-run.conf
echo "display_mode='${__current_resolution:?}'" >> /tmp/sunshine-exec-run.conf
echo "display_rate='${__current_refresh_rate:?}'" >> /tmp/sunshine-exec-run.conf
)
fi
# Run child process
/usr/bin/dumb-init "${@}" &
proc_pid=$!
# Wait for child process to exit:
echo " - Waiting for PID '${proc_pid}' to exit"
wait "$proc_pid"
# Clean up PID file
if [ -f /tmp/sunshine-exec-run.pid ]; then
echo " - Removing sunshine-run pidfile."
rm -f /tmp/sunshine-exec-run.pid
else
echo " - WARNING: No sunshine-run pidfile found for removal."
fi
echo "DONE"