aboutsummaryrefslogtreecommitdiff
path: root/contrib/pull-resolv-conf
diff options
context:
space:
mode:
authorDavide Brini <dave_br@gmx.com>2010-04-19 22:41:42 +0200
committerDavid Sommerseth <dazo@users.sourceforge.net>2010-10-21 11:37:03 +0200
commit5c9f1d2e703d0c8aaaf7254e9f3bd1bf0dddb120 (patch)
tree5a718070dc6cc2fa79491abc737044550044035d /contrib/pull-resolv-conf
parentThe man page does not mention that the default value of "mssfix" is 1450. (diff)
downloadopenvpn-5c9f1d2e703d0c8aaaf7254e9f3bd1bf0dddb120.tar.xz
Enhance contrib/pull-resolv-conf/client.{up,down} scripts
Patch arrived from Davide Brini: - No more bashisms (AFAICT). Should work with any POSIX-compatible shell (which means "almost all reasonably recent shells"), though I've only tested with bash and dash. - Unnecessary calls to external tools (sed) removed - Manages multiple DNS and DOMAIN options. Each DNS option becomes a "nameserver" line in the new resolv.conf (up to a maximum of 3). If there's a single DOMAIN option, it becomes a "domain" line in resolv.conf; otherwise, all the domains are listed in a "search" line in resolv.conf (eg "search foo.com example.net"). - Client.up renames the existing resolv.conf and creates a brand new one; client.down restores it from the saved copy when the VPN terminates (the usual rules about running as root apply). This is how Gentoo does that; the old scripts instead added/removed some lines at the beginning of the file, which looks a less clean approach to me. The rename approach also dramatically simplifies and shortens client.down, as you'll see. - Uses resolvconf if it's available (detected by the presence of /sbin/resolvconf) rather than writing to resolv.conf directly. Not sure whether this is a Linux-only thing or other systems use it though. Script has been smoke tested on Fedora 12 with OpenVPN 2.1.1 without the resolvconf package , and in addition Debian Lenny with OpenVPN 2.1_rc11 according to the patch. Signed-off-by: Davide Brini <dave_br@gmx.com> Signed-off-by: David Sommerseth <dazo@users.sourceforge.net> Acked-by: David Sommerseth <dazo@users.sourceforge.net>
Diffstat (limited to 'contrib/pull-resolv-conf')
-rw-r--r--contrib/pull-resolv-conf/client.down46
-rw-r--r--contrib/pull-resolv-conf/client.up87
2 files changed, 64 insertions, 69 deletions
diff --git a/contrib/pull-resolv-conf/client.down b/contrib/pull-resolv-conf/client.down
index 82dff54..2dffeaf 100644
--- a/contrib/pull-resolv-conf/client.down
+++ b/contrib/pull-resolv-conf/client.down
@@ -14,7 +14,6 @@
# Place this in /etc/openvpn/client.down
# Then, add the following to your /etc/openvpn/<clientconfig>.conf:
# client
-# pull dhcp-options
# up /etc/openvpn/client.up
# down /etc/openvpn/client.down
# Next, "chmod a+x /etc/openvpn/client.down"
@@ -23,8 +22,8 @@
# Note that this script is best served with the companion "client.up"
# script.
-# Only tested on Gentoo Linux 2005.0 with OpenVPN 2.0
-# It should work with any GNU/Linux with /etc/resolv.conf
+# Tested under Debian lenny with OpenVPN 2.1_rc11
+# It should work with any UNIX with a POSIX sh, /etc/resolv.conf or resolvconf
# This runs with the context of the OpenVPN UID/GID
# at the time of execution. This generally means that
@@ -36,41 +35,12 @@
# is to run OpenVPN as root. THIS IS NOT RECOMMENDED. You have
# been WARNED.
-# init variables
-
-i=1
-j=1
-unset fopt
-unset dns
-unset opt
-
-# Convert ENVs to an array
-
-while fopt=foreign_option_$i; [ -n "${!fopt}" ]; do
-{
- opt[i-1]=${!fopt}
- case ${opt[i-1]} in
- *DOMAIN* ) domain=`echo ${opt[i-1]} | \
- sed -e 's/dhcp-option DOMAIN //g'` ;;
- *DNS* ) dns[j-1]=`echo ${opt[i-1]} | \
- sed -e 's/dhcp-option DNS //g'`
- let j++ ;;
- esac
- let i++
-}
-done
-
-# Now, do the work
-
-if [ -n "${dns[*]}" ]; then
- for i in "${dns[@]}"; do
- sed -i -e "/nameserver ${i}/D" /etc/resolv.conf || die
- done
-fi
-
-if [ -n "${domain}" ]; then
- sed -i -e "/search ${domain}/D" /etc/resolv.conf || die
+if [ -x /sbin/resolvconf ] ; then
+ /sbin/resolvconf -d "${1}"
+elif [ -e /etc/resolv.conf.ovpnsave ] ; then
+ # cp + rm rather than mv in case it's a symlink
+ cp /etc/resolv.conf.ovpnsave /etc/resolv.conf
+ rm -f /etc/resolv.conf.ovpnsave
fi
-# all done...
exit 0
diff --git a/contrib/pull-resolv-conf/client.up b/contrib/pull-resolv-conf/client.up
index 0eed609..e81bd3a 100644
--- a/contrib/pull-resolv-conf/client.up
+++ b/contrib/pull-resolv-conf/client.up
@@ -1,4 +1,4 @@
-#!/bin/bash
+#!/bin/sh
# Copyright (c) 2005-2010 OpenVPN Technologies, Inc.
# Licensed under the GPL version 2
@@ -14,7 +14,6 @@
# Place this in /etc/openvpn/client.up
# Then, add the following to your /etc/openvpn/<clientconfig>.conf:
# client
-# pull dhcp-options
# up /etc/openvpn/client.up
# Next, "chmod a+x /etc/openvpn/client.up"
@@ -22,8 +21,8 @@
# Note that this script is best served with the companion "client.down"
# script.
-# Only tested on Gentoo Linux 2005.0 with OpenVPN 2.0
-# It should work with any GNU/Linux with /etc/resolv.conf
+# Tested under Debian lenny with OpenVPN 2.1_rc11
+# It should work with any UNIX with a POSIX sh, /etc/resolv.conf or resolvconf
# This runs with the context of the OpenVPN UID/GID
# at the time of execution. This generally means that
@@ -38,38 +37,64 @@
# init variables
i=1
-j=1
-unset fopt
-unset dns
-unset opt
-
-# Convert ENVs to an array
-
-while fopt=foreign_option_$i; [ -n "${!fopt}" ]; do
-{
- opt[i-1]=${!fopt}
- case ${opt[i-1]} in
- *DOMAIN* ) domain=`echo ${opt[i-1]} | \
- sed -e 's/dhcp-option DOMAIN //g'` ;;
- *DNS* ) dns[j-1]=`echo ${opt[i-1]} | \
- sed -e 's/dhcp-option DNS //g'`
- let j++ ;;
+domains=
+fopt=
+ndoms=0
+nns=0
+nl='
+'
+
+# $foreign_option_<n> is something like
+# "dhcp-option DOMAIN example.com" (multiple allowed)
+# or
+# "dhcp-option DNS 10.10.10.10" (multiple allowed)
+
+# each DNS option becomes a "nameserver" option in resolv.con
+# if we get one DOMAIN, that becomes "domain" in resolv.conf
+# if we get multiple DOMAINS, those become "search" lines in resolv.conf
+
+while true; do
+ eval fopt=\$foreign_option_${i}
+ [ -z "${fopt}" ] && break
+
+ case ${fopt} in
+ dhcp-option\ DOMAIN\ *)
+ ndoms=$((ndoms + 1))
+ domains="${domains} ${fopt#dhcp-option DOMAIN }"
+ ;;
+ dhcp-option\ DNS\ *)
+ nns=$((nns + 1))
+ if [ $nns -le 3 ]; then
+ dns="${dns}${dns:+$nl}nameserver ${fopt#dhcp-option DNS }"
+ else
+ printf "%s\n" "Too many nameservers - ignoring after third" >&2
+ fi
+ ;;
+ *)
+ printf "%s\n" "Unknown option \"${fopt}\" - ignored" >&2
+ ;;
esac
- let i++
-}
+ i=$((i + 1))
done
-# Now, do the work
-
-if [ -n "${dns[*]}" ]; then
- for i in "${dns[@]}"; do
- sed -i -e "1,1 i nameserver ${i}" /etc/resolv.conf || die
- done
+ds=domain
+if [ $ndoms -gt 1 ]; then
+ ds=search
fi
-if [ -n "${domain}" ]; then
- sed -i -e "$j,1 i search ${domain}" /etc/resolv.conf || die
+# This is the complete file - "$domains" has a leading space already
+out="# resolv.conf autogenerated by ${0} (${1})${nl}${dns}${nl}${ds}${domains}"
+
+# use resolvconf if it's available
+if [ -x /sbin/resolvconf ] ; then
+ printf "%s\n" "${out}" | /sbin/resolvconf -a "${1}"
+else
+ # Preserve the existing resolv.conf
+ if [ -e /etc/resolv.conf ] ; then
+ cp /etc/resolv.conf /etc/resolv.conf.ovpnsave
+ fi
+ printf "%s\n" "${out}" > /etc/resolv.conf
+ chmod 644 /etc/resolv.conf
fi
-# all done...
exit 0