Project

General

Profile

Download (8.16 KB) Statistics
| Branch: | Tag: | Revision:
1
#!/bin/sh
2
# $Id$
3
# $OpenBSD: dhclient-script,v 1.6 2004/05/06 18:22:41 claudio Exp $
4
# $FreeBSD: src/sbin/dhclient/dhclient-script,v 1.4 2005/06/10 03:41:18 brooks Exp $
5
#
6
# Copyright (c) 2003 Kenneth R Westerback <krw@openbsd.org>
7
#
8
# Permission to use, copy, modify, and distribute this software for any
9
# purpose with or without fee is hereby granted, provided that the above
10
# copyright notice and this permission notice appear in all copies.
11
#
12
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
13
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
14
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
15
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
16
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
17
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
18
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19
#
20

    
21
NETSTAT=/usr/bin/netstat
22
GREP=/usr/bin/grep
23
AWK=/usr/bin/awk
24
HOSTNAME=/bin/hostname
25
GREP=/usr/bin/grep
26
ROUTE=/sbin/route
27
SED=/usr/bin/sed
28
ARP=/usr/sbin/arp
29
IFCONFIG=/sbin/ifconfig
30

    
31
LOCALHOST=127.0.0.1
32

    
33
if [ -x /usr/bin/logger ]; then
34
	LOGGER="/usr/bin/logger -s -p user.notice -t dhclient"
35
else
36
	LOGGER=echo
