# GOG-only Wine/Whisky — без Steam, HoMM, export_wine_env_steam.
GOG_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
GAMES_DIR="$(cd "${GOG_DIR}/.." && pwd)"
GAMES_CACHE_DIR="${GAMES_DIR}/cache"

_env_file="${GOG_DIR}/bottle.env"
if [[ -f "${_env_file}" ]]; then
  # shellcheck source=/dev/null
  source "${_env_file}"
elif [[ -n "${GOG_BOTTLE_ID:-}" ]]; then
  BOTTLE_ID="${GOG_BOTTLE_ID}"
  BOTTLE_NAME="${GOG_BOTTLE_NAME:-GOG-Install}"
else
  echo "❌ Нет bottle для GOG."
  echo "   1) Whisky → New Bottle (Windows 10 64-bit), имя GOG-Install"
  echo "   2) bash ${GOG_DIR}/list-bottles.sh"
  echo "   3) bash ${GOG_DIR}/use-bottle.sh <UUID>"
  echo ""
  echo "   Не используйте bottle HoMM-OldenEra — там Steam, дампы и winedbg."
  exit 1
fi
unset _env_file

_FRANKE="${HOME}/Library/Containers/com.franke.Whisky/Bottles/${BOTTLE_ID}"
_ISAAC="${HOME}/Library/Containers/com.isaacmarovitz.Whisky/Bottles/${BOTTLE_ID}"
if [[ -d "${_FRANKE}/drive_c" ]]; then
  BOTTLE_DIR="${_FRANKE}"
  WHISKY_LIBS="${HOME}/Library/Application Support/com.franke.Whisky"
elif [[ -d "${_ISAAC}/drive_c" ]]; then
  BOTTLE_DIR="${_ISAAC}"
  WHISKY_LIBS="${HOME}/Library/Application Support/com.isaacmarovitz.Whisky"
else
  echo "❌ Bottle не найден: ${BOTTLE_NAME} (${BOTTLE_ID})"
  echo "   Проверьте UUID: bash ${GOG_DIR}/list-bottles.sh"
  exit 1
fi
unset _FRANKE _ISAAC

WINE64="${WHISKY_LIBS}/Libraries/Wine/bin/wine64"
WINE_LIB="${WHISKY_LIBS}/Libraries/Wine/lib"
WINEPATH_BIN="${WHISKY_LIBS}/Libraries/Wine/bin/winepath"

gog_data_volume_path() {
  if [[ -d /System/Volumes/Data ]]; then
    echo /System/Volumes/Data
  else
    echo "${HOME}"
  fi
}

gog_disk_free_kb() {
  df -k "$(gog_data_volume_path)" | awk 'NR==2 {print $4}'
}

gog_disk_guard() {
  local min_gb="${1:-5}"
  local min_kb free_kb
  min_kb=$((min_gb * 1024 * 1024))
  free_kb="$(gog_disk_free_kb)"
  if [[ "${free_kb}" -lt "${min_kb}" ]]; then
    echo "❌ Мало места (<${min_gb} GB на Data)."
    return 1
  fi
  return 0
}

gog_swap_used_mb() {
  local used
  used="$(sysctl vm.swapusage 2>/dev/null | sed -n 's/.*used = \([0-9.]*\)M.*/\1/p')"
  [[ -n "${used}" ]] || return 1
  printf '%.0f' "${used}"
}

gog_swap_guard() {
  local max_mb="${1:-400}"
  local used
  used="$(gog_swap_used_mb)" || return 0
  if awk -v u="${used}" -v m="${max_mb}" 'BEGIN{exit !(u>=m)}'; then
    echo "❌ Swap уже ~${used}MB (лимит ${max_mb}MB) — запуск GOG/Wine запрещён."
    echo "   bash ${GOG_DIR}/emergency-stop.sh"
    echo "   затем перезагрузка Mac (swap macOS отдаёт медленно)"
    return 1
  fi
  return 0
}

# JA3/CrossOver: жёсткий стоп только если swap высокий И Wine/JA3 ещё живы.
# «Залипший» swap после закрытия (macOS не отдал) — предупреждение, запуск разрешён.
gog_wine_or_ja3_active() {
  pgrep -f 'JA3\.exe|wineserver|wine64-preloader|winedbg|wine64\.exe|CrossOver.*wine' >/dev/null 2>&1
}

