The latest version of the (ath10k-ct 5 GHz) watchdog script can be obtained from GitHub: https://github.com/Catfriend1/openwrt-presence/tree/master/scripts/ath10k-ct-watchdog
The latest version of the 2.4 GHz WiFi "ath9k-watchdog" script is available from GitHub:
- https://github.com/Catfriend1/openwrt-presence/blob/master/scripts/ath9k-watchdog/ath9k-watchdog.sh
- discussion on the ath9k watchdog "healing" mechanism can be found here: Archer C7 2.4 GHz wireless dies in 24~48 hours - #211 by Catfriend1
Requires the following packages:
opkg update
opkg install bash
/root/wrtwatchdog
#/bin/sh
#trap "" SIGHUP
#
# Author: Catfriend1
#
# Info: OpenWRT Watchdog Script
# Filename: wrtwatchdog
# Usage: This script gets called during embedded linux startup.
#
# System -> Startup (scroll all the way down)
#
# # Start wrtwatchdog
# bash /root/wrtwatchdog start
# bash /root/wrtwatchdog debug
#
# # Logging and Monitoring:
# bash /root/wrtwatchdog showlog
# bash /root/wrtwatchdog livelog
#
# Installation:
#
# opkg update
# opkg install bash
# chmod +x "/root/wrtwatchdog"
# chmod +x "/root/wrtwatchdog_main.sh"
# bash "/root/wrtwatchdog start"
#
#
# Variables:
#
SERVICE_MAIN_SRC="/root/wrtwatchdog_main.sh"
SERVICE_MAIN_TMP="/tmp/wrtwatchdog_main.sh"
#
SERVICE_MAIN_LOG="/tmp/wrtwatchdog.log"
SERVICE_PID_FILE="/tmp/wrtwatchdog_main.sh.pid"
SHELL_INTERPRETER="bash"
#
#
# Functions:
#
createInstance ()
{
#
# Usage: createInstance
#
#
# Check prerequisites.
#
if [ ! -f "${SERVICE_MAIN_SRC}" ]; then
echo "$0: Creating service instance FAILED. Install ${SERVICE_MAIN_SRC} first."
return
fi
#
# Update script copies in "/tmp".
#
if [ -f "${SERVICE_MAIN_TMP}" ]; then
rm -f "${SERVICE_MAIN_TMP}"
fi
cat "${SERVICE_MAIN_SRC}" > "${SERVICE_MAIN_TMP}"
#
# Set executable and security permissions.
#
chmod +rx "${SERVICE_MAIN_TMP}"
#
# Run service instance.
#
if [ -f "/bin/${SHELL_INTERPRETER}" ]; then
echo "$0: Creating new service instance ..."
set -m
/bin/${SHELL_INTERPRETER} "${SERVICE_MAIN_TMP}" "${DEBUG_MODE}" > /dev/null &
else
echo "$0: Creating service instance FAILED. Install ${SHELL_INTERPRETER} first."
fi
return
}
findProcess ()
{
#
# Usage: findProcess <ps result line>
#
# Purpose: Searches for previously set environment variable "LOOK_FOR_PROCESS".
#
# We got a line from ps similar to:
# [ ]9396 nobody 13952 S /usr/bin/httpd
#
TEMP_RESULT=$(echo -n "$1" | grep -v grep | grep "$LOOK_FOR_PROCESS")
#
# Check if we found process specified in "LOOK_FOR_PROCESS".
#
if test "$TEMP_RESULT"; then
#
# Exclude our own PID from results.
#
MY_PID=$$
GOT_PID=$(echo -n "$1" | sed 's/ \+/|/g' | sed 's/^|//' | cut -d '|' -f 1)
if [ "$MY_PID" != "$GOT_PID" ]; then
if [ "$NEED_SEPARATOR_ONCE" -eq "0" ]; then
NEED_SEPARATOR_ONCE=1
else
echo -n " "
fi
echo -n "$GOT_PID"
fi
fi
return
}
#
terminateOldInstances ()
{
#
# Usage: terminateOldInstances <name_of_instance>
#
#
# Detect and kill any previously running instances of this service.
#
NEED_SEPARATOR_ONCE=0
LOOK_FOR_PROCESS="$1"
PS_LIST="$(ps w)"
PROC_KILL_LIST=$(echo -e "$PS_LIST" | while read file; do findProcess "${file}"; done)
if test "$PROC_KILL_LIST"; then
echo "$0: Terminating old \"$LOOK_FOR_PROCESS\" instance(s) #$PROC_KILL_LIST ..."
kill $PROC_KILL_LIST
fi
return
}
#
# ! Not supported on BusyBox routers.
#. /lib/lsb/init-functions
#
#
# Service instance control main.
#
DEBUG_MODE=""
case "$1" in
'debug')
# Set DEBUG_MODE to ON.
DEBUG_MODE="debug"
;;
esac
case "$1" in
'start' | 'reset' | 'restart' | 'debug')
sh $0 stop
#
# Hauptprogramm des Dienstes in neuer Instanz ausfuehren.
createInstance
#
exit 0
;;
'stop')
if [ -f "${SERVICE_PID_FILE}" ]; then
kill -INT "$(cat "${SERVICE_PID_FILE}")"
rm "${SERVICE_PID_FILE}"
fi
#
# Speicher von laufenden Instanzen befreien.
terminateOldInstances "${SHELL_INTERPRETER} ${SERVICE_MAIN_TMP}"
#
exit 0
;;
'showlog')
# Zeige Log des Dienstes.
tail -n 60 "${SERVICE_MAIN_LOG}"
exit 0
;;
'livelog')
# Zeige Log des Dienstes.
clear
tail -f "${SERVICE_MAIN_LOG}"
exit 0
;;
'diag')
ps w | egrep "watchdog|tail|logread" | grep -v "grep" | grep -v "livelog" | grep -v "diag"
exit 0
;;
'clean')
exit 0
;;
esac
echo "Usage: $0 {start|debug|stop|reset|restart|showlog|livelog|clean}"
exit 0
/root/wrtwatchdog_main.sh
#/bin/bash
trap "" SIGHUP
#
trap "trap - SIGTERM && kill -- -$$" SIGINT SIGTERM EXIT
#
# set +m
#
# Info: OpenWRT Watchdog Service Main Loop
# Prerequisites:
#
# * BASH (required for arrays)
#
# Filename: wrtwatchdog_main.sh
# Usage: This script gets instanced by "wrtwatchdog".
#
# Author: Catfriend1
#
# Prerequisites:
#
# wrtwatchdog main service wrapper
# wrtwatchdog_main.sh main service program
#
# For testing purposes only:
# killall logread; killall tail; sh wrtwatchdog stop; bash wrtwatchdog_main.sh debug
# kill -INT "$(cat "/tmp/wrtwatchdog_main.sh.pid")"
#
# Script Configuration.
#
PATH=/usr/bin:/usr/sbin:/sbin:/bin
CURRENT_SCRIPT_PATH="$(cd "$(dirname "$0")"; pwd)"
PID_FILE=/tmp/"$(basename "$0")".pid
LOGFILE="/tmp/wrtwatchdog.log"
LOG_MAX_LINES="1000"
DEBUG_MODE="0"
#
# Variables: RUNTIME.
#
MY_SERVICE_NAME="$(basename "$0")"
#
# -----------------------
# --- Function Import ---
# -----------------------
#
#
# -----------------------------------------------------
# -------------- START OF FUNCTION BLOCK --------------
# -----------------------------------------------------
logAdd ()
{
TMP_DATETIME="$(date '+%Y-%m-%d [%H-%M-%S]')"
TMP_LOGSTREAM="$(tail -n ${LOG_MAX_LINES} ${LOGFILE} 2>/dev/null)"
echo "${TMP_LOGSTREAM}" > "$LOGFILE"
if [ "$1" == "-q" ]; then
#
# Quiet mode.
#
echo "${TMP_DATETIME} ${@:2}" >> "${LOGFILE}"
else
#
# Loud mode.
#
echo "${TMP_DATETIME} $*" | tee -a "${LOGFILE}"
fi
return
}
logreader() {
#
# Called by: MAIN
#
logAdd -q "[INFO] BEGIN logreader_loop"
/sbin/logread -f | while read line; do
if $(echo -n "${line}" | grep -q "kernel.*ath10k_pci.*failed to send pdev bss chan info request"); then
logAdd -q "[ERROR] ath10k_pci 5G WiFi card failed. Restarting driver ..."
rmmod ath10k_pci
sleep 2
modprobe ath10k_pci
sleep 5
logAdd -q "[INFO] Restarting wifi after driver restart ..."
wifi up
fi
done
}
# ---------------------------------------------------
# -------------- END OF FUNCTION BLOCK --------------
# ---------------------------------------------------
#
#
#
#
#
#
#
#
# Check commmand line parameters.
#
case "$1" in
'debug')
# Turn DEBUG_MODE on.
DEBUG_MODE="1"
# Continue script execution.
;;
esac
#
# Service Startup.
#
if [ "${DEBUG_MODE}" == "0" ]; then
logAdd "${MY_SERVICE_NAME} wurde neu gestartet."
sleep 10
else
# Log message.
logAdd "${MY_SERVICE_NAME} wurde im DEBUG_MODE neu gestartet."
fi
#
# Service Main.
#
# Store script PID.
echo "$$" > "${PID_FILE}"
#
# Fork three permanently running background processes.
logreader &
#
# Wait for kill -INT from service stub.
wait
#
# We should never reach here.
#
logAdd "${MY_SERVICE_NAME}: End of script reached."
exit 0
Autorun setup:
- Edit /etc/rc.local
# Put your custom commands here that should be executed once
# the system init finished. By default this file does nothing.
/bin/bash /root/wrtwatchdog start
exit 0