#!/usr/bin/env bash

# Supervise the instantWM X11 process so it can restart without ending the
# display-manager session (and therefore without closing X11 applications).

RTD=""
if command -v instantruntimedir >/dev/null 2>&1; then
    RTD="$(instantruntimedir 2>/dev/null || true)"
fi
if [[ -z "$RTD" ]]; then
    if [[ -n "${XDG_RUNTIME_DIR:-}" ]]; then
        RTD="$XDG_RUNTIME_DIR/instantos"
    else
        RTD="/tmp/instantos-${UID}"
    fi
fi

mkdir -p "$RTD" "$HOME/.local/share"
RUNNING_FILE="$RTD/instantosrunning"
PID_FILE="$RTD/wmpid"
OVERRIDE_FILE="$RTD/wmoverride"
LOG_FILE="$HOME/.local/share/instantos.log"
WMPID=""
FIRST_START=true
SESSION_AUTOSTART="${INSTANTWM_AUTOSTART:-1}"

touch "$RUNNING_FILE"

stop_session() {
    rm -f "$RUNNING_FILE" "$PID_FILE"
    if [[ -n "$WMPID" ]] && kill -0 "$WMPID" 2>/dev/null; then
        kill "$WMPID" 2>/dev/null || true
        wait "$WMPID" 2>/dev/null || true
    fi
    exit 0
}
trap stop_session HUP INT TERM

cd "$HOME" || echo "failed to access home directory" >&2

if command -v iconf >/dev/null 2>&1 && command -v wmname >/dev/null 2>&1; then
    configured_wmname="$(iconf wmname 2>/dev/null || true)"
    if [[ -n "$configured_wmname" ]]; then
        wmname "$configured_wmname"
    fi
fi

if [[ -f "$HOME/.instantsession" ]]; then
    # shellcheck source=/dev/null
    source "$HOME/.instantsession"
fi

if command -v iconf >/dev/null 2>&1 && iconf -i debug; then
    export INSTANTDEBUG=true
fi

if [[ -z "${INSTANTDEBUG:-}" && -f "$LOG_FILE" ]] &&
    [[ "$(du -sm "$LOG_FILE" | awk '{print $1}')" -gt 20 ]]; then
    echo "log file has gotten out of hand, clearing logs"
    echo "start of log file" >"$LOG_FILE"
fi

export XDG_CURRENT_DESKTOP=instantwm
export XDG_SESSION_DESKTOP=instantwm
export DESKTOP_SESSION=instantwm

while [[ -e "$RUNNING_FILE" ]]; do
    if [[ -s "$OVERRIDE_FILE" ]]; then
        wm_command="$(<"$OVERRIDE_FILE")"
        rm -f "$OVERRIDE_FILE"
        if ! command -v "$wm_command" >/dev/null 2>&1; then
            echo "window manager override not found: $wm_command" >>"$LOG_FILE"
            continue
        fi
    else
        wm_command=instantwm
    fi

    if [[ "$wm_command" == instantwm ]]; then
        if [[ "$FIRST_START" == true ]]; then
            export INSTANTWM_AUTOSTART="$SESSION_AUTOSTART"
            FIRST_START=false
        else
            export INSTANTWM_AUTOSTART=0
        fi
        if [[ -n "${INSTANTDEBUG:-}" ]]; then
            instantwm --backend x11 >>"$LOG_FILE" 2>&1 &
        else
            instantwm --backend x11 2>>"$LOG_FILE" &
        fi
    else
        "$wm_command" 2>>"$LOG_FILE" &
    fi

    WMPID=$!
    echo "$WMPID" >"$PID_FILE"
    if wait "$WMPID"; then
        WMEXITCODE=0
    else
        WMEXITCODE=$?
    fi
    WMPID=""
    rm -f "$PID_FILE"

    if [[ -e "$RUNNING_FILE" ]]; then
        printf '%s: window manager exited with code %s; restarting\n' \
            "$(date)" "$WMEXITCODE" >>"$LOG_FILE"
        sleep 1
    fi
done