gog_swap_guard_ja3_launch() {
  local soft_mb="${1:-1200}"
  local hard_mb="${2:-4096}"
  local used
  used="$(gog_swap_used_mb)" || return 0
  if [[ "${JA3_IGNORE_SWAP:-0}" == "1" ]]; then
    echo "⚠️  JA3_IGNORE_SWAP=1 — swap ~${used}MB"
    return 0
  fi
  if gog_wine_or_ja3_active; then
    if awk -v u="${used}" -v m="${soft_mb}" 'BEGIN{exit !(u>=m)}'; then
      echo "❌ Swap ~${used}MB и Wine/JA3 ещё работают (лимит ${soft_mb}MB)."
      echo "   bash ${GOG_DIR}/reset-ja3-crossover.sh  или  bash ${GOG_DIR}/emergency-stop.sh"
      echo "   затем reboot Mac. Или: JA3_IGNORE_SWAP=1 bash …/run-ja3-crossover.sh"
      return 1
    fi
    return 0
  fi
  if awk -v u="${used}" -v m="${hard_mb}" 'BEGIN{exit !(u>=m)}'; then
    echo "❌ Swap ~${used}MB (лимит ${hard_mb}MB) — reboot Mac."
    echo "   Или: JA3_IGNORE_SWAP=1 bash …/run-ja3-crossover.sh"
    return 1
  fi
  if awk -v u="${used}" -v m="${soft_mb}" 'BEGIN{exit !(u>=m)}'; then
    echo "⚠️  Swap ~${used}MB — залип после прошлых сессий (Wine не запущен). Запуск JA3…"
    echo "   (reboot снизит swap; JA3_IGNORE_SWAP=1 — принудительный игнор)"
  fi
  return 0
}

# Виртуальный стол Wine — окно CEF часто «есть в логах», но не видно на macOS без /desktop.
GOG_VDESKTOP="${GOG_VDESKTOP:-1280x800}"
# 0 = прямой GalaxyClient (рекомендуется; vdesktop — в Whisky Metadata или launch-galaxy-ui.sh).
GOG_USE_WINEVDESKTOP="${GOG_USE_WINEVDESKTOP:-0}"
# GOG_LAUNCH_FG=1 — exec в текущем терминале (лучше для видимости окна, блокирует shell).
GOG_LAUNCH_FG="${GOG_LAUNCH_FG:-0}"
# GOG_CEF_PROFILE=steam — добавить -cef-in-process-gpu (A/B если login пустой).
# /deelevated — обязательно в Wine (иначе DeelevateStrategy + exit -31, см. WineHQ #41584).
GOG_GALAXY_BASE_ARGS="${GOG_GALAXY_BASE_ARGS:-/runWithoutUpdating /deelevated}"
GOG_GALAXY_CEF_ARGS="${GOG_GALAXY_CEF_ARGS:--allosarches -cef-force-32bit -no-cef-sandbox -cef-disable-gpu}"

gog_galaxy_cef_args_array() {
  local -a a=(${GOG_GALAXY_BASE_ARGS} ${GOG_GALAXY_CEF_ARGS})
  if [[ "${GOG_CEF_PROFILE:-}" == "steam" ]]; then
    a+=(-cef-in-process-gpu)
  fi
  printf '%s\n' "${a[@]}"
}

export_wine_env_gog() {
  export WINEPREFIX="${BOTTLE_DIR}"
  export WINEMSYNC=1
  unset WINEESYNC 2>/dev/null || true
  local _wine_ext="${WHISKY_LIBS}/Libraries/Wine/lib/external"
  if [[ -d "${_wine_ext}/D3DMetal.framework" ]]; then
    export DYLD_FRAMEWORK_PATH="${_wine_ext}:${DYLD_FRAMEWORK_PATH:-}"
    export DYLD_LIBRARY_PATH="${_wine_ext}:${WINE_LIB}:${DYLD_LIBRARY_PATH:-}"
  else
    export DYLD_LIBRARY_PATH="${WINE_LIB}:${DYLD_LIBRARY_PATH:-}"
  fi
  unset _wine_ext
  export WINEDLLOVERRIDES="gdiplus=n,b"
  unset DXVK_ASYNC DXVK_HUD 2>/dev/null || true
  export WINEDEBUG=-all
  export MVK_CONFIG_LOG_LEVEL=0
}

