#!/bin/bash

set -eoux pipefail

source common

do_ovn_ipsec_encryption_check () {
    echo "INFO: Ensuring ovn-ipsec is enabled"
    IPSEC_PODS=($(oc -n openshift-ovn-kubernetes get pods -l app=ovn-ipsec -o=jsonpath='{.items[*].metadata.name}'))
    WORKER_NODES=($(get_worker_nodes_linux))
    DATE=$(date +"%Y-%m-%d")
    PCAP_FILENAME="ipsec-test-${DATE}.pcap"

    # TODO check with oc get network.operator.openshift.io/cluster -o=jsonpath='{.items[*].spec.defaultNetwork.ovnKubernetesConfig.ipsecConfig}'
    # once tests can be run with real cluster
    if [ -z "$IPSEC_PODS" ]; then
        echo "No ovn-ipsec pods exist, tunnel traffic will be unencrypted --> see $PCAP_FILENAME"
    else
        echo "ovn-ipsec is enabled, tunnel traffic should be encryted --> see ${PCAP_FILENAME}"
    fi

    echo "ovn-ipsec is enabled"

    client_debug_pod="client-debug"-$(get_random_name); server_debug_pod="server-debug"-$(get_random_name)

    create_pod_on_node $client_debug_pod "${WORKER_NODES[0]}"
    create_pod_on_node $server_debug_pod "${WORKER_NODES[1]}"

    server_debug_pod_ip=$(get_pod_ip $server_debug_pod $(get_current_namespace))

    echo "INFO: make sure interface eth0 exists"

    if ip link list | grep -q eth0 ; then
        echo "INFO: interface eth0 exists!"
        interface="eth0"
    else
        echo "INFO: interface eth0 is not up sniff on all interfaces"
        interface="any"
    fi

    echo "INFO: packet sniffing command is: tcpdump -i ${interface} -vv -c 2 -w ${PCAP_FILENAME} src \
    $(kubectl get node "${WORKER_NODES[0]}" -o jsonpath='{.status.addresses[?(@.type=="InternalIP")].address}') \
    && dst $(kubectl get node "${WORKER_NODES[1]}" -o jsonpath='{.status.addresses[?(@.type=="InternalIP")].address}')"

    #start sniffer in background, but only look for packets going over the tunnel from node1 -> node2

    timeout 30s  tcpdump -i ${interface} -vv -c 2 -w "${PCAP_FILENAME}" \
    src "$(kubectl get node "${WORKER_NODES[0]}" -o jsonpath='{.status.addresses[?(@.type=="InternalIP")].address}')" and dst "$(kubectl get node "${WORKER_NODES[1]}" -o jsonpath='{.status.addresses[?(@.type=="InternalIP")].address}')" \
    & PID=$!

    echo "INFO: pinging server from client pod: oc rsh ${client_debug_pod} ping ${server_debug_pod_ip} -c 5 -W 2"

    oc rsh ${client_debug_pod} ping "${server_debug_pod_ip}" -c 10 -W 2 > /dev/null 2>&1

    wait "${PID}"

    if [ -f "${PCAP_FILENAME}" ]; then
        if tshark -r "${PCAP_FILENAME}" -T fields -e frame.protocols | grep -q "esp"; then
            echo "Tunnel traffic is encrypted with ovn-ipsec!"
        else
            echo "Tunnel traffic is not encrypted, check pcap: ${PCAP_FILENAME} for further details"
        fi
    else
        echo "tcpdump error ${PCAP_FILENAME} wasn't written"
    fi

}

main () {
    #TODO A better way of ensuring we can contact the API Server, serivce accounts
    do_ovn_ipsec_encryption_check
}

main
