Release openresolv-1.7.1
[openresolv] / libc.in
diff --git a/libc.in b/libc.in
index 9611402125f541137e0b01a2f665dd66b4095fa5..165cbdb64be9a37525f122bf09da50fd7a52ba4d 100755 (executable)
--- a/libc.in
+++ b/libc.in
@@ -1,9 +1,10 @@
 #!/bin/sh
-# Copyright 2006 Gentoo Foundation
-# Copyright 2007 Roy Marples
+# Copyright 2007-2008 Roy Marples
 # All rights reserved
 
-# libc subscriber for resolvconf 
+# libc subscriber for resolvconf
+# You could symlink /etc/resolv.conf to resolvconf/run/resolv.conf
+# for a read only etc, if resolvconf/run is linked to /var/run/resolvconf.
 
 # Redistribution and use in source and binary forms, with or without
 # modification, are permitted provided that the following conditions
 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
-PREFIX=
-RESOLVCONF="${PREFIX}"/etc/resolvconf
+RESOLVCONF=/etc/resolv.conf
+PREFIX=@PREFIX@
+SYSCONFDIR=@SYSCONFDIR@
 RESOLVCONFS="$(resolvconf -l)"
-BASE="${RESOLVCONF}/resolv.conf.d/base"
+BASE="${SYSCONFDIR}/resolv.conf.d/base"
 
-uniqify() {
+uniqify()
+{
     local result=
     while [ -n "$1" ]; do
                case " ${result} " in
-                       *" $1 "*);;
-                       *) result="${result} $1";;
+               *" $1 "*);;
+               *) result="${result} $1";;
                esac
                shift
        done
     echo "${result# *}"
 }
 
+# sed may not be available, and this is faster on small files
+key_get_value()
+{
+       local key="$1" value= x= line=
+
+       shift
+       if [ $# -eq 0 ]; then
+               while read line; do
+                       case "${line}" in
+                       "${key}"*) echo "${line##${key}}";;
+                       esac
+               done
+       else
+               for x; do
+                       while read line; do
+                               case "${line}" in
+                               "${key}"*) echo "${line##${key}}";;
+                               esac
+                       done < "${x}"
+               done
+       fi
+}
+
 OUR_NS=
 if [ -e "${BASE}" ]; then
-       OUR_NS="$(sed -n -e 's/^[[:space:]]*nameserver[[:space:]]*//p' "${BASE}")"
+       OUR_NS="$(key_get_value "nameserver " "${BASE}")"
 fi
 OUR_NS="$(uniqify \
        ${OUR_NS} \
-       $(echo "${RESOLVCONFS}" \
-       | sed -n -e 's/^[[:space:]]*nameserver[[:space:]]*//p') \
-)"
+       $(echo "${RESOLVCONFS}" | key_get_value "nameserver "))"
 
 # libc only allows for 3 nameservers
 # truncate after 127 as well
@@ -76,23 +100,25 @@ done
 OUR_SEARCH=
 if ${LOCALH}; then
        if [ -e "${BASE}" ]; then
-               OUR_SEARCH="$(sed -n -e 's/^[[:space:]]*search[[:space:]]*//p' "${BASE}")"
+               OUR_SEARCH="$(key_get_value "search " "${BASE}")"
        fi
-       OUR_SEARCH="${OUR_SEARCH} $(echo "${RESOLVCONFS}" \
-               | sed -n 's/^[[:space:]]*search[[:space:]]*//p')"
+       RESS="$(echo "${RESOLVCONFS}" | key_get_value "search ")"
+       OUR_SEARCH="${OUR_SEARCH} ${RESS}"
        if [ -e "${BASE}" ]; then
-               OUR_SEARCH="${OUR_SEARCH} $(sed -n -e 's/^[[:space:]]*domain[[:space:]]*//p' "${BASE}")"
+               RESD="$(key_get_value "domain " "${BASE}")"
+               OUR_SEARCH="${OUR_SEARCH} ${RESD}"
        fi
-       OUR_SEARCH="${OUR_SEARCH} $( echo "${RESOLVCONFS}" \
-               | sed -n -e 's/^[[:space:]]*domain[[:space:]]*//p')"
+       RESD="$(echo "${RESOLVCONFS}" | key_get_value "domain ")"
+       OUR_SEARCH="${OUR_SEARCH} ${RESD}"
 else
        if [ -e "${BASE}" ]; then
-               OUR_SEARCH="$(sed -n -e 's/^[[:space:]]*search[[:space:]]*//p' \
-                       -e 's/^[[:space:]]*domain[[:space:]]*//p' "${BASE}")"
+               RESS="$(key_get_value "search " "${BASE}")"
+               RESD="$(key_get_value "domain " "${BASE}")"
+               OUR_SEARCH="${RESS} ${RESD}"
        fi
