#!/bin/bash

# Check if running as root (needed for hosts file modification and firewall rules)
if [ "$EUID" -ne 0 ]; then 
    echo "Please run this script as root (use 'sudo')"
    exit 1
fi

# Get the directory where this script is located
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )"

echo "=== Configuring Firewall for ACBSP Executable (and SoftEther TCP 5555) ==="

ACB_EXEC="$SCRIPT_DIR/ACBSP.exe"
ACB_NAME="_ACBMP_P2P"
VPN_RULE="_SOFTETHER_VPN"

# Function to check if ufw is active
is_ufw_active() {
    ufw status | grep -q "Status: active"
    return $?
}

# -----------------------------
# UFW (Ubuntu/Debian)
# -----------------------------
if command -v ufw >/dev/null 2>&1; then
    if is_ufw_active; then
        echo "Configuring UFW firewall rules..."

        # Remove any existing rules for this executable
        ufw status numbered | grep "$ACB_NAME" | awk '{print $1}' | sort -r | while read num; do
            ufw delete -f "$num" >/dev/null 2>&1
        done

        # Add new inbound/outbound rules for the executable
        ufw allow in from any to any app "$(basename "$ACB_EXEC")" comment "$ACB_NAME"
        ufw allow out from any to any app "$(basename "$ACB_EXEC")" comment "$ACB_NAME"
        echo "UFW rules for ACBSP executable created"

        # Add TCP 5555
        echo "Adding UFW rule for TCP 5555 (_SOFTETHER_VPN)"
        ufw allow 5555/tcp comment "$VPN_RULE" >/dev/null 2>&1
    fi
fi

# -----------------------------
# firewalld (Fedora/RHEL/CentOS)
# -----------------------------
if command -v firewall-cmd >/dev/null 2>&1; then
    if systemctl is-active --quiet firewalld; then
        echo "firewalld is active — adding port 5555 TCP rule..."

        firewall-cmd --zone=public --add-port=5555/tcp --permanent >/dev/null 2>&1
        firewall-cmd --reload >/dev/null 2>&1

        echo "firewalld: TCP 5555 opened using name $VPN_RULE"
    fi
fi

# -----------------------------
# iptables fallback
# -----------------------------
if ! command -v ufw >/dev/null 2>&1 && ! command -v firewall-cmd >/dev/null 2>&1; then
    echo "Using iptables fallback..."

    iptables -C INPUT -p tcp --dport 5555 -j ACCEPT 2>/dev/null
    if [ $? -ne 0 ]; then
        iptables -A INPUT -p tcp --dport 5555 -j ACCEPT
        echo "iptables: TCP 5555 allowed"
    fi
fi

echo "=== Firewall Configuration Complete ==="
echo

CONFIG_FILE="${SCRIPT_DIR}/_ACBMP.ini"
HOSTS_FILE="/etc/hosts"
TEMP_HOSTS_FILE="/tmp/hosts.tmp"

# --- SoftEther auto-detection logic ---
echo "Searching for SoftEther VPN binaries..."
VPNCLIENT_BIN=$(command -v vpnclient 2>/dev/null)
[ -z "$VPNCLIENT_BIN" ] && VPNCLIENT_BIN=$(find /usr/local /opt "$HOME" ~/Downloads ~/Desktop -type f -name "vpnclient" 2>/dev/null | head -n 1)

VPNCMD_BIN=$(command -v vpncmd 2>/dev/null)
[ -z "$VPNCMD_BIN" ] && VPNCMD_BIN=$(find /usr/local /opt "$HOME" ~/Downloads ~/Desktop -type f -name "vpncmd" 2>/dev/null | head -n 1)

if ! [ -x "$VPNCLIENT_BIN" ] || ! [ -x "$VPNCMD_BIN" ]; then
    echo "Error: Could not find SoftEther VPN client binaries!"
    echo "Please install SoftEtherVPN Client and make sure vpnclient and vpncmd exist."
    exit 1
