#!/bin/sh
#Copyright: 2026 Aitor <aitor@genuen.org>
#License: CC0-1.0
#Comment: oneshot; invoke with: sv once sendsigs

exec 2>&1

ebegin() { [ "${VERBOSE:-}" = no ] || echo "$@"; }
eend() { r=${1:-0}; shift || true; [ "$r" -eq 0 ] || [ "${VERBOSE:-}" = no ] || echo "$*" >&2; return "$r"; }
einfo() { [ "${VERBOSE:-}" = no ] || echo "$@"; }
ewarn() { echo "$@" >&2; }
eerror() { echo "$@" >&2; }

. /lib/init/vars.sh

report_unkillable() {
	if [ -x /usr/bin/pstree ] ; then
		echo "Currently running processes (pstree):"
		pstree
	elif [ -x /bin/ps ] ; then
		echo "Currently running processes (ps):"
		ps -ef
	fi
}

OMITPIDS=

for omitfile in /run/sendsigs.omit; do
	if [ -e $omitfile ]; then
		for pid in $(cat $omitfile); do
			OMITPIDS="${OMITPIDS:+$OMITPIDS }-o $pid"
		done
	fi
done

for omitdir in /run/sendsigs.omit.d; do
	if [ -d "${omitdir}" ]; then
		for pidfile in "${omitdir}/"*; do
			[ -f "$pidfile" ] || continue
			for pid in $(cat $pidfile); do
				OMITPIDS="${OMITPIDS:+$OMITPIDS }-o $pid"
			done
		done
	fi
done

if [ -x /sbin/initctl ]; then
	for pid in $(initctl list | sed -n -e "/process [0-9]/s/.*process //p"); do
		OMITPIDS="${OMITPIDS:+$OMITPIDS }-o $pid"
	done
fi

sync

ebegin "Asking all remaining processes to terminate"
killall5 -15 $OMITPIDS
eend 0
alldead=""
for seq in 1 2 3 4 5 6 7 8 9 10; do
	if [ -x /sbin/initctl ]; then
	    for pid in $(initctl list | sed -n -e "/process [0-9]/s/.*process //p"); do
		OMITPIDS="${OMITPIDS:+$OMITPIDS }-o $pid"
	    done
	fi
	if killall5 -18 $OMITPIDS ; then
	    :
	else
	    alldead=1
	    break
	fi
	sleep 1
done
if [ -z "$alldead" ] ; then
    report_unkillable
    ebegin "Killing all remaining processes"
    killall5 -9 $OMITPIDS
    eend 1
else
    einfo "All processes ended within $seq seconds"
fi
exit 0