-       OUR_SEARCH="${OUR_SEARCH} $(echo "${RESOLVCONFS}" \
-               | sed -n -e 's/^[[:space:]]*search[[:space:]]*//p' \
-                       -e 's/^[[:space:]]*domain[[:space:]]*//p')"
+       RESS="$(echo "${RESOLVCONFS}" | key_get_value "search ")"
+       RESD="$(echo "${RESOLVCONFS}" | key_get_value "domain ")"
+       OUR_SEARCH="${OUR_SEARCH} ${RESS} ${RESD}"
 fi
 
 # libc only allows for 6 search domains 
@@ -106,46 +132,47 @@ done
 [ -n "${SEARCH}" ] && SEARCH="search${SEARCH}"
 
 # Hold our new resolv.conf in a variable to save on temporary files
-NEWCONF="# Generated by resolvconf\n"
-[ -e "${RESOLVCONF}"/resolv.conf.d/head ] \
-       && NEWCONF="${NEWCONF}$(cat "${RESOLVCONF}"/resolv.conf.d/head)\n"
+NEWCONF=""
+[ -e "${SYSCONFDIR}"/resolv.conf.d/head ] \
+       && NEWCONF="${NEWCONF}$(cat "${SYSCONFDIR}"/resolv.conf.d/head)\n"
 [ -n "${SEARCH}" ] && NEWCONF="${NEWCONF}${SEARCH}\n"
 for N in ${NS}; do
        NEWCONF="${NEWCONF}nameserver ${N}\n"
 done
 
-# Now dump everything else from our resolvs
+# Now get any configured options
+OPTS=
 if [ -e "${BASE}" ]; then
-       NEWCONF="${NEWCONF}$(sed -e '/^[[:space:]]*$/d' \
-               -e '/^[[:space:]]*nameserver[[:space:]]*.*/d' \
-               -e '/^[[:space:]]*search[[:space:]]*.*/d' \
-               -e '/^[[:space:]]*domain[[:space:]]*.*/d' \
-               "${BASE}")" 
+       OPTS="$(key_get_value "options " "${BASE}")"
+fi
+OPTS="${OPTS}${OPTS:+ }$(echo ${RESOLVCONFS} | key_get_value "options ")"
+if [ -n "${OPTS}" ]; then
+       NEWCONF="${NEWCONF}options"
+       for OPT in $(uniqify ${OPTS}); do
+               NEWCONF="${NEWCONF} ${OPT}"
+       done
+       NEWCONF="${NEWCONF}\n"
 fi
 
-# We don't know we're using GNU sed, so we do it like this
-NEWCONF="${NEWCONF}$(echo "${RESOLVCONFS}" | sed -e '/^[[:space:]]*$/d' \
-       -e '/^[[:space:]]*#/d' \
-       -e '/^[[:space:]]*nameserver[[:space:]]*.*/d' \
-       -e '/^[[:space:]]*search[[:space:]]*.*/d' \
-       -e '/^[[:space:]]*domain[[:space:]]*.*/d' \
-       )"
-[ -e "${RESOLVCONF}"/resolv.conf.d/tail ] \
-       && NEWCONF="${NEWCONF}$(cat "${RESOLVCONF}"/resolv.conf.d/tail)"
+[ -e "${SYSCONFDIR}"/resolv.conf.d/tail ] \
+       && NEWCONF="${NEWCONF}$(cat "${SYSCONFDIR}"/resolv.conf.d/tail)\n"
 
 # Check if the file has actually changed or not
-if [ -e "${RESOLVCONF}"/run/resolv.conf ]; then
-       [ "$(cat "${RESOLVCONF}"/run/resolv.conf)" = "$(printf "${NEWCONF}")" ] && exit 0
+if [ -e "${RESOLVCONF}" ]; then
+       [ "$(cat "${RESOLVCONF}")" = "$(printf "${NEWCONF}")" ] && exit 0
 fi
 
 # Create our resolv.conf now
-(umask 022; printf "${NEWCONF}" > "${RESOLVCONF}"/run/resolv.conf)
+(umask 022; printf "${NEWCONF}" > "${RESOLVCONF}")
 
 resolvconf -s nscd restart
+retval=$?
 
 # Notify users of the resolver
-for x in "${REVOLVCONF}"/update-libc.d/*; do
-       [ -e "${x}" ] && "${x}" "$@"
+for x in "${SYSCONFDIR}"/update-libc.d/*; do
+       if [ -e "${x}" ]; then
+               "${x}" "$@"
+               retval=$((${retval} + $?))
+       fi
 done
-
-# vim: ts=4 :
+exit ${retval}