openrc/init.d/network.in

361 lines
6.9 KiB
Plaintext
Raw Normal View History

#!@SBINDIR@/openrc-run
# Copyright (c) 2009-2015 The OpenRC Authors.
# See the Authors file at the top-level directory of this distribution and
# https://github.com/OpenRC/openrc/blob/master/AUTHORS
#
# This file is part of OpenRC. It is subject to the license terms in
# the LICENSE file found in the top-level directory of this
# distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
# This file may not be copied, modified, propagated, or distributed
# except according to the terms contained in the LICENSE file.
# This script was inspired by the equivalent rc.d network from NetBSD.
description="Configures network interfaces."
__nl="
"
depend()
{
need localmount
after bootmisc clock
if [ -n "$(interfaces)" ]; then
provide net
fi
keyword -jail -prefix -vserver
}
uniqify()
{
local result= i=
for i; do
case " $result " in
*" $i "*);;
*) result="$result $i";;
esac
done
echo "${result# *}"
}
reverse()
{
local result= i=
for i; do
result="$i $result"
done
echo "${result# *}"
}
sys_interfaces()
{
2009-04-20 02:32:31 +05:30
case "$RC_UNAME" in
Linux)
local w= rest= i= cmd=$1
while read w rest; do
i=${w%%:*}
case "$i" in
"$w") continue ;;
lo|lo0) continue ;;
*) ;;
esac
if [ "$cmd" = u ]; then
ifconfig "$i" | grep -q "[ ]*UP" || continue
fi
printf "%s " "$i"
done </proc/net/dev
;;
*)
ifconfig -l$1
;;
esac
}
2010-03-23 01:32:12 +05:30
tentative()
{
local inet= address= rest=
case "$RC_UNAME" in
Linux)
[ -x /sbin/ip ] || [ -x /bin/ip ] || return 1
2010-03-25 01:55:42 +05:30
[ -n "$(ip -f inet6 addr show tentative)" ]
;;
2010-03-23 01:32:12 +05:30
*)
local inet= address= rest=
LC_ALL=C ifconfig -a | while read inet address rest; do
case "${inet}" in
inet6)
case "${rest}" in
*" "tentative*) return 2;;
esac
;;
esac
done
[ $? = 2 ]
;;
esac
}
auto_interfaces()
{
local ifs= c= f=
2009-04-20 02:32:31 +05:30
case "$RC_UNAME" in
NetBSD)
for c in $(ifconfig -C 2>/dev/null); do
for f in /etc/ifconfig.${c}[0-9]*; do
[ -f "$f" ] && printf "%s" "$f{##*.} "
done
done
;;
*)
for f in /etc/ifconfig.*; do
[ -f "$f" ] && printf "%s" "${f##*.} "
done
for f in /etc/ip.*; do
[ -f "$f" ] && printf "%s" "${f##*.} "
done
;;
esac
echo
}
interfaces()
{
uniqify $(sys_interfaces "$@") $interfaces $(auto_interfaces)
}
dumpargs()
{
local f="$1"
shift
case "$@" in
'') [ -f "$f" ] && cat "$f";;
*"$__nl"*) echo "$@";;
*)
(
set -o noglob
IFS=';'; set -- $@
IFS="$__nl"; echo "$*"
);;
esac
}
intup=false
runip()
{
local int="$1" err=
shift
# Ensure we have a valid broadcast address
case "$@" in
*" broadcast "*|*" brd "*) ;;
2009-12-14 15:44:39 +05:30
*:*) ;; # Ignore IPv6
*) set -- "$@" brd +;;
esac
err=$(LC_ALL=C ip address add "$@" dev "$int" 2>&1)
if [ -z "$err" ]; then
# ip does not bring up the interface when adding addresses
if ! $intup; then
ip link set "$int" up
intup=true
fi
return 0
fi
if [ "$err" = "RTNETLINK answers: File exists" ]; then
2009-04-20 02:32:31 +05:30
ip address del "$@" dev "$int" 2>/dev/null
fi
# Localise the error
ip address add "$@" dev "$int"
}
routeflush()
{
2009-04-20 02:32:31 +05:30
if [ "$RC_UNAME" = Linux ]; then
if [ -x /sbin/ip ] || [ -x /bin/ip ]; then
ip route flush scope global
2009-12-15 01:01:18 +05:30
ip route delete default 2>/dev/null
else
# Sadly we also delete some link routes, but
# this cannot be helped
local dest= gate= net= flags= rest=
route -n | while read dest gate net flags rest; do
[ -z "$net" ] && continue
case "$dest" in
[0-9]*) ;;
*) continue;;
esac
local xtra= netmask="netmask $net"
case "$flags" in
U) continue;;
*H*) flags=-host; netmask=;;
*!*) flags=-net; xtra=reject;;
*) flags=-net;;
esac
route del $flags $dest $netmask $xtra
done
2009-12-15 01:01:18 +05:30
# Erase any default dev eth0 routes
route del default 2>/dev/null
fi
else
route -qn flush
fi
}
runargs()
{
dumpargs "$@" | while read -r args; do
case "$args" in
''|"#"*) ;;
*)
(
2009-04-25 17:09:18 +05:30
eval vebegin "${args#*!}"
eval "${args#*!}"
veend $?
);;
esac
done
}
start()
{
2009-04-20 02:40:06 +05:30
local cr=0 r= int= intv= cmd= args= upcmd=
2009-10-16 16:34:20 +05:30
2009-10-25 04:33:20 +05:30
if [ -z "$domainname" -a -s /etc/defaultdomain ]; then
2009-10-16 16:34:20 +05:30
domainname=$(cat /etc/defaultdomain)
fi
if [ -n "$domainname" ]; then
ebegin "Setting NIS domainname: $domainname"
domainname "$domainname"
eend $?
fi
einfo "Starting network"
routeflush
eindent
for int in $(interfaces); do
local func= cf=
2009-04-20 02:40:06 +05:30
intv=$(shell_var "$int")
eval upcmd=\$ifup_$intv
for func in ip ifconfig; do
2009-04-27 13:21:18 +05:30
eval cmd=\$${func}_$intv
if [ -n "$cmd" -o -f /etc/"$func.$int" ]; then
cf=/etc/"$func.$int"
break
fi
done
[ -n "$cf" -o -n "$upcmd" -o \
-f /etc/ifup."$int" -o -f "$cf" ] || continue
veinfo "$int"
case "$func" in
ip) func=runip; intup=false;;
esac
eindent
runargs /etc/ifup."$int" "$upcmd"
r=0
dumpargs "$cf" "$cmd" | while read -r args; do
case "$args" in
''|"#"*) ;;
"!"*)
(
2009-04-25 17:09:18 +05:30
eval vebegin "${args#*!}"
eval "${args#*!}"
veend $?
);;
*)
(
set -o noglob
eval set -- "$args"
vebegin "$@"
$func "$int" "$@"
veend $?
);;
esac
done
eoutdent
done
eoutdent
eend $cr
2010-03-23 01:32:12 +05:30
# Wait for any inet6 tentative addresses
r=5
while [ $r -gt 0 ]; do
tentative || break
2010-03-25 01:55:42 +05:30
[ $r = 5 ] && vebegin "Waiting for tentative addresses"
2010-03-23 01:32:12 +05:30
sleep 1
: $(( r -= 1 ))
2010-03-23 01:32:12 +05:30
done
2010-03-25 01:55:42 +05:30
if [ $r != 5 ]; then
[ $r != 0 ]
veend $?
fi
if [ -n "$defaultroute" ]; then
ebegin "Setting default route $defaultroute"
route add default $defaultroute
eend $?
elif [ -n "$defaultiproute" ]; then
2009-12-11 14:56:43 +05:30
ebegin "Setting default route $defaultiproute"
ip route add default $defaultiproute
eend $?
fi
2009-12-15 01:01:18 +05:30
if [ -n "$defaultroute6" ]; then
ebegin "Setting default route $defaultroute6"
if [ "$RC_UNAME" = Linux ]; then
routecmd="route -A inet6 add"
else
routecmd="route -inet6 add"
fi
$routecmd default $defaultroute6
eend $?
elif [ -n "$defaultiproute6" ]; then
ebegin "Setting default route $defaultiproute6"
ip -f inet6 route add default $defaultiproute6
2009-12-15 01:01:18 +05:30
eend $?
fi
return 0
}
stop()
{
# Don't stop the network at shutdown.
# We don't use the noshutdown keyword so that we are started again
# correctly if we go back to multiuser.
yesno ${keep_network:-YES} && yesno $RC_GOINGDOWN && return 0
local int= intv= cmd= downcmd= r=
einfo "Stopping network"
routeflush
eindent
for int in $(reverse $(interfaces u)); do
case "$int" in
lo|lo0) continue ;;
*) ;;
esac
2009-04-20 02:40:06 +05:30
intv=$(shell_var "$int")
eval downcmd=\$ifdown_$intv
eval cmd=\$ip_$intv
[ -z "$cmd" ] && eval cmd=\$ifconfig_$intv
if [ -n "$cmd" -o -f /etc/ip."$int" -o \
-f /etc/ifconfig."$int" -o \
-n "$downcmd" -o -f /etc/ifdown."$int" ];
then
veinfo "$int"
runargs /etc/ifdown."$int" "$downcmd"
if [ -x /sbin/ip ] || [ -x /bin/ip ]; then
2009-12-14 19:51:30 +05:30
# We need to do this, otherwise we may
# fail to add things correctly on restart
ip address flush dev "$int" 2>/dev/null
fi
ifconfig "$int" down 2>/dev/null
ifconfig "$int" destroy 2>/dev/null
fi
done
eoutdent
eend 0
}