diff --git a/openvpn-install.sh b/openvpn-install.sh index 92bb343..9f71dad 100755 --- a/openvpn-install.sh +++ b/openvpn-install.sh @@ -103,8 +103,8 @@ function installUnbound() { apt-get install -y unbound # Configuration - echo 'interface: 10.8.0.1 -access-control: 10.8.0.1/24 allow + echo 'interface: 10.5.0.1 +access-control: 10.5.0.1/24 allow hide-identity: yes hide-version: yes use-caps-for-id: yes @@ -114,8 +114,8 @@ prefetch: yes' >>/etc/unbound/unbound.conf yum install -y unbound # Configuration - sed -i 's|# interface: 0.0.0.0$|interface: 10.8.0.1|' /etc/unbound/unbound.conf - sed -i 's|# access-control: 127.0.0.0/8 allow|access-control: 10.8.0.1/24 allow|' /etc/unbound/unbound.conf + sed -i 's|# interface: 0.0.0.0$|interface: 10.5.0.1|' /etc/unbound/unbound.conf + sed -i 's|# access-control: 127.0.0.0/8 allow|access-control: 10.5.0.1/24 allow|' /etc/unbound/unbound.conf sed -i 's|# hide-identity: no|hide-identity: yes|' /etc/unbound/unbound.conf sed -i 's|# hide-version: no|hide-version: yes|' /etc/unbound/unbound.conf sed -i 's|use-caps-for-id: no|use-caps-for-id: yes|' /etc/unbound/unbound.conf @@ -124,8 +124,8 @@ prefetch: yes' >>/etc/unbound/unbound.conf dnf install -y unbound # Configuration - sed -i 's|# interface: 0.0.0.0$|interface: 10.8.0.1|' /etc/unbound/unbound.conf - sed -i 's|# access-control: 127.0.0.0/8 allow|access-control: 10.8.0.1/24 allow|' /etc/unbound/unbound.conf + sed -i 's|# interface: 0.0.0.0$|interface: 10.5.0.1|' /etc/unbound/unbound.conf + sed -i 's|# access-control: 127.0.0.0/8 allow|access-control: 10.5.0.1/24 allow|' /etc/unbound/unbound.conf sed -i 's|# hide-identity: no|hide-identity: yes|' /etc/unbound/unbound.conf sed -i 's|# hide-version: no|hide-version: yes|' /etc/unbound/unbound.conf sed -i 's|# use-caps-for-id: no|use-caps-for-id: yes|' /etc/unbound/unbound.conf @@ -147,8 +147,8 @@ prefetch: yes' >>/etc/unbound/unbound.conf directory: "/etc/unbound" trust-anchor-file: trusted-key.key root-hints: root.hints - interface: 10.8.0.1 - access-control: 10.8.0.1/24 allow + interface: 10.5.0.1 + access-control: 10.5.0.1/24 allow port: 53 num-threads: 2 use-caps-for-id: yes @@ -182,8 +182,8 @@ private-address: ::ffff:0:0/96" >>/etc/unbound/unbound.conf # Add Unbound 'server' for the OpenVPN subnet echo 'server: -interface: 10.8.0.1 -access-control: 10.8.0.1/24 allow +interface: 10.5.0.1 +access-control: 10.5.0.1/24 allow hide-identity: yes hide-version: yes use-caps-for-id: yes @@ -229,7 +229,7 @@ function installQuestions() { if [[ $APPROVE_IP =~ n ]]; then read -rp "IP address: " -e -i "$IP" IP fi - # If $IP is a private IP address, the server must be behind NAT + # If $IP is a private IP address, the server must be behind NAT if echo "$IP" | grep -qE '^(10\.|172\.1[6789]\.|172\.2[0-9]\.|172\.3[01]\.|192\.168)'; then echo "" echo "It seems this server is behind NAT. What is its public IPv4 address or hostname?" @@ -600,7 +600,6 @@ function installQuestions() { read -n1 -r -p "Press any key to continue..." fi } - function installOpenVPN() { if [[ $AUTO_INSTALL == "y" ]]; then # Set default choices so that no questions will be asked. @@ -615,7 +614,6 @@ function installOpenVPN() { CLIENT=${CLIENT:-client} PASS=${PASS:-1} CONTINUE=${CONTINUE:-y} - # Behind NAT, we'll default to the publicly reachable IPv4/IPv6. if [[ $IPV6_SUPPORT == "y" ]]; then PUBLIC_IP=$(curl https://ifconfig.co) @@ -624,16 +622,13 @@ function installOpenVPN() { fi ENDPOINT=${ENDPOINT:-$PUBLIC_IP} fi - # Run setup questions first, and set other variales if auto-install installQuestions - # Get the "public" interface from the default route NIC=$(ip -4 route ls | grep default | grep -Po '(?<=dev )(\S+)' | head -1) if [[ -z $NIC ]] && [[ $IPV6_SUPPORT == 'y' ]]; then NIC=$(ip -6 route show default | sed -ne 's/^default .* dev \([^ ]*\) .*$/\1/p') fi - # $NIC can not be empty for script rm-openvpn-rules.sh if [[ -z $NIC ]]; then echo @@ -646,7 +641,6 @@ function installOpenVPN() { exit 1 fi fi - # If OpenVPN isn't installed yet, install it. This script is more-or-less # idempotent on multiple runs, but will only install OpenVPN from upstream # the first time. @@ -679,14 +673,12 @@ function installOpenVPN() { rm -rf /etc/openvpn/easy-rsa/ fi fi - # Find out if the machine uses nogroup or nobody for the permissionless group if grep -qs "^nogroup:" /etc/group; then NOGROUP=nogroup else NOGROUP=nobody fi - # Install the latest version of easy-rsa from source, if not already installed. if [[ ! -d /etc/openvpn/easy-rsa/ ]]; then local version="3.0.7" @@ -694,7 +686,6 @@ function installOpenVPN() { mkdir -p /etc/openvpn/easy-rsa tar xzf ~/easy-rsa.tgz --strip-components=1 --directory /etc/openvpn/easy-rsa rm -f ~/easy-rsa.tgz - cd /etc/openvpn/easy-rsa/ || return case $CERT_TYPE in 1) @@ -705,27 +696,21 @@ function installOpenVPN() { echo "set_var EASYRSA_KEY_SIZE $RSA_KEY_SIZE" >vars ;; esac - # Generate a random, alphanumeric identifier of 16 characters for CN and one for server name SERVER_CN="cn_$(head /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 16 | head -n 1)" echo "$SERVER_CN" >SERVER_CN_GENERATED SERVER_NAME="server_$(head /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 16 | head -n 1)" echo "$SERVER_NAME" >SERVER_NAME_GENERATED - echo "set_var EASYRSA_REQ_CN $SERVER_CN" >>vars - # Create the PKI, set up the CA, the DH params and the server certificate ./easyrsa init-pki ./easyrsa --batch build-ca nopass - if [[ $DH_TYPE == "2" ]]; then # ECDH keys are generated on-the-fly so we don't need to generate them beforehand openssl dhparam -out dh.pem $DH_KEY_SIZE fi - ./easyrsa build-server-full "$SERVER_NAME" nopass EASYRSA_CRL_DAYS=3650 ./easyrsa gen-crl - case $TLS_SIG in 1) # Generate tls-crypt key @@ -742,16 +727,13 @@ function installOpenVPN() { cd /etc/openvpn/easy-rsa/ || return SERVER_NAME=$(cat SERVER_NAME_GENERATED) fi - # Move all the generated files cp pki/ca.crt pki/private/ca.key "pki/issued/$SERVER_NAME.crt" "pki/private/$SERVER_NAME.key" /etc/openvpn/easy-rsa/pki/crl.pem /etc/openvpn if [[ $DH_TYPE == "2" ]]; then cp dh.pem /etc/openvpn fi - # Make cert revocation list readable for non-root chmod 644 /etc/openvpn/crl.pem - # Generate server.conf echo "port $PORT" >/etc/openvpn/server.conf if [[ $IPV6_SUPPORT == 'n' ]]; then @@ -759,7 +741,6 @@ function installOpenVPN() { elif [[ $IPV6_SUPPORT == 'y' ]]; then echo "proto ${PROTOCOL}6" >>/etc/openvpn/server.conf fi - echo "dev tun user nobody group $NOGROUP @@ -767,9 +748,8 @@ persist-key persist-tun keepalive 10 120 topology subnet -server 10.8.0.0 255.255.255.0 +server 10.5.0.0 255.255.255.0 ifconfig-pool-persist ipp.txt" >>/etc/openvpn/server.conf - # DNS resolvers case $DNS in 1) # Current system resolvers @@ -789,7 +769,7 @@ ifconfig-pool-persist ipp.txt" >>/etc/openvpn/server.conf done ;; 2) # Self-hosted DNS resolver (Unbound) - echo 'push "dhcp-option DNS 10.8.0.1"' >>/etc/openvpn/server.conf + echo 'push "dhcp-option DNS 10.5.0.1"' >>/etc/openvpn/server.conf if [[ $IPV6_SUPPORT == 'y' ]]; then echo 'push "dhcp-option DNS fd42:42:42:42::1"' >>/etc/openvpn/server.conf fi @@ -827,8 +807,8 @@ ifconfig-pool-persist ipp.txt" >>/etc/openvpn/server.conf echo 'push "dhcp-option DNS 77.88.8.1"' >>/etc/openvpn/server.conf ;; 11) # AdGuard DNS - echo 'push "dhcp-option DNS 176.103.130.130"' >>/etc/openvpn/server.conf - echo 'push "dhcp-option DNS 176.103.130.131"' >>/etc/openvpn/server.conf + echo 'push "dhcp-option DNS 94.140.14.14"' >>/etc/openvpn/server.conf + echo 'push "dhcp-option DNS 94.140.15.15"' >>/etc/openvpn/server.conf ;; 12) # NextDNS echo 'push "dhcp-option DNS 45.90.28.167"' >>/etc/openvpn/server.conf @@ -842,7 +822,6 @@ ifconfig-pool-persist ipp.txt" >>/etc/openvpn/server.conf ;; esac echo 'push "redirect-gateway def1 bypass-dhcp"' >>/etc/openvpn/server.conf - # IPv6 network settings if needed if [[ $IPV6_SUPPORT == 'y' ]]; then echo 'server-ipv6 fd42:42:42:42::/112 @@ -851,18 +830,15 @@ push tun-ipv6 push "route-ipv6 2000::/3" push "redirect-gateway ipv6"' >>/etc/openvpn/server.conf fi - if [[ $COMPRESSION_ENABLED == "y" ]]; then echo "compress $COMPRESSION_ALG" >>/etc/openvpn/server.conf fi - if [[ $DH_TYPE == "1" ]]; then echo "dh none" >>/etc/openvpn/server.conf echo "ecdh-curve $DH_CURVE" >>/etc/openvpn/server.conf elif [[ $DH_TYPE == "2" ]]; then echo "dh dh.pem" >>/etc/openvpn/server.conf fi - case $TLS_SIG in 1) echo "tls-crypt tls-crypt.key" >>/etc/openvpn/server.conf @@ -871,7 +847,6 @@ push "redirect-gateway ipv6"' >>/etc/openvpn/server.conf echo "tls-auth tls-auth.key 0" >>/etc/openvpn/server.conf ;; esac - echo "crl-verify crl.pem ca ca.crt cert $SERVER_NAME.crt @@ -885,12 +860,10 @@ tls-cipher $CC_CIPHER client-config-dir /etc/openvpn/ccd status /var/log/openvpn/status.log verb 3" >>/etc/openvpn/server.conf - # Create client-config-dir dir mkdir -p /etc/openvpn/ccd # Create log dir mkdir -p /var/log/openvpn - # Enable routing echo 'net.ipv4.ip_forward=1' >/etc/sysctl.d/99-openvpn.conf if [[ $IPV6_SUPPORT == 'y' ]]; then @@ -898,7 +871,6 @@ verb 3" >>/etc/openvpn/server.conf fi # Apply sysctl rules sysctl --system - # If SELinux is enabled and a custom port was selected, we need this if hash sestatus 2>/dev/null; then if sestatus | grep "Current mode" | grep -qs "enforcing"; then @@ -907,12 +879,10 @@ verb 3" >>/etc/openvpn/server.conf fi fi fi - # Finally, restart and enable OpenVPN if [[ $OS == 'arch' || $OS == 'fedora' || $OS == 'centos' ]]; then # Don't modify package-provided service cp /usr/lib/systemd/system/openvpn-server@.service /etc/systemd/system/openvpn-server@.service - # Workaround to fix OpenVPN service on OpenVZ sed -i 's|LimitNPROC|#LimitNPROC|' /etc/systemd/system/openvpn-server@.service # Another workaround to keep using /etc/openvpn/ @@ -921,7 +891,6 @@ verb 3" >>/etc/openvpn/server.conf if [[ $OS == "fedora" ]]; then sed -i 's|--cipher AES-256-GCM --ncp-ciphers AES-256-GCM:AES-128-GCM:AES-256-CBC:AES-128-CBC:BF-CBC||' /etc/systemd/system/openvpn-server@.service fi - systemctl daemon-reload systemctl enable openvpn-server@server systemctl restart openvpn-server@server @@ -933,32 +902,26 @@ verb 3" >>/etc/openvpn/server.conf else # Don't modify package-provided service cp /lib/systemd/system/openvpn\@.service /etc/systemd/system/openvpn\@.service - # Workaround to fix OpenVPN service on OpenVZ sed -i 's|LimitNPROC|#LimitNPROC|' /etc/systemd/system/openvpn\@.service # Another workaround to keep using /etc/openvpn/ sed -i 's|/etc/openvpn/server|/etc/openvpn|' /etc/systemd/system/openvpn\@.service - systemctl daemon-reload systemctl enable openvpn@server systemctl restart openvpn@server fi - if [[ $DNS == 2 ]]; then installUnbound fi - # Add iptables rules in two scripts mkdir -p /etc/iptables - # Script to add rules echo "#!/bin/sh -iptables -t nat -I POSTROUTING 1 -s 10.8.0.0/24 -o $NIC -j MASQUERADE +iptables -t nat -I POSTROUTING 1 -s 10.5.0.0/24 -o $NIC -j MASQUERADE iptables -I INPUT 1 -i tun0 -j ACCEPT iptables -I FORWARD 1 -i $NIC -o tun0 -j ACCEPT iptables -I FORWARD 1 -i tun0 -o $NIC -j ACCEPT iptables -I INPUT 1 -i $NIC -p $PROTOCOL --dport $PORT -j ACCEPT" >/etc/iptables/add-openvpn-rules.sh - if [[ $IPV6_SUPPORT == 'y' ]]; then echo "ip6tables -t nat -I POSTROUTING 1 -s fd42:42:42:42::/112 -o $NIC -j MASQUERADE ip6tables -I INPUT 1 -i tun0 -j ACCEPT @@ -966,15 +929,13 @@ ip6tables -I FORWARD 1 -i $NIC -o tun0 -j ACCEPT ip6tables -I FORWARD 1 -i tun0 -o $NIC -j ACCEPT ip6tables -I INPUT 1 -i $NIC -p $PROTOCOL --dport $PORT -j ACCEPT" >>/etc/iptables/add-openvpn-rules.sh fi - # Script to remove rules echo "#!/bin/sh -iptables -t nat -D POSTROUTING -s 10.8.0.0/24 -o $NIC -j MASQUERADE +iptables -t nat -D POSTROUTING -s 10.5.0.0/24 -o $NIC -j MASQUERADE iptables -D INPUT -i tun0 -j ACCEPT iptables -D FORWARD -i $NIC -o tun0 -j ACCEPT iptables -D FORWARD -i tun0 -o $NIC -j ACCEPT iptables -D INPUT -i $NIC -p $PROTOCOL --dport $PORT -j ACCEPT" >/etc/iptables/rm-openvpn-rules.sh - if [[ $IPV6_SUPPORT == 'y' ]]; then echo "ip6tables -t nat -D POSTROUTING -s fd42:42:42:42::/112 -o $NIC -j MASQUERADE ip6tables -D INPUT -i tun0 -j ACCEPT @@ -982,35 +943,28 @@ ip6tables -D FORWARD -i $NIC -o tun0 -j ACCEPT ip6tables -D FORWARD -i tun0 -o $NIC -j ACCEPT ip6tables -D INPUT -i $NIC -p $PROTOCOL --dport $PORT -j ACCEPT" >>/etc/iptables/rm-openvpn-rules.sh fi - chmod +x /etc/iptables/add-openvpn-rules.sh chmod +x /etc/iptables/rm-openvpn-rules.sh - # Handle the rules via a systemd script echo "[Unit] Description=iptables rules for OpenVPN Before=network-online.target Wants=network-online.target - [Service] Type=oneshot ExecStart=/etc/iptables/add-openvpn-rules.sh ExecStop=/etc/iptables/rm-openvpn-rules.sh RemainAfterExit=yes - [Install] WantedBy=multi-user.target" >/etc/systemd/system/iptables-openvpn.service - # Enable service and apply rules systemctl daemon-reload systemctl enable iptables-openvpn systemctl start iptables-openvpn - # If the server is behind a NAT, use the correct IP address for the clients to connect to if [[ $ENDPOINT != "" ]]; then IP=$ENDPOINT fi - # client-template.txt is created so we have a template to add further users later echo "client" >/etc/openvpn/client-template.txt if [[ $PROTOCOL == 'udp' ]]; then @@ -1036,35 +990,28 @@ tls-cipher $CC_CIPHER ignore-unknown-option block-outside-dns setenv opt block-outside-dns # Prevent Windows 10 DNS leak verb 3" >>/etc/openvpn/client-template.txt - if [[ $COMPRESSION_ENABLED == "y" ]]; then echo "compress $COMPRESSION_ALG" >>/etc/openvpn/client-template.txt fi - # Generate the custom client.ovpn newClient echo "If you want to add more clients, you simply need to run this script another time!" } - function newClient() { echo "" echo "Tell me a name for the client." echo "The name must consist of alphanumeric character. It may also include an underscore or a dash." - until [[ $CLIENT =~ ^[a-zA-Z0-9_-]+$ ]]; do read -rp "Client name: " -e CLIENT done - echo "" echo "Do you want to protect the configuration file with a password?" echo "(e.g. encrypt the private key with a password)" echo " 1) Add a passwordless client" echo " 2) Use a password for the client" - until [[ $PASS =~ ^[1-2]$ ]]; do read -rp "Select an option [1-2]: " -e -i 1 PASS done - CLIENTEXISTS=$(tail -n +2 /etc/openvpn/easy-rsa/pki/index.txt | grep -c -E "/CN=$CLIENT\$") if [[ $CLIENTEXISTS == '1' ]]; then echo "" @@ -1083,7 +1030,6 @@ function newClient() { esac echo "Client $CLIENT added." fi - # Home directory of the user, where the client configuration (.ovpn) will be written if [ -e "/home/$CLIENT" ]; then # if $1 is a user name homeDir="/home/$CLIENT" @@ -1092,29 +1038,24 @@ function newClient() { else # if not SUDO_USER, use /root homeDir="/root" fi - # Determine if we use tls-auth or tls-crypt if grep -qs "^tls-crypt" /etc/openvpn/server.conf; then TLS_SIG="1" elif grep -qs "^tls-auth" /etc/openvpn/server.conf; then TLS_SIG="2" fi - # Generates the custom client.ovpn cp /etc/openvpn/client-template.txt "$homeDir/$CLIENT.ovpn" { echo "" cat "/etc/openvpn/easy-rsa/pki/ca.crt" echo "" - echo "" awk '/BEGIN/,/END/' "/etc/openvpn/easy-rsa/pki/issued/$CLIENT.crt" echo "" - echo "" cat "/etc/openvpn/easy-rsa/pki/private/$CLIENT.key" echo "" - case $TLS_SIG in 1) echo "" @@ -1129,14 +1070,11 @@ function newClient() { ;; esac } >>"$homeDir/$CLIENT.ovpn" - echo "" echo "The configuration file has been written to $homeDir/$CLIENT.ovpn." echo "Download the .ovpn file and import it in your OpenVPN client." - exit 0 } - function revokeClient() { NUMBEROFCLIENTS=$(tail -n +2 /etc/openvpn/easy-rsa/pki/index.txt | grep -c "^V") if [[ $NUMBEROFCLIENTS == '0' ]]; then @@ -1144,7 +1082,6 @@ function revokeClient() { echo "You have no existing clients!" exit 1 fi - echo "" echo "Select the existing client certificate you want to revoke" tail -n +2 /etc/openvpn/easy-rsa/pki/index.txt | grep "^V" | cut -d '=' -f 2 | nl -s ') ' @@ -1165,26 +1102,21 @@ function revokeClient() { find /home/ -maxdepth 2 -name "$CLIENT.ovpn" -delete rm -f "/root/$CLIENT.ovpn" sed -i "/^$CLIENT,.*/d" /etc/openvpn/ipp.txt - echo "" echo "Certificate for client $CLIENT revoked." } - function removeUnbound() { # Remove OpenVPN-related config sed -i '/include: \/etc\/unbound\/openvpn.conf/d' /etc/unbound/unbound.conf rm /etc/unbound/openvpn.conf - until [[ $REMOVE_UNBOUND =~ (y|n) ]]; do echo "" echo "If you were already using Unbound before installing OpenVPN, I removed the configuration related to OpenVPN." read -rp "Do you want to completely remove Unbound? [y/n]: " -e REMOVE_UNBOUND done - if [[ $REMOVE_UNBOUND == 'y' ]]; then # Stop Unbound systemctl stop unbound - if [[ $OS =~ (debian|ubuntu) ]]; then apt-get autoremove --purge -y unbound elif [[ $OS == 'arch' ]]; then @@ -1194,9 +1126,7 @@ function removeUnbound() { elif [[ $OS == 'fedora' ]]; then dnf remove -y unbound fi - rm -rf /etc/unbound/ - echo "" echo "Unbound removed!" else @@ -1205,7 +1135,6 @@ function removeUnbound() { echo "Unbound wasn't removed." fi } - function removeOpenVPN() { echo "" read -rp "Do you really want to remove OpenVPN? [y/n]: " -e -i n REMOVE @@ -1213,7 +1142,6 @@ function removeOpenVPN() { # Get OpenVPN port from the configuration PORT=$(grep '^port ' /etc/openvpn/server.conf | cut -d " " -f 2) PROTOCOL=$(grep '^proto ' /etc/openvpn/server.conf | cut -d " " -f 2) - # Stop OpenVPN if [[ $OS =~ (fedora|arch|centos) ]]; then systemctl disable openvpn-server@server @@ -1229,7 +1157,6 @@ function removeOpenVPN() { # Remove customised service rm /etc/systemd/system/openvpn\@.service fi - # Remove the iptables rules related to the script systemctl stop iptables-openvpn # Cleanup @@ -1238,7 +1165,6 @@ function removeOpenVPN() { systemctl daemon-reload rm /etc/iptables/add-openvpn-rules.sh rm /etc/iptables/rm-openvpn-rules.sh - # SELinux if hash sestatus 2>/dev/null; then if sestatus | grep "Current mode" | grep -qs "enforcing"; then @@ -1247,7 +1173,6 @@ function removeOpenVPN() { fi fi fi - if [[ $OS =~ (debian|ubuntu) ]]; then apt-get autoremove --purge -y openvpn if [[ -e /etc/apt/sources.list.d/openvpn.list ]]; then @@ -1261,7 +1186,6 @@ function removeOpenVPN() { elif [[ $OS == 'fedora' ]]; then dnf remove -y openvpn fi - # Cleanup find /home/ -maxdepth 2 -name "*.ovpn" -delete find /root/ -maxdepth 1 -name "*.ovpn" -delete @@ -1269,7 +1193,6 @@ function removeOpenVPN() { rm -rf /usr/share/doc/openvpn* rm -f /etc/sysctl.d/99-openvpn.conf rm -rf /var/log/openvpn - # Unbound if [[ -e /etc/unbound/openvpn.conf ]]; then removeUnbound @@ -1281,7 +1204,6 @@ function removeOpenVPN() { echo "Removal aborted!" fi } - function manageMenu() { echo "Welcome to OpenVPN-install!" echo "The git repository is available at: https://github.com/angristan/openvpn-install" @@ -1296,7 +1218,6 @@ function manageMenu() { until [[ $MENU_OPTION =~ ^[1-4]$ ]]; do read -rp "Select an option [1-4]: " MENU_OPTION done - case $MENU_OPTION in 1) newClient @@ -1312,10 +1233,8 @@ function manageMenu() { ;; esac } - # Check for root, TUN, OS... initialCheck - # Check if OpenVPN is already installed if [[ -e /etc/openvpn/server.conf && $AUTO_INSTALL != "y" ]]; then manageMenu