#!/bin/sh
# Meldet einen postfix-master, den NICHT unser s6-supervise haelt.
#
# Der Fall, gegen den das steht (dns-1, 22./23.09.2026): ein "master -w" mit
# PPID 1 haelt /var/spool/postfix/pid/master.pid. Jeder master, den s6 danach
# startet, endet mit rc 1 -- und zwar OHNE eine Zeile auf stdout, weil postfix
# seine Diagnose nach syslog schreibt. Das Ergebnis liest sich als
#   s6-svstat: up (pid ...) 0 seconds   (bei jedem Blick neu)
#   svctl isup: running
#   ss -lnt: :25 lauscht
# und das s6-Log der Unit bleibt leer. Ein Zustand, der sich selbst nicht
# erklaert, kostet Stunden; diese Meldung ist der fehlende Satz.
#
# Woher der Verwaiste kam: "service postfix start" fiel unter s6 auf
# /etc/init.d/postfix zurueck (behoben in init-system-helpers-s6 0.1.5, das
# /usr/sbin/service auf svctl abbildet). Das Wachtor bleibt trotzdem, weil auch
# ein "postfix start" von Hand denselben Zustand herstellt.
#
# Es TOETET NICHTS. Ein Run-Skript, das fremde Prozesse beendet, ist die falsche
# Stelle fuer diese Entscheidung: der Prozess kann einem Administrator gehoeren,
# der gerade etwas untersucht. Reinigung von Hand, in dieser Reihenfolge:
#   svctl stop postfix ; postfix stop ; svctl start postfix
# ("postfix stop" nimmt pickup/qmgr mit und raeumt master.pid auf -- ein
# kill -TERM auf den Verwaisten laesst die PID-Datei abgestanden liegen.)

set -u

PIDFILE=${POSTFIX_PIDFILE:-/var/spool/postfix/pid/master.pid}

[ -r "$PIDFILE" ] || exit 0

# postfix schreibt die PID RECHTSBUENDIG in ein Feld fester Breite -- die Datei
# enthaelt "                            6428" (33 Bytes, nachgemessen 23.09.2026).
# Ein "case $pid in *[!0-9]*) raus" verwirft das als "keine Zahl", und das
# Wachtor waere genau in dem Fall still geblieben, fuer den es gebaut ist.
# Deshalb nur die Ziffern nehmen.
pid=$(tr -dc '0-9' < "$PIDFILE" 2>/dev/null | head -c 12)
case ${pid:-} in
'' ) exit 0 ;;
esac

# Lebt der Prozess ueberhaupt? Eine abgestandene PID-Datei ist kein Befund --
# "postfix check" raeumt sie auf, und master startet dann normal.
kill -0 "$pid" 2>/dev/null || exit 0

ppid=$(awk '{print $4}' "/proc/$pid/stat" 2>/dev/null)
case ${ppid:-} in
'' | *[!0-9]*) exit 0 ;;
esac

# Gehoert der Prozess einem s6-supervise fuer DIESE Unit? Geprueft wird die
# Kommandozeile des Elternprozesses, nicht die eigene Aufrufkette -- damit die
# Pruefung unabhaengig davon ist, wie tief das Run-Skript verschachtelt wurde.
parent=$(tr '\0' ' ' < "/proc/$ppid/cmdline" 2>/dev/null)
case $parent in
*s6-supervise*postfix*) exit 0 ;;
esac

echo "postfix-s6: WARNUNG ein fremder master haelt ${PIDFILE}: PID ${pid}, Elternprozess ${ppid} (${parent:-unbekannt})."
echo "postfix-s6: WARNUNG s6 hat ihn NICHT gestartet. Jeder master, den s6 jetzt startet, stirbt daran mit rc 1 --"
echo "postfix-s6: WARNUNG und zwar ohne Zeile in diesem Log, weil postfix seine Diagnose nach syslog schreibt"
echo "postfix-s6: WARNUNG (/var/log/mail.log). s6-svstat zeigt dann 'up ... 0 seconds' bei jedem Blick."
echo "postfix-s6: WARNUNG Reinigung: svctl stop postfix ; postfix stop ; svctl start postfix"
exit 0
