#!/usr/bin/env bash # ----- # - You need the the following sudo permissions (visudo) for that user, # - who starts this script # - # - chris ALL=(ALL) NOPASSWD: /usr/bin/find # - chris ALL=(ALL) NOPASSWD: /usr/bin/systemctl start wg-quick* # - chris ALL=(ALL) NOPASSWD: /usr/bin/systemctl stop wg-quick* # - chris ALL=(ALL) NOPASSWD:/bin/rm -f /var/run/* # - chris ALL=(ALL) NOPASSWD:/bin/kill # ----- script_name="$(basename $(realpath $0))" working_dir="$(dirname $(realpath $0))" log_file="$(mktemp)" conf_file="${working_dir}/conf/${script_name%%.*}.conf" DEFAULT_WIREGUARD_DIR="/etc/wireguard" DEFAULT_VPN_User="chris" VPN_Network="" declare -a wireguard_connection_arr=() # ---------- # Base Function(s) # ---------- clean_up() { rm -f $log_file blank_line exit $1 } echononl(){ if $terminal ; then echo X\\c > /tmp/shprompt$$ if [ `wc -c /tmp/shprompt$$ | awk '{print $1}'` -eq 1 ]; then echo -e -n " $*\\c" 1>&2 else echo -e -n " $*" 1>&2 fi rm /tmp/shprompt$$ fi } fatal(){ echo "" if $terminal ; then echo -e " [ \033[31m\033[1mFatal\033[m ] $*" else echo -e " [ Fatal ] $*" fi echo "" if $terminal ; then echo -e " \033[1mScript terminated\033[m.." else echo -e " Script terminated.." fi echo "" rm -f $log_file exit 1 } error (){ echo "" if $terminal ; then echo -e " [ \033[31m\033[1mError\033[m ] $*" else echo " [ Error ] $*" fi echo "" } warn (){ if $terminal ; then echo "" if $terminal ; then echo -e " [ \033[33m\033[1mWarn\033[m ] $*" else echo " [ Warn ] $*" fi echo "" fi } info (){ if $terminal ; then echo "" if $terminal ; then echo -e " [ \033[32m\033[1mInfo\033[m ] $*" else echo " [ Warn ] $*" fi echo "" fi } echo_done() { if $terminal ; then echo -e "\033[75G[ \033[32mdone\033[m ]" fi } echo_failed(){ if $terminal ; then echo -e "\033[75G[ \033[1;31mfailed\033[m ]" fi } echo_wait(){ if $terminal ; then echo -en "\033[75G[ \033[5m\033[1m..\033[m ]" fi } echo_skipped() { if $terminal ; then echo -e "\033[75G[ \033[33m\033[1mskipped\033[m ]" fi } blank_line() { if $terminal ; then echo "" fi } is_valid_ipv4() { local -a octets=( ${1//\./ } ) local RETURNVALUE=0 # return an error if the IP doesn't have exactly 4 octets [[ ${#octets[@]} -ne 4 ]] && return 1 for octet in ${octets[@]} do if [[ ${octet} =~ ^[0-9]{1,3}$ ]] then # shift number by 8 bits, anything larger than 255 will be > 0 ((RETURNVALUE += octet>>8 )) else # octet wasn't numeric, return error return 1 fi done return ${RETURNVALUE} } # - Test if given argument is a valid IPv6 Address # - is_valid_ipv6() { local _ipv6="$1" _regex_ipv6='^([0-9a-fA-F]{0,4}:){1,7}[0-9a-fA-F]{0,4}$' if [[ "$_ipv6" =~ ${_regex_ipv6} ]]; then return 0 else return 1 fi } is_number() { return $(test ! -z "${1##*[!0-9]*}" > /dev/null 2>&1); # - also possible # - #[[ ! -z "${1##*[!0-9]*}" ]] && return 0 || return 1 #return $([[ ! -z "${1##*[!0-9]*}" ]]) } is_int() { return $(test "$@" -eq "$@" > /dev/null 2>&1); } # ---------- # - Jobhandling # ---------- # - Run 'clean_up' for signals SIGHUP SIGINT SIGTERM # - trap clean_up SIGHUP SIGINT SIGTERM # ---------- # - Some checks .. # ---------- # - Running in a terminal? # - if [[ -t 1 ]] ; then terminal=true else terminal=false fi [[ -n "$WIREGUARD_DIR" ]] || WIREGUARD_DIR="$DEFAULT_WIREGUARD_DIR" [[ -n "$VPN_User" ]] || VPN_User="$DEFAULT_VPN_User" # ---------- # - Headline # ---------- if $terminal ; then echo "" echo -e "\033[1m----------\033[m" echo -e "\033[32m\033[1mRunning script \033[m\033[1m$script_name\033[32m .. \033[m" echo -e "\033[1m----------\033[m" fi blank_line echononl "Load Configuration File $(basename ${conf_file}).." if [[ -f "$conf_file" ]]; then source "$conf_file" > $log_file 2>&1 if [[ $? -eq 0 ]]; then echo_done else echo_failed fatal "$(cat $log_file)" fi else echo_skipped fi blank_line # ---------- # - Main part of script # ---------- if $terminal ; then # - Get available WireGuard configuration files. # - while IFS='' read -r -d '' _file_name ; do #[[ "$_file_name" = ".." ]] && continue #[[ "$_file_name" = "." ]] && continue _wg_conf_file="$(basename "$_file_name")" _wg_device="${_wg_conf_file%%.conf}" wireguard_connection_arr+=("$(basename "$_file_name")") wireguard_device_arr+=("$_wg_device") if $(ip -br addr show | grep "$_wg_device" > /dev/null 2>&1 ) ; then wireguard_device_online_arr+=("$_wg_device") else wireguard_device_offline_arr+=("$_wg_device") fi done < <(sudo find "$WIREGUARD_DIR" -mindepth 1 -maxdepth 1 -type f -regex '.*.conf' -print0 | sort -z) if [[ ${#wireguard_connection_arr[@]} -eq 0 ]] ; then fatal "No WireGuard VPN configured!" clean_up 1 fi if [[ ${#wireguard_device_online_arr[@]} -eq 0 ]]; then info "All available WireGuard connections already offline." clean_up 2 fi echo "" echo "" echo "" echo -e " \033[1mWhich Connection should be terminated?\033[m" echo "" for i in ${!wireguard_device_online_arr[@]}; do WG_ENTRY="${wireguard_device_online_arr[$i]}" WG_ENTRY="${WG_ENTRY#wg-}" echo -e " [$i]\033[9G$WG_ENTRY" done echo "" echo -e " [99]\033[9G\033[33mExit programm\033[m" echo "" echononl "Choose: " _OK=false while ! $_OK ; do read _IN if is_number "$_IN" && [[ -n ${wireguard_device_online_arr[$_IN]} ]]; then WG_DEVICE="${wireguard_device_online_arr[$_IN]}" _OK=true elif is_number "$_IN" && [[ $_IN -eq 99 ]] ;then echo"" exit 0 else echo "" echo -e "\tWrong value !" echo "" echononl "Choose again: " fi done fi blank_line blank_line echononl "Terminate WireGuard connection \033[32m\033[1m${WG_DEVICE#wg-}\033[m.." sudo systemctl stop wg-quick@${WG_DEVICE} if [[ $? -gt 0 ]] ; then echo_failed else echo_done fi clean_up 0