#!/usr/bin/env bash
set -euo pipefail

ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
FLOWLOG_BIN="${FLOWLOG_BIN:-$ROOT/flowlog}"
FLOWLOG_TIMEOUT="${FLOWLOG_TIMEOUT:-120s}"
FLOWLOG_ENGINE="${FLOWLOG_ENGINE:-interp}"
FLOWLOG_PARALLEL_PROFILE="${FLOWLOG_PARALLEL_PROFILE:-off}"
# By default, suppress per-test stderr noise (the INRIA suite intentionally
# triggers a couple of "unknown procedure" warnings when `unknown=warning`).
# Set to 1 to see stderr for every file.
FLOWLOG_INRIA_SHOW_STDERR="${FLOWLOG_INRIA_SHOW_STDERR:-0}"

if [[ ! -x "$FLOWLOG_BIN" ]]; then
  make -C "$ROOT" >/dev/null
fi

suite_dir="$ROOT/build/inria_suite/inriasuite"
suite_driver="$suite_dir/inriasuite.pl"
suite_wrapper="$ROOT/build/inria_suite/flowlog_inriasuite.pl"

if [[ ! -f "$suite_driver" || ! -f "$suite_wrapper" ]]; then
  "$ROOT/tests/setup_inria_suite.sh" >/dev/null
fi

if [[ ! -f "$suite_driver" || ! -f "$suite_wrapper" ]]; then
  echo "inria: suite not set up (missing: $suite_driver and/or $suite_wrapper)" >&2
  exit 1
fi

mapfile -t files < <(
  rg '^file\(' "$suite_driver" \
    | sed -E 's/^file\((.*)\)\..*/\1/' \
    | sed -E 's/[[:space:]]+$//'
)

failures=0
total_files=0

echo "INRIA suite file-by-file, timeout=$FLOWLOG_TIMEOUT"

err_tmp=""
if [[ "$FLOWLOG_INRIA_SHOW_STDERR" == "0" || "$FLOWLOG_INRIA_SHOW_STDERR" == "off" || "$FLOWLOG_INRIA_SHOW_STDERR" == "false" ]]; then
  err_tmp="$(mktemp "$ROOT/build/inria_suite/flowlog_inria_stderr.XXXXXX")"
  trap 'rm -f "$err_tmp"' EXIT
fi

for f in "${files[@]}"; do
  [[ -n "$f" ]] || continue
  total_files=$((total_files + 1))

  out=""
  st=0
  set +e
  if [[ -n "$err_tmp" ]]; then
    : >"$err_tmp"
    out="$(
      timeout "$FLOWLOG_TIMEOUT" \
        "$FLOWLOG_BIN" --engine "$FLOWLOG_ENGINE" --parallel-profile "$FLOWLOG_PARALLEL_PROFILE" \
          "$suite_wrapper" -g "run_tests_score($f,T,W)." 2>"$err_tmp"
    )"
  else
    out="$(
      timeout "$FLOWLOG_TIMEOUT" \
        "$FLOWLOG_BIN" --engine "$FLOWLOG_ENGINE" --parallel-profile "$FLOWLOG_PARALLEL_PROFILE" \
          "$suite_wrapper" -g "run_tests_score($f,T,W)."
    )"
  fi
  st=$?
  set -e

  if [[ "$st" -ne 0 ]]; then
    echo "  $f: exit=$st" >&2
    if [[ -n "$err_tmp" && -s "$err_tmp" ]]; then
      sed -e 's/^/    /' "$err_tmp" >&2
    fi
    failures=$((failures + 1))
    continue
  fi

  t="$(printf '%s' "$out" | sed -nE 's/.*T = ([0-9]+).*/\1/p' | head -n 1 || true)"
  w="$(printf '%s' "$out" | sed -nE 's/.*W = ([0-9]+).*/\1/p' | head -n 1 || true)"

  if [[ -z "$t" || -z "$w" ]]; then
    echo "  $f: unable to parse output: $out" >&2
    if [[ -n "$err_tmp" && -s "$err_tmp" ]]; then
      sed -e 's/^/    /' "$err_tmp" >&2
    fi
    failures=$((failures + 1))
    continue
  fi

  if [[ "$w" != "0" ]]; then
    echo "  $f: wrong=$w/$t" >&2
    if [[ -n "$err_tmp" && -s "$err_tmp" ]]; then
      sed -e 's/^/    /' "$err_tmp" >&2
    fi
    failures=$((failures + 1))
  fi
done

if [[ "$failures" -eq 0 ]]; then
  echo "OK: $total_files files, 0 failing"
else
  echo "FAIL: $failures/$total_files files failing" >&2
  exit 1
fi
