#!/bin/bash
-# Copyright (C) 2019 Ian Kelling
-# SPDX-License-Identifier: AGPL-3.0-or-later
+
+# Basic system status on on Ian's computers
+# Copyright (C) 2024 Ian Kelling
+
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# SPDX-License-Identifier: GPL-3.0-or-later
# usage: runs once every 15 seconds unless any args are passed, or we
# then just runs once and have verbose output. On battery power, run
exit 1
fi
-source /a/bin/errhandle/err
+source /a/bin/bash-bear-trap/bash-bear
status_file=/dev/shm/iank-status
shopt -s nullglob
dynamicipupdate
)
bads=()
- if systemctl show -p SubState --value ${services[@]} | egrep -v '^(running|)$' &>/dev/null; then
+ if systemctl show -p SubState --value ${services[@]} | grep -E -v '^(running|)$' &>/dev/null; then
for s in ${services[@]}; do
if [[ $(systemctl show -p SubState --value $s 2>&1) != running ]]; then
bads+=($s)
prometheus
)
bads=()
- if systemctl show -p SubState --value ${services[@]} | egrep -v '^(running|)$' &>/dev/null; then
+ if systemctl show -p SubState --value ${services[@]} | grep -E -v '^(running|)$' &>/dev/null; then
for s in ${services[@]}; do
if [[ $(systemctl show -p SubState --value $s 2>&1) != running ]]; then
bads+=($s)
## check if last snapshot was recent
old_snap_limit=$(( 3 * 60 * 60 ))
- for vol in a o q; do
- case $vol in
- o) btrbk_root=/mnt/o/btrbk ;;
- *) btrbk_root=/mnt/root/btrbk ;;
- esac
- # this section generally copied from btrbk scripts, but
- # this part modified to speed things up by about half a second.
- # I'm not sure if its quite as reliable, but it looks pretty safe.
- # Profiled it using time and also adding to the top of the file:
- # set -x
- # PS4='+ $(date "+%2N") '
- # allow failure in case there are no snapshots yet.
- # shellcheck disable=SC2012
- shopt -s nullglob
- files=($btrbk_root/$vol.20*)
- shopt -u nullglob
- if (( ! ${#files[@]} )); then
- continue
- fi
- snaps=($(ls -1avdr "${files[@]}" 2>/dev/null |head -n1 || : ))
+ vol=o
+ btrbk_root=/mnt/o/btrbk
+ # this section generally copied from btrbk scripts, but
+ # this part modified to speed things up by about half a second.
+ # I'm not sure if its quite as reliable, but it looks pretty safe.
+ # Profiled it using time and also adding to the top of the file:
+ # set -x
+ # PS4='+ $(date "+%2N") '
+ # allow failure in case there are no snapshots yet.
+ shopt -s nullglob
+ files=($btrbk_root/$vol.20*)
+ shopt -u nullglob
+ if (( ${#files[@]} )); then
+ # shellcheck disable=SC2012 # using ls version sort. not sure this is needed.
+ snaps=("$(ls -1avdr "${files[@]}" 2>/dev/null |head -n1 || : )")
now=$EPOCHSECONDS
maxtime=0
for s in ${snaps[@]}; do
file=${s##*/}
- t=$(date -d $(sed -r 's/(.{4})(..)(.{5})(..)(.*)/\1-\2-\3:\4:\5/' <<<${file#$vol.}) +%s)
+ t=$(date -d "$(sed -r 's/(.{4})(..)(.{5})(..)(.*)/\1-\2-\3:\4:\5/' <<<${file#"$vol."})" +%s)
if (( t > maxtime )); then
maxtime=$t
fi
p "$snapshotmsg" | lo -1 old-snapshot
fi
# not bothering to get info on all volumes if we find an old one.
- break
fi
- done
+ fi
if [[ $MAIL_HOST == "$HOSTNAME" ]]; then
# this is for tracking dns over tls issue, which
# fixvpndns() in brc2 fixes.
stat=$(resolvectl dnsovertls tunfsf 2>/dev/null ||: )
- read _ _ _ istls <<<"$stat"
+ read -r _ _ _ istls <<<"$stat"
case $istls in
no) : ;;
*)
fi
p $var_mail_msg | loday -1 var_mail
- # early in install process, we dont have permission yet for exiqgrep.
- # 1100 helps allow for system restarts
- qlen=$(/usr/sbin/exiqgrep -o 1100 -c -b | awk '{print $1}') ||:
+ # Note, early in install process, we dont have permission yet for exiqgrep.
+ #
+ # todo: don't do this every 15 seconds, more like once every 2 minutes to
+ # save cpu cycles.
+ #
+ # 2400 = 40 mins. This should allow for system restarts, and
+ # 30 minute message delay plus 10 minute queu runs.
+ qlen=$(/usr/sbin/exiqgrep -o 2400 -c -b | awk '{print $1}') ||:
qmsg=
if ((qlen)); then
- qmsg="queue length $qlen"
- chars+=("q $qlen")
+ # Do sending of long delayed messages, and dont count them in our queue warnings.
+ for mid in $(exiqgrep -o 2400 -zi); do
+ if exim -Mvh $mid | awk 'tolower($2) == "fdate:"' | grep -q .; then
+ qlen=$(( qlen - 1 ))
+ # shellcheck disable=SC2016 # exim var, not a bash bar
+ if (( $(date -d "$(exim -Mset $mid -be <<<'$h_date:' | sed -n 's/^> *//;/./p')" +%s) < EPOCHSECONDS )); then
+ if ip a show veth0-mail &>/dev/null; then
+ pid=$(pgrep -f "/usr/sbin/exim4 -bd -q30m -C /etc/exim4/nn-mainlog.conf"|head -n1);
+ nsenter -t $pid -n -m /usr/sbin/exim4 -C /etc/exim4/nn-mainlog.conf -M $mid
+ else
+ /usr/sbin/exim4 -M $mid
+ fi
+ fi
+ fi
+ done
+
+ if ((qlen)); then
+ qmsg="queue length $qlen"
+ chars+=("q $qlen")
+ fi
fi
case $HOSTNAME in
# No point in emailing about the mailq on a host where we don't
# check email.
$MAIL_HOST)
p $qmsg | loday -120 qlen
+
+
+ f=/var/spool/exim4/gw/no-delay-eximids
+ if (( loop_count % 10 == 0 )) && \
+ [[ -s $f ]] && [[ $(cat $f) == all ]]; then
+ # I've left this on longer than I intended, so just auto-delete
+ # it after some time.
+ find $f -mmin +180 -delete
+ if [[ -s $f ]]; then
+ chars+=("NO_DELAY")
+ fi
+ fi
+
+
;;
*)
rmg /home/iank/cron-errors/qlen*
if grep -qxF $HOSTNAME $x; then all_dirs+=( ${x%.hosts} ); fi
done
+ script_files=("${my_service_scripts[@]}" "${my_bin_files[@]}" $my_lib_files)
+
# Just because i forget a lot, -mmin -NUM means files modified <= NUM minutes ago
- if (( fmin < 0 )) && [[ $(find ${all_my_scripts[@]} ${all_dirs[@]} -mmin $fmin -type f -print -quit 2>/dev/null) ]]; then
+ if (( fmin < 0 )) && [[ $(find "${script_files[@]}" ${all_dirs[@]} -mmin $fmin -type f -print -quit 2>/dev/null) ]]; then
v conflink newer filesystem files
chars+=(CONFLINK)
break
# leave it up to epanic-clean to send email notification
fi
+ mprom=/var/lib/prometheus/node-exporter/mailtest-check.prom
+ if [[ -s $mprom ]]; then
+ if grep -qE 'mailtest_check_(unexpected|missing).*[^ ][^0]$' $mprom; then
+ chars+=("MTEST_SPAM")
+ fi
+ mtest_found=false
+ # shellcheck disable=SC2013 # these are words
+ for t in $(grep -E ^mailtest_check_last_usec $mprom | awk '{print $NF}'); do
+ if (( t + 60 * 20 < EPOCHSECONDS )); then
+ mtest_found=true
+ fi
+ done
+ if $mtest_found; then
+ chars+=("MTEST_AGE")
+ fi
+ fi
+
if [[ ! -e $status_file || -w $status_file ]]; then
if [[ -e /a/bin/bash_unpublished/source-state ]]; then
cat /a/bin/bash_unpublished/source-state >$status_file
echo "ps_char=\"${chars[*]} \$ps_char\"" >>$status_file
fi
fi
+
+ if [[ -e $HOME/.iank-stream-on ]] && ! pgrep -fc '^ffmpeg.*icecast://source.*/fsf-sysops' >/dev/null; then
+ rm -f $HOME/.iank-stream-on
+ fi
+
+} # end write-status
+
+# This prevents me having to mute notifications when I'm going to bed.
+mute() {
+ local locked
+ export DISPLAY=:0
+ locked=false
+ if lock_info=$(xscreensaver-command -time 2>/dev/null); then
+ if [[ $lock_info != *non-blanked* ]]; then
+ locked=true
+ fi
+ midnight=$(date -d 00:00 +%s)
+ mdiff=$(( EPOCHSECONDS - midnight ))
+ if $locked && (( mdiff < 6 *60*60 || mdiff > 21 *60*60 )); then
+ case $(pactl get-sink-mute @DEFAULT_SINK@ | awk '{print $2}') in
+ no)
+ # for log purposes
+ echo muted
+ pactl set-sink-mute @DEFAULT_SINK@ true
+ ;;
+ esac
+ fi
+ if ! $locked && (( mdiff > 6 *60*60 || mdiff < 12 *60*60 )) && [[ ! -e /tmp/ianknap ]]; then
+ case $(pactl get-sink-mute @DEFAULT_SINK@ | awk '{print $2}') in
+ yes)
+ # for log purposes
+ echo unmuted
+ pactl set-sink-mute @DEFAULT_SINK@ false
+ ;;
+ esac
+ fi
+ fi
}
+
# use this if we want to do something just once per minute
first_chars=()
-
write-status
if [[ $1 ]]; then
cat $status_file
exit 0
fi
+loop_count=0
main-loop() {
while true; do
power=true
if [[ -e /sys/class/power_supply/AC/online && $(</sys/class/power_supply/AC/online) == 0 ]]; then
power=false
fi
- wait=15
- if ! $power; then
- if systemctl -q is-active bitcoind; then
- bitcoinoff
- fi
+
+ if $power; then
+ wait=15
+ else
wait=60
fi
sleep $wait
write-status
+ mute
+ loop_count=$(( loop_count + 1 ))
done
}