37
fi
38

    
39
#
40
# Helper functions that implement common actions.
41
#
42

    
43
check_hostname() {
44
	current_hostname=`$HOSTNAME`
45
	if [ -z "$current_hostname" ]; then
46
		$LOGGER "New Hostname ($interface): $new_host_name"
47
		$HOSTNAME $new_host_name
48
	elif [ "$current_hostname" = "$old_host_name" -a \
49
	       "$new_host_name" != "$old_host_name" ]; then
50
		$LOGGER "New Hostname ($interface): $new_host_name"
51
		$HOSTNAME $new_host_name
52
	fi
53
}
54

    
55
arp_flush() {
56
	$ARP -an -i $interface | \
57
		$SED -n -e 's/^.*(\(.*\)) at .*$/arp -d \1/p' | \
58
		/bin/sh >/dev/null 2>&1
59
}
60

    
61
delete_old_address() {
62
	$IFCONFIG $interface inet -alias $old_ip_address $medium
63
}
64

    
65
add_new_address() {
66

    
67
	$LOGGER "Starting add_new_address()"
68

    
69
	$LOGGER "ifconfig $interface inet $new_ip_address netmask $new_subnet_mask broadcast $new_broadcast_address $medium"
70

    
71
	$IFCONFIG $interface \
72
		inet $new_ip_address \
73
		netmask $new_subnet_mask \
74
		broadcast $new_broadcast_address \
75
		$medium
76

    
77
		$LOGGER "New IP Address ($interface): $new_ip_address"
78
		$LOGGER "New Subnet Mask ($interface): $new_subnet_mask"
79
		$LOGGER "New Broadcast Address ($interface): $new_broadcast_address"
80
		$LOGGER "New Routers ($interface): $new_routers"
81

    
82
        echo $new_routers > /tmp/${interface}_router
83
	cp /var/db/${interface}_ip /tmp/rc.newwanip_oldip 2>/dev/null
84
	/usr/local/sbin/pfSctl -c "'interface reload $interface'"
85
				
86
}
87

    
88
delete_old_alias() {
89
	if [ -n "$alias_ip_address" ]; then
90
		$IFCONFIG $interface inet -alias $alias_ip_address > /dev/null 2>&1
91
		$ROUTE delete $alias_ip_address $LOCALHOST > /dev/null 2>&1
92
	fi
93
}
94

    
95
add_new_alias() {
96
	if [ -n "$alias_ip_address" ]; then
97
		$IFCONFIG $interface inet alias $alias_ip_address netmask \
98
		    $alias_subnet_mask
99
		$ROUTE add $alias_ip_address $LOCALHOST
100
	fi
101
}
102

    
103
delete_old_routes() {
104
	$LOGGER "Deleting old routes"
105
	$ROUTE delete "$old_ip_address" $LOCALHOST >/dev/null 2>&1
106
	# Only allow the default route to be overridden if it's on our own interface
107
	DEFAULTROUTE_IFACE=`/sbin/route get default | grep interface | awk '{print $2};'`
108
	if [ -z "${DEFAULTROUTE_IFACE}" -o "{$interface}" = "${DEFAULTROUTE_IFACE}" ]; then
109
		for router in $old_routers; do
110
			if [ $if_defaultroute = x -o $if_defaultroute = $interface ]; then
111
				$ROUTE delete default $route >/dev/null 2>&1
112
                        	/bin/rm -f /tmp/${interface}_router
113
			fi
114
		done
115
	fi
116

    
117
	if [ -n "$old_static_routes" ]; then
118
		set $old_static_routes
119
		while [ $# -gt 1 ]; do
120
			$ROUTE delete "$1" "$2"
121
			shift; shift
122
                        /bin/rm -f /tmp/${interface}_router
123
		done
124
	fi
125

    
126
	arp_flush
127
}
128

    
129
add_new_routes() {
130
	$LOGGER "Adding new routes to interface: $interface"
131

    
132
	# Only allow the default route to be overridden if it's on our own interface
133
	if [ -f "/tmp/${interface}_defaultgw" ]; then
134
		$ROUTE delete default
135
		for router in $new_routers; do
136
			if [ "$new_ip_address" = "$router" ]; then
137
				$ROUTE add default -iface $interface
138
				echo $ROUTE add default -iface $interface | $LOGGER
139
				echo $router > /tmp/${interface}_router
140
				echo $router > /tmp/${interface}_defaultgw
141
			else
142
				$ROUTE add default $router
143
				echo $ROUTE add default $router | $LOGGER
144
                       		echo $router > /tmp/${interface}_router
145
				echo $router > /tmp/${interface}_defaultgw
146
			fi
147
			# 2nd and subsequent default routers error out, so explicitly
148
			# stop processing the list after the first one.
149
			break
150
		done
151
	fi
152

    
153
	if [ -n "$new_static_routes" ]; then
154
		$LOGGER "New Static Routes ($interface): $new_static_routes"
155
		set $new_static_routes
156
		while [ $# -gt 1 ]; do
157
			$ROUTE add $1 $2
158
			shift; shift
159
                        echo $new_routers > /tmp/${interface}_router
160
		done
161
	fi
162
}
163

    
164
add_new_resolv_conf() {
165
	$LOGGER "Creating resolv.conf"
166
	if [ ! -f "/var/etc/nameserver_$interface" ]; then
167
		# Make sure file exists to avoid errors
168
		touch /var/etc/nameserver_$interface
169
	fi
170
	if [ -n "$new_domain_name_servers" ]; then
171
		# Remove old entries
172
		for nameserver in `cat /var/etc/nameserver_$interface`; do
173
			$ROUTE delete $nameserver
174
		done
175
		rm -f /var/etc/nameserver_$interface
176
		for nameserver in $new_domain_name_servers; do
177
			# Add a route to the nameserver out the correct interface
178
			# so that mulitple wans work correctly with multiple dns
179
			# also backup the nameserver for later route removal
180
			echo $nameserver >>/var/etc/nameserver_$interface
181
			$ROUTE add $nameserver -iface $interface
182
		done
183
		echo $new_domain_name >/var/etc/defaultdomain.conf
184
	fi
185

    
186
	/usr/local/sbin/pfSctl -c "'interface reload $interface'"
187

    
188
	return 0
189
}
190

    
191
# Notify rc.newwanip of changes to an interface
192
notify_rc_newwanip() {
193
}
194

    
195
#
196
# Start of active code.
197
#
198

    
199
# Invoke the local dhcp client enter hooks, if they exist.
200
if [ -f /etc/dhclient-enter-hooks ]; then
201
	$LOGGER "dhclient-enter-hooks"
202
	exit_status=0
203
	. /etc/dhclient-enter-hooks
204
	# allow the local script to abort processing of this state
205
	# local script must set exit_status variable to nonzero.
206
	if [ $exit_status -ne 0 ]; then
207
		exit $exit_status
208
	fi
209
fi
210

    
211
if [ -x $ROUTE ]; then
212
	if_defaultroute=`$ROUTE get default | $GREP interface | $AWK '{print $2}'`
213
else
214
	$LOGGER "if_defaultroute"
215
	if_defaultroute="x"
216
fi
217

    
218
$LOGGER $reason
219
case $reason in
220
MEDIUM)
221
	$IFCONFIG $interface $medium
222
	$IFCONFIG $interface inet -alias 0.0.0.0 $medium >/dev/null 2>&1
223
	/bin/sleep 1
224
	;;
225

    
226
PREINIT)
227
	delete_old_alias
