]>
Commit | Line | Data |
---|---|---|
a8b970d7 | 1 | #! /bin/sh |
6054c1eb | 2 | # SPDX-License-Identifier: GPL-2.0 |
aba5acdf SH |
3 | |
4 | CheckForwarding () { | |
5 | local sbase fwd | |
6 | sbase=/proc/sys/net/ipv4/conf | |
7 | fwd=0 | |
8 | if [ -d $sbase ]; then | |
9 | for dir in $sbase/*/forwarding; do | |
a8b970d7 | 10 | fwd=$(( fwd + $(cat "$dir") )) |
aba5acdf SH |
11 | done |
12 | else | |
13 | fwd=2 | |
14 | fi | |
15 | return $fwd | |
16 | } | |
17 | ||
18 | RestartRDISC () { | |
19 | killall -HUP rdisc || rdisc -fs | |
20 | } | |
21 | ||
22 | ABCMaskLen () { | |
23 | local class; | |
24 | ||
25 | class=${1%%.*} | |
26 | if [ "$1" = "" -o $class -eq 0 -o $class -ge 224 ]; then return 0 | |
27 | elif [ $class -ge 224 ]; then return 0 | |
28 | elif [ $class -ge 192 ]; then return 24 | |
29 | elif [ $class -ge 128 ]; then return 16 | |
30 | else return 8; fi | |
31 | } | |
32 | ||
33 | label="label $1" | |
34 | ldev="$1" | |
35 | dev=${1%:*} | |
36 | if [ "$dev" = "" -o "$1" = "help" ]; then | |
37 | echo "Usage: ifcfg DEV [[add|del [ADDR[/LEN]] [PEER] | stop]" 1>&2 | |
38 | echo " add - add new address" 1>&2 | |
39 | echo " del - delete address" 1>&2 | |
40 | echo " stop - completely disable IP" 1>&2 | |
41 | exit 1 | |
42 | fi | |
43 | shift | |
44 | ||
45 | CheckForwarding | |
46 | fwd=$? | |
47 | if [ $fwd -ne 0 ]; then | |
48 | echo "Forwarding is ON or its state is unknown ($fwd). OK, No RDISC." 1>&2 | |
49 | fi | |
50 | ||
51 | ||
52 | deleting=0 | |
53 | case "$1" in | |
54 | add) shift ;; | |
55 | stop) | |
56 | if [ "$ldev" != "$dev" ]; then | |
57 | echo "Cannot stop alias $ldev" 1>&2 | |
58 | exit 1; | |
59 | fi | |
60 | ip -4 addr flush dev $dev $label || exit 1 | |
61 | if [ $fwd -eq 0 ]; then RestartRDISC; fi | |
62 | exit 0 ;; | |
63 | del*) | |
64 | deleting=1; shift ;; | |
65 | *) | |
66 | esac | |
67 | ||
68 | ipaddr= | |
69 | pfxlen= | |
70 | if [ "$1" != "" ]; then | |
71 | ipaddr=${1%/*} | |
72 | if [ "$1" != "$ipaddr" ]; then | |
73 | pfxlen=${1#*/} | |
74 | fi | |
75 | if [ "$ipaddr" = "" ]; then | |
76 | echo "$1 is bad IP address." 1>&2 | |
77 | exit 1 | |
78 | fi | |
79 | fi | |
80 | shift | |
81 | ||
82 | peer=$1 | |
83 | if [ "$peer" != "" ]; then | |
84 | if [ "$pfxlen" != "" -a "$pfxlen" != "32" ]; then | |
85 | echo "Peer address with non-trivial netmask." 1>&2 | |
86 | exit 1 | |
87 | fi | |
88 | pfx="$ipaddr peer $peer" | |
89 | else | |
58bb642f SH |
90 | if [ "$ipaddr" = "" ]; then |
91 | echo "Missing IP address argument." 1>&2 | |
92 | exit 1 | |
93 | fi | |
aba5acdf SH |
94 | if [ "$pfxlen" = "" ]; then |
95 | ABCMaskLen $ipaddr | |
96 | pfxlen=$? | |
97 | fi | |
98 | pfx="$ipaddr/$pfxlen" | |
99 | fi | |
100 | ||
101 | if [ "$ldev" = "$dev" -a "$ipaddr" != "" ]; then | |
102 | label= | |
103 | fi | |
104 | ||
105 | if [ $deleting -ne 0 ]; then | |
106 | ip addr del $pfx dev $dev $label || exit 1 | |
107 | if [ $fwd -eq 0 ]; then RestartRDISC; fi | |
108 | exit 0 | |
109 | fi | |
110 | ||
111 | ||
112 | if ! ip link set up dev $dev ; then | |
113 | echo "Error: cannot enable interface $dev." 1>&2 | |
114 | exit 1 | |
115 | fi | |
116 | if [ "$ipaddr" = "" ]; then exit 0; fi | |
117 | ||
118 | if ! arping -q -c 2 -w 3 -D -I $dev $ipaddr ; then | |
119 | echo "Error: some host already uses address $ipaddr on $dev." 1>&2 | |
120 | exit 1 | |
121 | fi | |
122 | ||
123 | if ! ip address add $pfx brd + dev $dev $label; then | |
124 | echo "Error: failed to add $pfx on $dev." 1>&2 | |
125 | exit 1 | |
126 | fi | |
127 | ||
128 | arping -q -A -c 1 -I $dev $ipaddr | |
129 | noarp=$? | |
130 | ( sleep 2 ; | |
a8b970d7 | 131 | arping -q -U -c 1 -I $dev $ipaddr ) >/dev/null 2>&1 </dev/null & |
aba5acdf | 132 | |
a8b970d7 MF |
133 | ip route add unreachable 224.0.0.0/24 >/dev/null 2>&1 |
134 | ip route add unreachable 255.255.255.255 >/dev/null 2>&1 | |
1e3197e0 | 135 | if [ "`ip link ls $dev | grep -c MULTICAST`" -ge 1 ]; then |
a8b970d7 | 136 | ip route add 224.0.0.0/4 dev $dev scope global >/dev/null 2>&1 |
aba5acdf SH |
137 | fi |
138 | ||
139 | if [ $fwd -eq 0 ]; then | |
140 | if [ $noarp -eq 0 ]; then | |
141 | ip ro append default dev $dev metric 30000 scope global | |
142 | elif [ "$peer" != "" ]; then | |
143 | if ping -q -c 2 -w 4 $peer ; then | |
144 | ip ro append default via $peer dev $dev metric 30001 | |
145 | fi | |
146 | fi | |
147 | RestartRDISC | |
148 | fi | |
149 | ||
150 | exit 0 |