diff --git a/overlay/usr/bin/sunshine-run b/overlay/usr/bin/sunshine-run index 657d705..4a9267a 100755 --- a/overlay/usr/bin/sunshine-run +++ b/overlay/usr/bin/sunshine-run @@ -10,7 +10,7 @@ ### set -e -exec >> >(tee -a /tmp/sunshine-exec-run.log) 2>&1 +exec >> >(tee -a ${USER_HOME:?}/.cache/log/sunshine_run.log) 2>&1 echo echo "-------------------------------" echo @@ -33,57 +33,68 @@ 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 - echo " - Setting display resolution to ${SUNSHINE_CLIENT_WIDTH:?}x${SUNSHINE_CLIENT_HEIGHT:?} ${SUNSHINE_CLIENT_FPS:?}Hz" + # 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}') + # 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 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}') + # 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 + # 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:?}" + # 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 + # 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=$! -echo " - Recording sunshine-run PID '${proc_pid}' in /tmp/sunshine-exec-run.pid" -echo "${proc_pid}" > /tmp/sunshine-exec-run.pid # Wait for child process to exit: echo " - Waiting for PID '${proc_pid}' to exit" wait "$proc_pid" # Clean up PID file -rm -f /tmp/sunshine-exec-run.pid +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" diff --git a/overlay/usr/bin/sunshine-stop b/overlay/usr/bin/sunshine-stop index ed0562e..6c9bb7f 100755 --- a/overlay/usr/bin/sunshine-stop +++ b/overlay/usr/bin/sunshine-stop @@ -10,7 +10,7 @@ ### set -e -exec >> >(tee -a /tmp/sunshine-exec-stop.log) 2>&1 +exec >> >(tee -a ${USER_HOME:?}/.cache/log/sunshine_stop.log) 2>&1 echo echo "-------------------------------" echo @@ -23,52 +23,81 @@ echo # Read the run config if [ -f /tmp/sunshine-exec-run.conf ]; then + echo " - Reading sunshine-run config." . /tmp/sunshine-exec-run.conf +else + echo " - WARNING: No sunshine-run config found for import." fi # Read the process PID process_pid="$(cat /tmp/sunshine-exec-run.pid)" -echo " - Found initial sunshine-run PID '${process_pid}'" +echo " - Found initial sunshine-run PID '${process_pid}'." # Send a INT signal to the PID -echo " - Sending SIGINT to PID '${process_pid}'" -kill -INT "${process_pid}" +echo " - Sending SIGINT to PID '${process_pid}'." +kill -INT "${process_pid}" || true # Run a loop to check for any other "sunshine-run" processes and send them also a INT signal -echo " - Checking for other sunshine-run processes '${process_pid}'" +echo " - Checking for other sunshine-run processes..." for process_pid in $(ps aux | grep -v grep | grep sunshine-run | awk '{print $2}'); do - echo " - Sending SIGINT to PID '${process_pid}'" - kill -INT "${process_pid}" 2>/dev/null + # Ensure this process is still running + if ! kill -0 "$process_pid" 2>/dev/null; then + continue + fi + echo " - Stopping PID '${process_pid}' - $(ps -p ${process_pid} -o command | awk 'NR>1')" + # Send this process a SIGINT + echo " - Sending SIGINT to PID '${process_pid}'." + kill -INT "${process_pid}" 2>/dev/null || true sleep 0.5 + # Send this process a SIGTERM every 2 seconds util stopped or until it has sent 3 signals counter=0 while kill -0 "$process_pid" 2>/dev/null; do - echo " - Sending SIGTERM to PID '${process_pid}'" - kill -TERM "$process_pid" 2>/dev/null + echo " - Sending SIGTERM to PID '${process_pid}'." + kill -TERM "$process_pid" 2>/dev/null || true counter=$((counter + 1)) [ "$counter" -gt 2 ] && break sleep 2 done + # Send this process a SIGKILL every second until stopped or until it has sent 3 signals counter=0 while kill -0 "$process_pid" 2>/dev/null; do - echo " - Sending SIGKILL to PID '${process_pid}'" - kill -KILL "$process_pid" 2>/dev/null + echo " - Sending SIGKILL to PID '${process_pid}'." + kill -KILL "$process_pid" 2>/dev/null || true counter=$((counter + 1)) [ "$counter" -gt 2 ] && break sleep 1 done + if ! kill -0 "$process_pid" 2>/dev/null; then + echo " - PID '${process_pid}' stopped." + else + echo " - ERROR: Failed to kill PID '${process_pid}'." + fi done +echo " - All sunshine-run related processes stopped." # Check if the required information was stored for resetting the display resolution and refresh rate if ([ "X${primary_output:-}" != "X" ] && [ "X${display_mode:-}" != "X" ] && [ "X${display_rate:-}" != "X" ]); then # Reset display resolution and refresh rate echo " - Resetting display resolution to ${display_mode:?} ${display_rate:?}Hz" xrandr --output "${primary_output:?}" --mode "${display_mode:?}" --rate "${display_rate:?}" +else + echo " - WARNING: original display config not found. Resolution will not be reset." fi # Clean up config file -rm -f /tmp/sunshine-exec-run.conf +if [ -f /tmp/sunshine-exec-run.conf ]; then + echo " - Removing sunshine-run config." + rm -f /tmp/sunshine-exec-run.conf +else + echo " - WARNING: No sunshine-run config found for removal." +fi # Clean up PID file -rm -f /tmp/sunshine-exec-run.pid +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"