228
	$IFCONFIG $interface inet 0.0.0.0 netmask 0.0.0.0 broadcast 255.255.255.255 up
229
	/bin/rm -f /tmp/${interface}_router
230
	;;
231

    
232
ARPCHECK|ARPSEND)
233
	;;
234

    
235
BOUND|RENEW|REBIND|REBOOT)
236
	check_hostname
237
	changes=no
238
	if [ -n "$old_ip_address" ]; then
239
		if [ -n "$alias_ip_address" ] && \
240
		   [ "$old_ip_address" != "$alias_ip_address" ]; then
241
			delete_old_alias
242
			changes=yes
243
		fi
244
		if [ "$old_ip_address" != "$new_ip_address" ]; then
245
			delete_old_address
246
			delete_old_routes
247
			changes=yes
248
		fi
249
	fi
250
	if [ "$reason" = BOUND ] || \
251
	   [ "$reason" = REBOOT ] || \
252
	   [ -z "$old_ip_address" ] || \
253
	   [ "$old_ip_address" != "$new_ip_address" ]; then
254
		add_new_address
255
		add_new_routes
256
		changes=yes
257
	fi
258
	if [ -n "$alias_ip_address" ] && \
259
       [ "$new_ip_address" != "$alias_ip_address" ]; then
260
		add_new_alias
261
		changes=yes
262
	fi
263
	add_new_resolv_conf
264
	if [ "$changes" = "yes" ] ; then
265
		notify_rc_newwanip
266
	fi
267
	;;
268

    
269
EXPIRE|FAIL)
270
	delete_old_alias
271
	if [ -n "$old_ip_address" ]; then
272
		delete_old_address
273
		delete_old_routes
274
	fi
275
	;;
276

    
277
TIMEOUT)
278
	delete_old_alias
279
	add_new_address
280
	/bin/sleep 1
281
	if [ -n "$new_routers" ]; then
282
		$LOGGER "New Routers ($interface): $new_routers"
283
		set "$new_routers"
284
		if /sbin/ping -q -c 1 -w 1 "$1"; then
285
			if [ "$new_ip_address" != "$alias_ip_address" ]; then
286
				add_new_alias
287
			fi
288
			add_new_routes
289
			if add_new_resolv_conf; then
290
				notify_rc_newwanip
291
			fi
292
		fi
293
	fi
294
	$IFCONFIG $interface inet -alias $new_ip_address $medium
295
	delete_old_routes
296
	;;
297
esac
298

    
299
# Invoke the local dhcp client exit hooks, if they exist.
300
if [ -f /etc/dhclient-exit-hooks ]; then
301
	$LOGGER "dhclient-exit-hooks"
302
	exit_status=0
303
	. /etc/dhclient-exit-hooks
304
	# allow the local script to abort processing of this state
305
	# local script must set exit_status variable to nonzero.
306
	exit $exit_status
307
fi
(2-2/3)