fi

# Function to read a value from the config file
get_config_value() {
    grep -i "^$1=" "$CONFIG_FILE" | cut -d'=' -f2- | tr -d '\r'
}

# Check if config file exists
if [ ! -f "$CONFIG_FILE" ]; then
    echo "_ACBMP.ini not found, creating a new one..."
    cat > "$CONFIG_FILE" << EOL
ServerIP=
ServerHostname=animusnetwork2.ydns.eu
onlineUser=your_username
onlinePassword=your_password
EOL
    echo "A new _ACBMP.ini has been created in $SCRIPT_DIR"
    echo "Please fill in the required values and run this script again."
    chmod 600 "$CONFIG_FILE"
    exit 1
fi

# Read config values
SERVER_IP=$(get_config_value "ServerIP")
SERVER_HOSTNAME=$(get_config_value "ServerHostname")
onlineUser=$(get_config_value "onlineUser")
onlinePassword=$(get_config_value "onlinePassword")

# Determine which IP to use
if [ -n "$SERVER_IP" ]; then
    IP="$SERVER_IP"
    echo "Using provided server IP: $IP"
elif [ -n "$SERVER_HOSTNAME" ]; then
    echo "Resolving IPv4 for hostname: $SERVER_HOSTNAME"
    IP=$(getent ahostsv4 "$SERVER_HOSTNAME" | head -n 1 | awk '{print $1}')
    if [ -z "$IP" ]; then
        echo "Error: Could not resolve IPv4 of the hostname $SERVER_HOSTNAME"
        exit 1
    fi
    echo "Resolved IPv4 for $SERVER_HOSTNAME: $IP"
else
    echo "Error: Neither ServerIP nor ServerHostname provided in _ACBMP.ini"
    exit 1
fi

# Backup the current hosts file
cp "$HOSTS_FILE" "${HOSTS_FILE}.bak"
echo "Backed up hosts file to ${HOSTS_FILE}.bak"

# Update or add the hosts entry
if grep -qi "onlineconfigservice.ubi.com" "$HOSTS_FILE"; then
    if ! grep -q "^[[:space:]]*${IP}[[:space:]]\+onlineconfigservice.ubi.com" "$HOSTS_FILE"; then
        grep -vi "onlineconfigservice.ubi.com" "$HOSTS_FILE" > "$TEMP_HOSTS_FILE"
        echo -e "${IP}\tonlineconfigservice.ubi.com" >> "$TEMP_HOSTS_FILE"
        mv "$TEMP_HOSTS_FILE" "$HOSTS_FILE"
        echo "Updated the hosts file with the new IP."
    else
        echo "The hosts file entry is already up to date."
    fi
else
    echo -e "${IP}\tonlineconfigservice.ubi.com" | sudo tee -a "$HOSTS_FILE" > /dev/null
    echo "Added the server redirection to the hosts file."
fi

# Change to the script's directory
cd "$SCRIPT_DIR"

[ -n "$onlineUser" ] && [ -n "$onlinePassword" ] && echo "Signing in as user: $onlineUser"

# Backup ACBSP.exe and rename ACBMP.exe
if [ -f "ACBSP.exe" ] && [ ! -f "ACBSP1.exe" ]; then
    echo "Backing up ACBSP.exe to ACBSP1.exe..."
    mv "ACBSP.exe" "ACBSP1.exe"
fi
if [ -f "ACBMP.exe" ]; then
    echo "Renaming ACBMP.exe to ACBSP.exe..."
    mv "ACBMP.exe" "ACBSP.exe"
fi

# Function to configure random IP on the VPN interface
configure_ip() {
    local interface=$1
    octet3=$((RANDOM % 8 + 248))
    octet4=$(( octet3 == 255 ? RANDOM % 129 : RANDOM % 255 ))
    ip_addr="172.29.$octet3.$octet4"
    echo "Assigning random IP: $ip_addr/20 on $interface"
    ip addr flush dev "$interface" 2>/dev/null
    ip addr add "$ip_addr/20" dev "$interface"
    ip link set "$interface" up
    ip route add default dev "$interface" 2>/dev/null
    echo "IP and route configured successfully."
}

