From 8375af5452f4e0466cfb8439abd70479b4b29b1a Mon Sep 17 00:00:00 2001 From: Stanislas Date: Mon, 15 Dec 2025 10:53:15 +0100 Subject: [PATCH] feat: add configurable MTU support (#1417) ## Summary - Add `--mtu ` CLI option to configure tunnel MTU (valid range: 576-65535) - Add interactive prompt with user-friendly explanation for non-technical users - Write `tun-mtu` to server.conf and client template when custom value is set - OpenVPN auto-calculates MSSFIX based on the MTU value (no separate option needed) ## Use cases - PPPoE connections (typically need MTU ~1492) - Mobile/cellular networks with variable MTU - Networks with connectivity issues due to fragmentation ## Usage ```bash # CLI mode ./openvpn-install.sh install --mtu 1400 # Interactive mode prompts with explanation: # "MTU controls the maximum packet size. Lower values can help # with connectivity issues on some networks (e.g., PPPoE, mobile)." ``` Close https://github.com/angristan/openvpn-install/pull/1300 Co-authored-by: Fabian Druschke --- README.md | 2 ++ openvpn-install.sh | 38 ++++++++++++++++++++++++++++++++++++++ test/server-entrypoint.sh | 27 +++++++++++++++++++++++++++ 3 files changed, 67 insertions(+) diff --git a/README.md b/README.md index 69b2427..57e250e 100644 --- a/README.md +++ b/README.md @@ -44,6 +44,7 @@ That said, OpenVPN still makes sense when you need: - Uses [official OpenVPN repositories](https://community.openvpn.net/openvpn/wiki/OpenvpnSoftwareRepos) when possible for the latest stable releases - Firewall rules and forwarding managed seamlessly (native firewalld and nftables support, iptables fallback) - Configurable VPN subnet (default: `10.8.0.0/24`) +- Configurable tunnel MTU (default: `1500`) - If needed, the script can cleanly remove OpenVPN, including configuration and firewall rules - Customisable encryption settings, enhanced default settings (see [Security and Encryption](#security-and-encryption) below) - Uses latest OpenVPN features when available (see [Security and Encryption](#security-and-encryption) below) @@ -272,6 +273,7 @@ The `install` command supports many options for customization: - `--port ` - OpenVPN port (default: `1194`) - `--port-random` - Use random port (49152-65535) - `--protocol ` - Protocol (default: `udp`) +- `--mtu ` - Tunnel MTU (default: `1500`) **DNS Options:** diff --git a/openvpn-install.sh b/openvpn-install.sh index 4ad0eb2..9e94dd8 100755 --- a/openvpn-install.sh +++ b/openvpn-install.sh @@ -210,6 +210,7 @@ show_install_help() { --port OpenVPN port (default: 1194) --port-random Use random port (49152-65535) --protocol Protocol: udp or tcp (default: udp) + --mtu Tunnel MTU (default: 1500) DNS Options: --dns DNS provider (default: cloudflare) @@ -502,6 +503,13 @@ validate_positive_int() { fi } +validate_mtu() { + local mtu="$1" + if ! [[ "$mtu" =~ ^[0-9]+$ ]] || [[ "$mtu" -lt 576 ]] || [[ "$mtu" -gt 65535 ]]; then + log_fatal "Invalid MTU: $mtu. Must be between 576 and 65535." + fi +} + # Handle install command cmd_install() { local interactive=false @@ -563,6 +571,12 @@ cmd_install() { esac shift 2 ;; + --mtu) + [[ -z "${2:-}" ]] && log_fatal "--mtu requires an argument" + validate_mtu "$2" + MTU="$2" + shift 2 + ;; --dns) [[ -z "${2:-}" ]] && log_fatal "--dns requires an argument" parse_dns_provider "$2" @@ -1789,6 +1803,20 @@ function installQuestions() { read -rp "Allow multiple devices per client? [y/n]: " -e -i n MULTI_CLIENT done log_menu "" + log_prompt "Do you want to customize the tunnel MTU?" + log_menu " MTU controls the maximum packet size. Lower values can help" + log_menu " with connectivity issues on some networks (e.g., PPPoE, mobile)." + log_menu " 1) Default (1500) - works for most networks" + log_menu " 2) Custom" + until [[ $MTU_CHOICE =~ ^[1-2]$ ]]; do + read -rp "MTU choice [1-2]: " -e -i 1 MTU_CHOICE + done + if [[ $MTU_CHOICE == "2" ]]; then + until [[ $MTU =~ ^[0-9]+$ ]] && [[ $MTU -ge 576 ]] && [[ $MTU -le 65535 ]]; do + read -rp "MTU [576-65535]: " -e -i 1500 MTU + done + fi + log_menu "" log_prompt "Do you want to customize encryption settings?" log_prompt "Unless you know what you're doing, you should stick with the default parameters provided by the script." log_prompt "Note that whatever you choose, all the choices presented in the script are safe (unlike OpenVPN's defaults)." @@ -2046,6 +2074,7 @@ function installOpenVPN() { PORT_CHOICE=${PORT_CHOICE:-1} PROTOCOL_CHOICE=${PROTOCOL_CHOICE:-1} DNS=${DNS:-3} + MTU_CHOICE=${MTU_CHOICE:-1} MULTI_CLIENT=${MULTI_CLIENT:-n} CUSTOMIZE_ENC=${CUSTOMIZE_ENC:-n} CLIENT=${CLIENT:-client} @@ -2068,6 +2097,7 @@ function installOpenVPN() { log_info " PORT_CHOICE=$PORT_CHOICE" log_info " PROTOCOL_CHOICE=$PROTOCOL_CHOICE" log_info " DNS=$DNS" + [[ -n $MTU ]] && log_info " MTU=$MTU" log_info " MULTI_CLIENT=$MULTI_CLIENT" log_info " CUSTOMIZE_ENC=$CUSTOMIZE_ENC" log_info " CLIENT=$CLIENT" @@ -2371,6 +2401,10 @@ push "route-ipv6 2000::/3" push "redirect-gateway ipv6"' >>/etc/openvpn/server/server.conf fi + if [[ -n $MTU ]]; then + echo "tun-mtu $MTU" >>/etc/openvpn/server/server.conf + fi + if [[ $DH_TYPE == "1" ]]; then echo "dh none" >>/etc/openvpn/server/server.conf echo "ecdh-curve $DH_CURVE" >>/etc/openvpn/server/server.conf @@ -2636,6 +2670,10 @@ ignore-unknown-option block-outside-dns setenv opt block-outside-dns # Prevent Windows 10 DNS leak verb 3" >>/etc/openvpn/server/client-template.txt + if [[ -n $MTU ]]; then + echo "tun-mtu $MTU" >>/etc/openvpn/server/client-template.txt + fi + # Generate the custom client.ovpn if [[ $NEW_CLIENT == "n" ]]; then log_info "No clients added. To add clients, simply run the script again." diff --git a/test/server-entrypoint.sh b/test/server-entrypoint.sh index 7159518..a4e0b5e 100755 --- a/test/server-entrypoint.sh +++ b/test/server-entrypoint.sh @@ -31,6 +31,7 @@ INSTALL_CMD=(/opt/openvpn-install.sh install) INSTALL_CMD+=(--endpoint openvpn-server) INSTALL_CMD+=(--dns unbound) INSTALL_CMD+=(--subnet "$VPN_SUBNET") +INSTALL_CMD+=(--mtu 1400) INSTALL_CMD+=(--client testclient) # Add TLS signature mode if non-default @@ -189,6 +190,32 @@ fi echo "=== systemd service configuration verified ===" echo "" + +# ===================================================== +# Verify MTU configuration +# ===================================================== +echo "=== Verifying MTU configuration ===" + +# Verify MTU in server config +if grep -q "tun-mtu 1400" /etc/openvpn/server/server.conf; then + echo "PASS: Server config has tun-mtu 1400" +else + echo "FAIL: Server config missing tun-mtu 1400" + grep "tun-mtu" /etc/openvpn/server/server.conf || echo "No tun-mtu directive found" + exit 1 +fi + +# Verify MTU in client template +if grep -q "tun-mtu 1400" /etc/openvpn/server/client-template.txt; then + echo "PASS: Client template has tun-mtu 1400" +else + echo "FAIL: Client template missing tun-mtu 1400" + grep "tun-mtu" /etc/openvpn/server/client-template.txt || echo "No tun-mtu directive found" + exit 1 +fi + +echo "=== MTU configuration verified ===" +echo "" echo "Server config:" cat /etc/openvpn/server/server.conf