#!/usr/bin/env bash
# One-time field commissioning: USB driver + ETH caps + systemd boot service.
# Position-free + role-based: identity = hostname; ETHERGOLD_ROLE selects stack.
#
# Usage (on Pi, after deploy):
#   sudo bash commission_prod_boot.sh                         # default ROLE=listen
#   sudo env ETHERGOLD_ROLE=listen bash commission_prod_boot.sh
#   sudo env ETHERGOLD_ROLE=edge EDGE_ROLE=peer-a EDGE_UPLINK=eth0 bash commission_prod_boot.sh
#   sudo env DISABLE_DYZINEFRAME=1 bash commission_prod_boot.sh  # force-off DF (topbox/listen default on)
#
# Idempotent — safe to re-run after kernel updates or driver changes.

if grep -q $'\r' "${BASH_SOURCE[0]}" 2>/dev/null; then
  sed -i 's/\r$//' "${BASH_SOURCE[0]}"
  exec bash "${BASH_SOURCE[0]}" "$@"
fi

set -euo pipefail

POS="${FIXTURE_POS:-1}"
if ! [[ "${POS}" =~ ^[1-9][0-9]?$ ]]; then
  echo "FATAL: FIXTURE_POS must be 1..99 (internal id); leave unset for prod default 1" >&2
  exit 1
fi

ROLE="${ETHERGOLD_ROLE:-listen}"
case "${ROLE}" in
  topbox|listen|edge) ;;
  *)
    echo "FATAL: ETHERGOLD_ROLE must be topbox|listen|edge (got '${ROLE}')" >&2
    exit 1
    ;;
esac

if [[ "${EUID}" -ne 0 ]]; then
  echo "FATAL: run with sudo (commission installs driver + systemd unit)" >&2
  exit 1
fi

REAL_USER="${SUDO_USER:-topbox}"
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
# shellcheck source=ethergold_field_env.sh
source "${SCRIPT_DIR}/ethergold_field_env.sh"
if [[ -f "${SCRIPT_DIR}/../sync/ethergold_paths.sh" ]]; then
  # shellcheck source=../sync/ethergold_paths.sh
  source "${SCRIPT_DIR}/../sync/ethergold_paths.sh"
elif [[ -f "${SCRIPT_DIR}/../../sync/ethergold_paths.sh" ]]; then
  # shellcheck source=../../sync/ethergold_paths.sh
  source "${SCRIPT_DIR}/../../sync/ethergold_paths.sh"
else
  # shellcheck source=/dev/null
  source "${HOME}/EtherGold/sync/ethergold_paths.sh"
fi
DRIVER="${ETHERGOLD_DAEMON}/xr-usb-serial-pog422"

# Windows tar/scp often land *.sh as 644; install_pi.sh is nested so a top-level chmod misses it.
find "${SCRIPT_DIR}" -type f -name '*.sh' -exec chmod +x {} + 2>/dev/null || true

echo "=== commission_prod_boot role=${ROLE} pos=${POS} user=${REAL_USER} ==="
ethergold_migrate_legacy_paths

echo "--- stop capture / prod workers ---"
if [[ -f "${ETHERGOLD_BRIDGE}/stop_fixture_session.sh" ]]; then
  sudo -u "${REAL_USER}" env SKIP_SYNC=1 bash "${ETHERGOLD_BRIDGE}/stop_fixture_session.sh" || true
fi
sudo -u "${REAL_USER}" env FIXTURE_POS="${POS}" bash "${SCRIPT_DIR}/disable_prod.sh" || true
for pattern in pog422_fixture_bridge pog422_bridge pog422_fixture_listen \
               fixture_link_watch ethergold_supervisor fixture_supervisor \
               ethergold_listen_supervisor; do
  pkill -TERM -f "${pattern}" 2>/dev/null || true
done
sleep 1
for pattern in pog422_fixture_bridge pog422_bridge pog422_fixture_listen \
               fixture_link_watch ethergold_supervisor fixture_supervisor \
               ethergold_listen_supervisor; do
  pkill -KILL -f "${pattern}" 2>/dev/null || true
done

if [[ -x "${DRIVER}/remove_gpio7low.sh" ]]; then
  echo "--- remove legacy gpio7low (conflicts with POG422 RS485 auto) ---"
  sudo -u "${REAL_USER}" bash "${DRIVER}/remove_gpio7low.sh" || true
fi

echo "--- POG422 USB driver (install_pi.sh) ---"
if [[ ! -f "${DRIVER}/install_pi.sh" ]]; then
  echo "FATAL: missing ${DRIVER}/install_pi.sh — run PC deploy or migrate-field first" >&2
  exit 1
fi
chmod +x "${DRIVER}/install_pi.sh" || true
WANT_DRV="$(grep -m1 '^EXPECTED_VER=' "${DRIVER}/install_pi.sh" | cut -d= -f2 | tr -d '"' || true)"
HAVE_DRV="$(cat /sys/module/xr_usb_serial_common/version 2>/dev/null || true)"
DISK_DRV="$(modinfo -F version xr_usb_serial_common 2>/dev/null || true)"
if [[ "${FORCE_DRIVER:-0}" == "1" ]]; then
  sudo -u "${REAL_USER}" bash -lc "cd '${DRIVER}' && bash install_pi.sh"
elif [[ "${SKIP_DRIVER:-0}" == "1" ]]; then
  echo "--- skip USB driver (SKIP_DRIVER=1) ---"
