diff options
author | Scott Ullrich <sullrich@pfsense.org> | 2005-08-29 21:20:15 +0000 |
---|---|---|
committer | Scott Ullrich <sullrich@pfsense.org> | 2005-08-29 21:20:15 +0000 |
commit | b43ba51b63bb6b29c32fc61316dbdece2372b365 (patch) | |
tree | 60f94ae59b5e2515903168af890c62a5d3550712 /sbin/dhclient-script | |
parent | e1b58215a5e31afbab24e84b0dc64e7ba91478f7 (diff) | |
download | pfsense-b43ba51b63bb6b29c32fc61316dbdece2372b365.zip pfsense-b43ba51b63bb6b29c32fc61316dbdece2372b365.tar.gz |
Bring back in OpenBSD's dhclient-script for doctoring
Diffstat (limited to 'sbin/dhclient-script')
-rwxr-xr-x | sbin/dhclient-script | 474 |
1 files changed, 267 insertions, 207 deletions
diff --git a/sbin/dhclient-script b/sbin/dhclient-script index 1eb7e96..6e83744 100755 --- a/sbin/dhclient-script +++ b/sbin/dhclient-script @@ -1,234 +1,294 @@ #!/bin/sh # -# $Id$ +# $OpenBSD: dhclient-script,v 1.6 2004/05/06 18:22:41 claudio Exp $ +# $FreeBSD: src/sbin/dhclient/dhclient-script,v 1.4 2005/06/10 03:41:18 brooks Exp $ +# +# Copyright (c) 2003 Kenneth R Westerback <krw@openbsd.org> +# +# Permission to use, copy, modify, and distribute this software for any +# purpose with or without fee is hereby granted, provided that the above +# copyright notice and this permission notice appear in all copies. +# +# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +# # -# $FreeBSD: src/contrib/isc-dhcp/client/scripts/freebsd,v 1.9.2.6 2003/03/02 16:42:38 murray Exp $ + +NETSTAT=/usr/bin/netstat +GREP=/usr/bin/grep +AWK=/usr/bin/awk +HOSTNAME=/bin/hostname + +LOCALHOST=127.0.0.1 if [ -x /usr/bin/logger ]; then - LOGGER="/usr/bin/logger -s -p user.notice -t dhclient" + LOGGER="/usr/bin/logger -s -p user.notice -t dhclient" else - LOGGER=echo + LOGGER=echo fi -make_resolv_conf() { - if [ x"$new_domain_name_servers" != x ]; then - if [ "x$new_domain_name" != x ]; then - echo $new_domain_name >/var/etc/defaultdomain.conf - else - rm -f /var/etc/defaultdomain.conf - fi - rm -f /var/etc/nameservers.conf - for nameserver in $new_domain_name_servers; do - echo $nameserver >>/var/etc/nameservers.conf - done - fi +# +# Helper functions that implement common actions. +# + +check_hostname() { + current_hostname=`$HOSTNAME` + if [ -z "$current_hostname" ]; then + $LOGGER "New Hostname ($interface): $new_host_name" + $HOSTNAME $new_host_name + elif [ "$current_hostname" = "$old_host_name" -a \ + "$new_host_name" != "$old_host_name" ]; then + $LOGGER "New Hostname ($interface): $new_host_name" + $HOSTNAME $new_host_name + fi +} + +arp_flush() { + arp -an -i $interface | \ + sed -n -e 's/^.*(\(.*\)) at .*$/arp -d \1/p' | \ + sh >/dev/null 2>&1 +} + +delete_old_address() { + ifconfig $interface inet -alias $old_ip_address $medium +} + +add_new_address() { + ifconfig $interface \ + inet $new_ip_address \ + netmask $new_subnet_mask \ + broadcast $new_broadcast_address \ + $medium + + $LOGGER "New IP Address ($interface): $new_ip_address" + $LOGGER "New Subnet Mask ($interface): $new_subnet_mask" + $LOGGER "New Broadcast Address ($interface): $new_broadcast_address" + $LOGGER "New Routers ($interface): $new_routers" + + echo $new_routers > /tmp/${interface}_router + +} + +delete_old_alias() { + if [ -n "$alias_ip_address" ]; then + ifconfig $interface inet -alias $alias_ip_address > /dev/null 2>&1 + route delete $alias_ip_address $LOCALHOST > /dev/null 2>&1 + fi +} + +add_new_alias() { + if [ -n "$alias_ip_address" ]; then + ifconfig $interface inet alias $alias_ip_address netmask \ + $alias_subnet_mask + route add $alias_ip_address $LOCALHOST + fi +} + +delete_old_routes() { + route delete "$old_ip_address" $LOCALHOST >/dev/null 2>&1 + for router in $old_routers; do + if [ $if_defaultroute = x -o $if_defaultroute = $interface ]; then + route delete default $route >/dev/null 2>&1 + rm -f /tmp/${interface}_router + fi + done + + if [ -n "$old_static_routes" ]; then + set $old_static_routes + while [ $# -gt 1 ]; do + route delete "$1" "$2" + shift; shift + rm -f /tmp/${interface}_router + done + fi + + arp_flush +} + +add_new_routes() { + route add $new_ip_address $LOCALHOST >/dev/null 2>&1 + for router in $new_routers; do + if [ "$new_ip_address" = "$router" ]; then + route add default -iface $router >/dev/null 2>&1 + else + route add default $router >/dev/null 2>&1 + echo $new_routers > /tmp/${interface}_router + fi + # 2nd and subsequent default routers error out, so explicitly + # stop processing the list after the first one. + break + done + + if [ -n "$new_static_routes" ]; then + $LOGGER "New Static Routes ($interface): $new_static_routes" + set $new_static_routes + while [ $# -gt 1 ]; do + route add $1 $2 + shift; shift + echo $new_routers > /tmp/${interface}_router + done + fi +} + +add_new_resolv_conf() { + # XXX Old code did not create/update resolv.conf unless both + # $new_domain_name and $new_domain_name_servers were provided. PR + # #3135 reported some ISP's only provide $new_domain_name_servers and + # thus broke the script. This code creates the resolv.conf if either + # are provided. + + rm -f /var/etc/resolv.conf.std + + if [ -n "$new_domain_name" ]; then + echo "search $new_domain_name" >>/var/etc/resolv.conf.std + fi + + rm -f /var/etc/nameservers.conf + + if [ -n "$new_domain_name_servers" ]; then + for nameserver in $new_domain_name_servers; do + echo "nameserver $nameserver" >>/var/etc/resolv.conf.std + echo $nameserver >>/var/etc/nameservers.conf + echo $new_domain_name >/var/etc/defaultdomain.conf + done + fi + + if [ -f /var/etc/resolv.conf.std ]; then + if [ -f /var/etc/resolv.conf.tail ]; then + cat /var/etc/resolv.conf.tail >>/var/etc/resolv.conf.std + fi + + # In case (e.g. during OpenBSD installs) /var/etc/resolv.conf + # is a symbolic link, take care to preserve the link and write + # the new data in the correct location. + + if [ -f /var/etc/resolv.conf ]; then + cat /var/etc/resolv.conf > /var/etc/resolv.conf.save + fi + cat /var/etc/resolv.conf.std > /var/etc/nameservers.conf + cat /var/etc/resolv.conf.std > /var/etc/resolv.conf + rm -f /var/etc/resolv.conf.std + + # Try to ensure correct ownership and permissions. + chown -RL root:wheel /var/etc/resolv.conf + chmod -RL 644 /var/etc/resolv.conf + + return 0 + fi + + return 1 } # Must be used on exit. Invokes the local dhcp client exit hooks, if any. exit_with_hooks() { - exit_status=$1 - if [ -f /etc/dhclient-exit-hooks ]; then - . /etc/dhclient-exit-hooks - fi -# probably should do something with exit status of the local script - exit $exit_status + exit_status=$1 + if [ -f /etc/dhclient-exit-hooks ]; then + . /etc/dhclient-exit-hooks + fi + # probably should do something with exit status of the local script + exit $exit_status } +# +# Start of active code. +# + # Invoke the local dhcp client enter hooks, if they exist. if [ -f /etc/dhclient-enter-hooks ]; then - exit_status=0 - . /etc/dhclient-enter-hooks - # allow the local script to abort processing of this state - # local script must set exit_status variable to nonzero. - if [ $exit_status -ne 0 ]; then - exit $exit_status - fi + exit_status=0 + . /etc/dhclient-enter-hooks + # allow the local script to abort processing of this state + # local script must set exit_status variable to nonzero. + if [ $exit_status -ne 0 ]; then + exit $exit_status + fi fi -if [ x$new_network_number != x ]; then - $LOGGER New Network Number: $new_network_number +if [ -x $NETSTAT ]; then + if_defaulroute=`$NETSTAT -rn | $GREP "^default" | $AWK '{print $6}'` +else + if_defaultroute="x" fi -if [ x$new_broadcast_address != x ]; then - $LOGGER New Broadcast Address: $new_broadcast_address - new_broadcast_arg="broadcast $new_broadcast_address" -fi -if [ x$old_broadcast_address != x ]; then - old_broadcast_arg="broadcast $old_broadcast_address" -fi -if [ x$new_subnet_mask != x ]; then - new_netmask_arg="netmask $new_subnet_mask" -fi -if [ x$old_subnet_mask != x ]; then - old_netmask_arg="netmask $old_subnet_mask" -fi -if [ x$alias_subnet_mask != x ]; then - alias_subnet_arg="netmask $alias_subnet_mask" -fi +case $reason in +MEDIUM) + ifconfig $interface $medium + ifconfig $interface inet -alias 0.0.0.0 $medium >/dev/null 2>&1 + sleep 1 + ;; -if [ x$reason = xMEDIUM ]; then - eval "ifconfig $interface $medium" - eval "ifconfig $interface inet -alias 0.0.0.0 $medium" >/dev/null 2>&1 - sleep 1 - exit 0 -fi +PREINIT) + delete_old_alias + ifconfig $interface inet 0.0.0.0 netmask 0.0.0.0 broadcast 255.255.255.255 up + rm -f /tmp/${interface}_router + ;; -if [ x$reason = xPREINIT ]; then - if [ x$alias_ip_address != x ]; then - ifconfig $interface inet -alias $alias_ip_address > /dev/null 2>&1 - route delete $alias_ip_address 127.0.0.1 > /dev/null 2>&1 - fi - ifconfig $interface inet 0.0.0.0 netmask 0.0.0.0 \ - broadcast 255.255.255.255 up - exit 0 -fi - -if [ x$reason = xARPCHECK ] || [ x$reason = xARPSEND ]; then - exit 0; -fi +ARPCHECK|ARPSEND) + ;; -if [ x$reason = xBOUND ] || [ x$reason = xRENEW ] || \ - [ x$reason = xREBIND ] || [ x$reason = xREBOOT ]; then - current_hostname=`/bin/hostname` - if [ x$current_hostname = x ] || \ - [ x$current_hostname = x$old_host_name ]; then - if [ x$current_hostname = x ] || \ - [ x$new_host_name != x$old_host_name ]; then - $LOGGER "New Hostname: $new_host_name" - hostname $new_host_name - fi - fi - if [ x$old_ip_address != x ] && [ x$alias_ip_address != x ] && \ - [ x$alias_ip_address != x$old_ip_address ]; then - ifconfig $interface inet -alias $alias_ip_address > /dev/null 2>&1 - route delete $alias_ip_address 127.0.0.1 > /dev/null 2>&1 - fi - if [ x$old_ip_address != x ] && [ x$old_ip_address != x$new_ip_address ] - then - eval "ifconfig $interface inet -alias $old_ip_address $medium" - route delete $old_ip_address 127.1 >/dev/null 2>&1 - for router in $old_routers; do - route delete default $router >/dev/null 2>&1 - done - if [ -n "$old_static_routes" ]; then - set -- $old_static_routes - while [ $# -gt 1 ]; do - route delete $1 $2 - shift; shift - done - fi - arp -n -a | sed -n -e 's/^.*(\(.*\)) at .*$/arp -d \1/p' |sh - fi - if [ x$old_ip_address = x ] || [ x$old_ip_address != x$new_ip_address ] || \ - [ x$reason = xBOUND ] || [ x$reason = xREBOOT ]; then - eval "ifconfig $interface inet $new_ip_address $new_netmask_arg \ - $new_broadcast_arg $medium" - $LOGGER "New IP Address ($interface): $new_ip_address" - $LOGGER "New Subnet Mask ($interface): $new_subnet_mask" - $LOGGER "New Broadcast Address ($interface): $new_broadcast_address" - if [ -n "$new_routers" ]; then - $LOGGER "New Routers: $new_routers" - echo $new_routers > /tmp/${interface}_router - fi - route add $new_ip_address 127.1 >/dev/null 2>&1 - for router in $new_routers; do - route add default $router >/dev/null 2>&1 - done - if [ -n "$new_static_routes" ]; then - $LOGGER "New Static Routes: $new_static_routes" - set -- $new_static_routes - while [ $# -gt 1 ]; do - route add $1 $2 - shift; shift - done - fi - fi - if [ x$new_ip_address != x$alias_ip_address ] && [ x$alias_ip_address != x ]; - then - ifconfig $interface inet alias $alias_ip_address $alias_subnet_arg - route add $alias_ip_address 127.0.0.1 - fi - make_resolv_conf - exit_with_hooks 0 -fi +BOUND|RENEW|REBIND|REBOOT) + check_hostname + if [ -n "$old_ip_address" ]; then + if [ "$old_ip_address" != "$alias_ip_address" ]; then + delete_old_alias + fi + if [ "$old_ip_address" != "$new_ip_address" ]; then + delete_old_address + delete_old_routes + fi + fi + if [ "$reason" = BOUND ] || \ + [ "$reason" = REBOOT ] || \ + [ -z "$old_ip_address" ] || \ + [ "$old_ip_address" != "$new_ip_address" ]; then + add_new_address + add_new_routes + fi + if [ "$new_ip_address" != "$alias_ip_address" ]; then + add_new_alias + fi + add_new_resolv_conf + ;; -if [ x$reason = xEXPIRE ] || [ x$reason = xFAIL ] || [ x$reason = xRELEASE ] \ - || [ x$reason = xSTOP ]; then - if [ x$alias_ip_address != x ]; then - ifconfig $interface inet -alias $alias_ip_address > /dev/null 2>&1 - route delete $alias_ip_address 127.0.0.1 > /dev/null 2>&1 - fi - if [ x$old_ip_address != x ]; then - eval "ifconfig $interface inet -alias $old_ip_address $medium" - route delete $old_ip_address 127.1 >/dev/null 2>&1 - for router in $old_routers; do - route delete default $router >/dev/null 2>&1 - done - if [ -n "$old_static_routes" ]; then - set -- $old_static_routes - while [ $# -gt 1 ]; do - route delete $1 $2 - shift; shift - done - fi - arp -n -a | sed -n -e 's/^.*(\(.*\)) at .*$/arp -d \1/p' \ - |sh >/dev/null 2>&1 - fi - if [ x$alias_ip_address != x ]; then - ifconfig $interface inet alias $alias_ip_address $alias_subnet_arg - route add $alias_ip_address 127.0.0.1 - fi - exit_with_hooks 0 -fi +EXPIRE|FAIL) + delete_old_alias + if [ -n "$old_ip_address" ]; then + delete_old_address + delete_old_routes + fi + # XXX Why add alias we just deleted above? + add_new_alias + if [ -f /var/etc/resolv.conf.save ]; then + cat /var/etc/resolv.conf.save > /var/etc/resolv.conf + fi + ;; -if [ x$reason = xTIMEOUT ]; then - if [ x$alias_ip_address != x ]; then - ifconfig $interface inet -alias $alias_ip_address > /dev/null 2>&1 - route delete $alias_ip_address 127.0.0.1 > /dev/null 2>&1 - fi - eval "ifconfig $interface inet $new_ip_address $new_netmask_arg \ - $new_broadcast_arg $medium" - $LOGGER "New IP Address ($interface): $new_ip_address" - $LOGGER "New Subnet Mask ($interface): $new_subnet_mask" - $LOGGER "New Broadcast Address ($interface): $new_broadcast_address" - sleep 1 - if [ -n "$new_routers" ]; then - $LOGGER "New Routers: $new_routers" - echo $new_routers > /tmp/${interface}_router - set -- $new_routers - if ping -q -c 1 $1; then - if [ x$new_ip_address != x$alias_ip_address ] && \ - [ x$alias_ip_address != x ]; then - ifconfig $interface inet alias $alias_ip_address $alias_subnet_arg - route add $alias_ip_address 127.0.0.1 - fi - route add $new_ip_address 127.1 >/dev/null 2>&1 - for router in $new_routers; do - route add default $router >/dev/null 2>&1 - done - set -- $new_static_routes - while [ $# -gt 1 ]; do - route add $1 $2 - shift; shift - done - make_resolv_conf - exit_with_hooks 0 - fi - fi - eval "ifconfig $interface inet -alias $new_ip_address $medium" - for router in $old_routers; do - route delete default $router >/dev/null 2>&1 - done - if [ -n "$old_static_routes" ]; then - set -- $old_static_routes - while [ $# -gt 1 ]; do - route delete $1 $2 - shift; shift - done - fi - arp -n -a | sed -n -e 's/^.*(\(.*\)) at .*$/arp -d \1/p' \ - |sh >/dev/null 2>&1 - exit_with_hooks 1 -fi +TIMEOUT) + delete_old_alias + add_new_address + sleep 1 + if [ -n "$new_routers" ]; then + $LOGGER "New Routers ($interface): $new_routers" + set "$new_routers" + if ping -q -c 1 -w 1 "$1"; then + if [ "$new_ip_address" != "$alias_ip_address" ]; then + add_new_alias + fi + add_new_routes + if add_new_resolv_conf; then + exit_with_hooks 0 + fi + fi + fi + ifconfig $interface inet -alias $new_ip_address $medium + delete_old_routes + exit_with_hooks 1 + ;; +esac exit_with_hooks 0 |