ja3_gptk_available() {
  [[ -d "${WHISKY_LIBS}/Libraries/Wine/lib/external/D3DMetal.framework" ]] && return 0
  [[ -f "${WHISKY_LIBS}/Libraries/.gptk_installed" ]] && return 0
  [[ -d "${WHISKY_LIBS}/D3DMetal" ]] && return 0
  [[ -d "${WHISKY_LIBS}/GPTK" ]] && return 0
  return 1
}

ja3_bottle_uses_d3dmetal() {
  local meta="${BOTTLE_DIR}/Metadata.plist"
  [[ -f "${meta}" ]] || return 1
  plutil -extract graphicsConfig.backend raw -o - "${meta}" 2>/dev/null | grep -q d3dMetal
}

ja3_dxmt_installed() {
  [[ -f "${BOTTLE_DIR}/.ja3_dxmt_installed" ]]
}

# JA3 = D3D12 (Porting Kit / GPTK). Без GPTK — best-effort D3D11+DXVK (d3d12=d).
export_wine_env_ja3() {
  export_wine_env_gog
  if ja3_gptk_available || ja3_bottle_uses_d3dmetal; then
    export WINED3DMETAL=1
    unset DXVK_ASYNC DXVK_HUD DXVK_CONFIG_FILE 2>/dev/null || true
    # builtin d3d12/dxgi + libd3dshared.so; без n,b на GPTK PE
    export WINEDLLOVERRIDES="libxess,xess,dxcompiler,dxil,nvngx_dlss,XeFX,XeFX_Loader=d;gdiplus=n,b"
    return 0
  fi
  if ja3_dxmt_installed; then
    # DXMT builtin: не ставить dxgi/d3d11=n,b (ломает загрузку, c000007b).
    export WINEDLLOVERRIDES="d3d12=d;libxess,xess,dxcompiler,dxil,nvngx_dlss,XeFX,XeFX_Loader=d;gdiplus=n,b"
  else
    export WINEDLLOVERRIDES="d3d11,d3d10core=n,b;d3d12=d;libxess,xess,dxcompiler,dxil,nvngx_dlss,XeFX,XeFX_Loader=d;gdiplus=n,b"
  fi
  unset DXVK_ASYNC DXVK_HUD DXVK_CONFIG_FILE 2>/dev/null || true
  export SDL_VIDEO_MAC_FULLSCREEN_SPACES="${SDL_VIDEO_MAC_FULLSCREEN_SPACES:-0}"
  export MVK_CONFIG_RESUME_LOST_DEVICE=1
}

export_wine_env_ja3_d3dmetal() {
  export_wine_env_gog
  export WINED3DMETAL=1
  export WINEDLLOVERRIDES="libxess,xess,dxcompiler,dxil,nvngx_dlss,XeFX,XeFX_Loader=d;gdiplus=n,b"
  unset DXVK_ASYNC DXVK_HUD 2>/dev/null || true
}

gog_steam_client_in_bottle() {
  local f
  [[ -d "${BOTTLE_DIR}/drive_c/Program Files (x86)/Steam" ]] && return 0
  [[ -f "${BOTTLE_DIR}/drive_c/Program Files (x86)/Steam/steam.exe" ]] && return 0
  f="$(find "${BOTTLE_DIR}/drive_c" -maxdepth 4 -iname 'steam.exe' -print -quit 2>/dev/null || true)"
  [[ -n "${f}" ]]
}

gog_assert_no_steam_client() {
  if gog_steam_client_in_bottle; then
    echo "❌ В bottle ${BOTTLE_NAME} найден Steam client — контур GOG/JA3 без Steam."
    echo "   bash ${GOG_DIR}/purge-steam-from-bottle.sh"
    return 1
  fi
  if [[ "${BOTTLE_ID}" == "38412122-AAE1-4831-9F2E-6A0EB364B3F9" ]]; then
    echo "❌ Это bottle HoMM-OldenEra (Steam). JA3 только в GOG-Install:"
    echo "   bash ${GOG_DIR}/use-bottle.sh <UUID-GOG-Install>"
    return 1
  fi
  return 0
}

gog_wine_check() {
  if [[ ! -x "${WINE64}" ]]; then
    echo "Нет Wine: bash ${GAMES_DIR}/install-whiskywine-manual.sh"
    exit 1
  fi
  if [[ ! -d "${BOTTLE_DIR}/drive_c" ]]; then
    echo "❌ Нет drive_c в ${BOTTLE_DIR}"
    echo "   Откройте bottle «${BOTTLE_NAME}» в Whisky один раз."
    exit 1
  fi
}