elif [[ -n "${WANT_DRV}" && ( "${HAVE_DRV}" == "${WANT_DRV}" || "${DISK_DRV}" == "${WANT_DRV}" ) ]]; then
  echo "--- USB driver already ${HAVE_DRV:-disk ${DISK_DRV}}; skip rebuild (FORCE_DRIVER=1 to reinstall) ---"
else
  if ! sudo -u "${REAL_USER}" bash -lc "cd '${DRIVER}' && bash install_pi.sh"; then
    echo "WARN: USB driver install/reload failed (often usbserial in use). Enable systemd anyway; reboot to load 2.2.2.10."
  fi
fi

PREP_ETH="${ETHERGOLD_DAEMON}/prep_eth_for_ethergold.sh"
if [[ ! -f "${PREP_ETH}" ]]; then
  PREP_ETH="${ETHERGOLD_DAEMON}/prep_eth_for_fixture.sh"
fi
echo "--- ETH raw socket caps (${PREP_ETH##*/}) ---"
bash "${PREP_ETH}"

echo "--- NetworkManager: unmanage eth0/eth1 (AF_PACKET; no DHCP) ---"
NM_INSTALL=""
for cand in \
  "${SCRIPT_DIR}/install_nm_eth_unmanaged.sh" \
  "${ETHERGOLD_DAEMON}/install_nm_eth_unmanaged.sh" \
  "${ETHERGOLD_BRIDGE}/install_nm_eth_unmanaged.sh" \
  "${ETHERGOLD_DEV}/install_nm_eth_unmanaged.sh"; do
  if [[ -f "${cand}" ]]; then
    NM_INSTALL="${cand}"
    break
  fi
done
if [[ -n "${NM_INSTALL}" ]]; then
  bash "${NM_INSTALL}"
else
  echo "WARN: install_nm_eth_unmanaged.sh missing — eth ports may stay NM-managed" >&2
fi

echo "--- set EtherGold role=${ROLE} ---"
ROLE_ARGS=(bash "${SCRIPT_DIR}/set_ethergold_role.sh" "${ROLE}")
if [[ "${ROLE}" == "edge" ]]; then
  ER="${EDGE_ROLE:-}"
  EU="${EDGE_UPLINK:-eth0}"
  if [[ -z "${ER}" ]]; then
    echo "FATAL: edge commission needs EDGE_ROLE=peer-a|peer-b (and optional EDGE_UPLINK)" >&2
    exit 1
  fi
  ROLE_ARGS+=(--role "${ER}" --uplink "${EU}")
  if [[ -n "${EDGE_WIFI_PSK:-}" ]]; then
    ROLE_ARGS+=(--wifi-psk "${EDGE_WIFI_PSK}")
  fi
  if [[ -n "${EDGE_GAME_IF:-}" ]]; then
    ROLE_ARGS+=(--game-if "${EDGE_GAME_IF}")
  fi
fi
FIXTURE_POS="${POS}" "${ROLE_ARGS[@]}"

# Role helper already toggles DyzineFrame (topbox + listen ON; edge OFF unless --display-on).
# Honor explicit DISABLE_DYZINEFRAME override.
if [[ "${ROLE}" == "edge" && "${DISABLE_DYZINEFRAME:-1}" == "0" ]]; then
  echo "--- override: enable DyzineFrame on edge (DISABLE_DYZINEFRAME=0) ---"
  DF_DISABLE="${ETHERGOLD_SYNC}/disable_dyzineframe_autostart.sh"
  if [[ -f "${DF_DISABLE}" ]]; then
    sudo -u "${REAL_USER}" bash "${DF_DISABLE}" --enable || true
  fi
elif [[ "${ROLE}" != "edge" && "${DISABLE_DYZINEFRAME:-0}" == "1" ]]; then
  echo "--- override: disable DyzineFrame autostart (DISABLE_DYZINEFRAME=1) ---"
  DF_DISABLE="${ETHERGOLD_SYNC}/disable_dyzineframe_autostart.sh"
  if [[ -f "${DF_DISABLE}" ]]; then
    sudo -u "${REAL_USER}" bash "${DF_DISABLE}" || true
  fi
fi

echo "--- CPU affinity (EG core + IRQ/RPS best-effort) ---"
if [[ -f "${SCRIPT_DIR}/install_cpu_affinity.sh" ]]; then
  bash "${SCRIPT_DIR}/install_cpu_affinity.sh" || true
else
  echo "WARN: install_cpu_affinity.sh missing" >&2
fi

echo "--- ethergold-http :31234 (progressives + config/status + fireworks for DF/OHD) ---"
if [[ -f "${SCRIPT_DIR}/install_ethergold_http.sh" ]]; then
  bash "${SCRIPT_DIR}/install_ethergold_http.sh"
else
  echo "WARN: install_ethergold_http.sh missing" >&2
fi

loginctl enable-linger "${REAL_USER}" 2>/dev/null || true

echo ""
echo "=== commission_prod_boot complete host=$(hostname) role=${ROLE} ==="
echo "  systemctl status ethergold            # topbox/edge"
echo "  systemctl status ethergold-collector  # listen"
echo "  systemctl status ohd-irq-affinity     # USB→EG / net softirq layout"
echo "  systemctl status ethergold-http        # :31234 progressives / config / status"
echo "  cat /etc/ethergold/role.env"
echo "  tail -f ${ETHERGOLD_LOGS}/supervisor.log"
echo "  Reboot this Pi to start DyzineFrame on the desktop (HTTP_EXTERNAL + ethergold-http)."
echo "  Do not SSH-start DyzineFrame."