echo "=== Starting SoftEther VPN Setup ==="
sudo "$VPNCLIENT_BIN" start
[ $? -ne 0 ] && echo "Error: Failed to start SoftEther VPN client." && exit 1
echo "SoftEther VPN client started successfully."

# --- VPN NIC setup ---
VPN_NIC="vpn"
if ! "$VPNCMD_BIN" localhost /client /CMD NicList | grep -q "$VPN_NIC"; then
    echo "Creating new VPN NIC..."
    "$VPNCMD_BIN" localhost /client /CMD NicCreate "$VPN_NIC"
else
    echo "VPN NIC already exists, skipping creation..."
fi
"$VPNCMD_BIN" localhost /client /CMD NicEnable "$VPN_NIC"

# --- VPN Account setup ---
VPN_ACCOUNT="Animus Network"
if "$VPNCMD_BIN" localhost /client /CMD AccountList | grep -q "$VPN_ACCOUNT"; then
    echo "Deleting existing VPN account to avoid duplicates..."
    "$VPNCMD_BIN" localhost /client /CMD AccountDelete "$VPN_ACCOUNT"
fi
[ ! -f "Animus-Network.vpn" ] && echo "Error: Animus-Network.vpn not found!" && exit 1
"$VPNCMD_BIN" localhost /client /CMD AccountImport Animus-Network.vpn
"$VPNCMD_BIN" localhost /client /CMD AccountNicSet "$VPN_ACCOUNT" /NICNAME:vpn_vpn
"$VPNCMD_BIN" localhost /client /CMD AccountConnect "$VPN_ACCOUNT"
"$VPNCMD_BIN" localhost /client /CMD AccountStatusGet "$VPN_ACCOUNT"

# Configure VPN NIC with random IP
configure_ip vpn_vpn

echo "Waiting for VPN connection to stabilize..."
sleep 3

# Display network info
echo -e "\n--- Network Configuration ---"
ip addr show vpn_vpn 2>/dev/null || echo "Interface vpn_vpn not found"
echo -e "\n--- IPv4 Address ---"
ip -4 addr show vpn_vpn | grep -oP '(?<=inet\s)\d+(\.\d+){3}' || echo "No IPv4 assigned"
echo -e "\n--- Routing Table ---"
ip route | grep vpn_vpn || echo "No specific routes for vpn_vpn"
echo -e "\n--- Interface Status ---"
ip -4 addr show vpn_vpn 2>/dev/null || echo "No IP configuration found for vpn_vpn"

# Launch the game
if [ -f "ACBSP.exe" ]; then
    echo "Launching Assassin's Creed Brotherhood Multiplayer..."

    if [ -n "$onlineUser" ] && [ -n "$onlinePassword" ]; then
        wine "ACBSP.exe" "/onlineUser:$onlineUser" "/onlinePassword:$onlinePassword"
    else
        wine "ACBSP.exe"
    fi

    if [ $? -ne 0 ]; then
        echo "Wine failed, falling back to Steam..."

        if command -v steam >/dev/null 2>&1; then
            GAME_ID="48190"
            STEAM_USER="${SUDO_USER:-$USER}"

            if [ -n "$onlineUser" ] && [ -n "$onlinePassword" ]; then
                sudo -u "$STEAM_USER" steam -applaunch $GAME_ID -- "/onlineUser:$onlineUser" "/onlinePassword:$onlinePassword"
            else
                sudo -u "$STEAM_USER" steam -applaunch $GAME_ID
            fi
        else
            echo "Error: Steam not found. Cannot launch the game."
            exit 1
        fi
    fi
else
    echo "Error: Could not find ACBSP.exe in $SCRIPT_DIR"
    exit 1
fi
