Skip to content

Commit 3a1eac6

Browse files
committed
feature/network: Move cmdline parser into a separate source and add tests for it
Signed-off-by: Alexey Gladkov <gladkov.alexey@gmail.com>
1 parent dd8e78f commit 3a1eac6

File tree

8 files changed

+464
-137
lines changed

8 files changed

+464
-137
lines changed
Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,143 @@
1+
#!/bin/bash
2+
3+
if [ -z "${__net_cmdline_sh_functions-}" ]; then
4+
__net_cmdline_sh_functions=1
5+
6+
. shell-error
7+
8+
ip_to_var()
9+
{
10+
local i v="$1:"
11+
set --
12+
13+
while [ -n "$v" ]; do
14+
if [ -z "${v##\[*:*:*\]:*}" ]; then
15+
# handle IPv6 address
16+
i="${v%%\]:*}"
17+
i="${i##\[}"
18+
19+
set -- "$@" "$i"
20+
v=${v#\[$i\]:}
21+
else
22+
set -- "$@" "${v%%:*}"
23+
v=${v#*:}
24+
fi
25+
done
26+
27+
ipaddr='' srv='' gw='' netmask='' hostname='' interface='' autoconf='' macaddr='' mtu='' dns1='' dns2=''
28+
29+
if [ $# -eq 0 ] || [ -z "$1" ]; then
30+
autoconf="error"
31+
return 0
32+
fi
33+
34+
# format: ip=<autoconf>
35+
36+
if [ $# -eq 1 ]; then
37+
autoconf="$1"
38+
return 0
39+
fi
40+
41+
# format: ip=<interface>:<autoconf>[:[<mtu>][:<macaddr>]]
42+
43+
case "${2-}" in
44+
on|any|dhcp|auto|dhcp4|auto4|dhcp6|auto6)
45+
interface="$1"
46+
autoconf="$2"
47+
shift 2
48+
[ $# -eq 0 ] ||
49+
{ mtu="$1"; shift; }
50+
[ $# -ne 6 ] ||
51+
{ macaddr="$1:$2:$3:$4:$5:$6"; shift 6; }
52+
[ $# -eq 0 ] ||
53+
fatal "syntax error: macaddr must contain 6 components"
54+
[ -n "$interface" ] ||
55+
fatal "interface name must be non-empty"
56+
return 0
57+
;;
58+
esac
59+
60+
# format: ip=<ipaddr>:[<peer>]:<gw>:<netmask>:<hostname>:<interface>:<autoconf>[:[<mtu>][:<macaddr>]]
61+
62+
ipaddr="$1" srv="$2" gw="$3" netmask="$4" hostname="$5" interface="$6" autoconf="$7"
63+
shift 7
64+
65+
[ -n "$interface" ] ||
66+
fatal "interface name must be non-empty"
67+
68+
[ $# -gt 0 ] ||
69+
return 0
70+
71+
if [ -z "$1" ] || [ -n "${1##*[!0-9]*}" ]; then
72+
mtu="$1"; shift
73+
[ $# -ne 6 ] ||
74+
{ macaddr="$1:$2:$3:$4:$5:$6"; shift 6; }
75+
[ $# -eq 0 ] ||
76+
fatal "syntax error: macaddr must contain 6 components"
77+
return 0
78+
fi
79+
80+
# format: ip=<ipaddr>:[<peer>]:<gw>:<netmask>:<hostname>:<interface>:<autoconf>[:[<dns1>][:<dns2>]]
81+
82+
dns1="$1"; shift
83+
[ $# -eq 0 ] || dns2="$1"
84+
}
85+
86+
route_to_var()
87+
{
88+
local i v="$1:"
89+
set --
90+
while [ -n "$v" ]; do
91+
if [ "${v#\[*:*:*\]:}" != "$v" ]; then
92+
# handle IPv6 address
93+
i="${v%%\]:*}"
94+
i="${i##\[}"
95+
set -- "$@" "$i"
96+
v=${v#\[$i\]:}
97+
else
98+
set -- "$@" "${v%%:*}"
99+
v=${v#*:}
100+
fi
101+
done
102+
103+
# format: route=<net>/<netmask>:<gateway>:<interface>
104+
105+
route_mask='' route_gw='' interface=''
106+
107+
case "$#" in
108+
3)
109+
route_mask="$1"
110+
route_gw="$2"
111+
interface="$3"
112+
;;
113+
*)
114+
fatal "syntax error: route must contain 3 components"
115+
;;
116+
esac
117+
}
118+
119+
ifname_to_var()
120+
{
121+
local IFS=:
122+
123+
# format: ifname=<interface>:<macaddr>
124+
set :$1
125+
126+
interface='' macaddr=''
127+
128+
case "$#" in
129+
7)
130+
interface="${1#:}"
131+
macaddr="$2:$3:$4:$5:$6:$7"
132+
;;
133+
21)
134+
interface="${1#:}"
135+
macaddr="$2:$3:$4:$5:$6:$7:$8:$9:${10}:${11}:${12}:${13}:${14}:${15}:${16}:${17}:${18}:${19}:${20}:${21}"
136+
;;
137+
*)
138+
fatal "syntax error: ifname must contain 7 or 21 components"
139+
;;
140+
esac
141+
}
142+
143+
fi #__net_cmdline_sh_functions

features/network/data/lib/initrd/post/cmdline/network

Lines changed: 3 additions & 137 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
. /etc/init.d/functions
77
. shell-ip-address
88
. network-sh-functions
9+
. network-cmdline-sh-functions
910

1011
lower_before_char()
1112
{
@@ -17,147 +18,12 @@ lower_before_char()
1718
fi
1819
}
1920

20-
ip_to_var()
21-
{
22-
local i v="$1:"
23-
set --
24-
25-
while [ -n "$v" ]; do
26-
if [ -z "${v##\[*:*:*\]:*}" ]; then
27-
# handle IPv6 address
28-
i="${v%%\]:*}"
29-
i="${i##\[}"
30-
31-
set -- "$@" "$i"
32-
v=${v#\[$i\]:}
33-
else
34-
set -- "$@" "${v%%:*}"
35-
v=${v#*:}
36-
fi
37-
done
38-
39-
ipaddr='' srv='' gw='' netmask='' hostname='' interface='' autoconf='' macaddr='' mtu='' dns1='' dns2=''
40-
41-
if [ $# -eq 0 ]; then
42-
autoconf="error"
43-
return 0
44-
fi
45-
46-
# format: ip=<autoconf>
47-
48-
if [ $# -eq 1 ]; then
49-
autoconf="$1"
50-
return 0
51-
fi
52-
53-
# format: ip=<interface>:<autoconf>[:[<mtu>][:<macaddr>]]
54-
55-
case "${2-}" in
56-
on|any|dhcp|auto|dhcp4|auto4|dhcp6|auto6)
57-
interface="$1"
58-
autoconf="$2"
59-
shift 2
60-
[ $# -eq 0 ] ||
61-
{ mtu="$1"; shift; }
62-
[ $# -ne 6 ] ||
63-
{ macaddr="$1:$2:$3:$4:$5:$6"; shift 6; }
64-
[ $# -eq 0 ] ||
65-
fatal "syntax error: macaddr must contain 6 components"
66-
[ -n "$interface" ] ||
67-
fatal "interface name must be non-empty"
68-
return 0
69-
;;
70-
esac
71-
72-
# format: ip=<ipaddr>:[<peer>]:<gw>:<netmask>:<hostname>:<interface>:<autoconf>[:[<mtu>][:<macaddr>]]
73-
74-
ipaddr="$1" srv="$2" gw="$3" netmask="$4" hostname="$5" interface="$6" autoconf="$7"
75-
shift 7
76-
77-
[ -n "$interface" ] ||
78-
fatal "interface name must be non-empty"
79-
80-
[ $# -gt 0 ] ||
81-
return 0
82-
83-
if [ -z "$1" ] || [ -n "${1##*[!0-9]*}" ]; then
84-
mtu="$1"; shift
85-
[ $# -ne 6 ] ||
86-
{ macaddr="$1:$2:$3:$4:$5:$6"; shift 6; }
87-
[ $# -eq 0 ] ||
88-
fatal "syntax error: macaddr must contain 6 components"
89-
return 0
90-
fi
91-
92-
# format: ip=<ipaddr>:[<peer>]:<gw>:<netmask>:<hostname>:<interface>:<autoconf>[:[<dns1>][:<dns2>]]
93-
94-
dns1="$1"; shift
95-
[ $# -eq 0 ] || dns2="$1"
96-
}
97-
98-
route_to_var()
99-
{
100-
local i v="$1:"
101-
set --
102-
while [ -n "$v" ]; do
103-
if [ "${v#\[*:*:*\]:}" != "$v" ]; then
104-
# handle IPv6 address
105-
i="${v%%\]:*}"
106-
i="${i##\[}"
107-
set -- "$@" "$i"
108-
v=${v#\[$i\]:}
109-
else
110-
set -- "$@" "${v%%:*}"
111-
v=${v#*:}
112-
fi
113-
done
114-
115-
# format: route=<net>/<netmask>:<gateway>:<interface>
116-
117-
route_mask='' route_gw='' interface=''
118-
119-
case "$#" in
120-
3)
121-
route_mask="$1"
122-
route_gw="$2"
123-
interface="$3"
124-
;;
125-
*)
126-
fatal "syntax error: route must contain 3 components"
127-
;;
128-
esac
129-
}
130-
131-
ifname_to_var()
132-
{
133-
local IFS=:
134-
135-
# format: ifname=<interface>:<macaddr>
136-
set :$1
137-
138-
interface='' macaddr=''
139-
140-
case "$#" in
141-
7)
142-
interface="${1#:}"
143-
macaddr="$2:$3:$4:$5:$6:$7"
144-
;;
145-
21)
146-
interface="${1#:}"
147-
macaddr="$2:$3:$4:$5:$6:$7:$8:$9:${10}:${11}:${12}:${13}:${14}:${15}:${16}:${17}:${18}:${19}:${20}:${21}"
148-
;;
149-
*)
150-
fatal "syntax error: ifname must contain 7 or 21 components"
151-
;;
152-
esac
153-
}
154-
15521
get_version()
15622
{
15723
local i="${2-}"
15824
case "$1" in
159-
*.*.*.*) i=4 ;;
160-
*:*:*) i=6 ;;
25+
*.*.*.*) i=4 ;;
26+
*:*:*) i=6 ;;
16127
esac
16228
ip_version=$i
16329
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
IFNAME: bootif0:8b:3f:d2:1c:d6:bc
2+
- interface: bootif0
3+
- macaddr : 8b:3f:d2:1c:d6:bc
4+
5+
IFNAME: bootif0:00:00:10:29:fe:80:00:00:00:00:00:00:b8:ce:f6:03:00:99:4c:42
6+
- interface: bootif0
7+
- macaddr : 00:00:10:29:fe:80:00:00:00:00:00:00:b8:ce:f6:03:00:99:4c:42
8+
9+
IFNAME: bootif0:8b:3f:d2:1c:d6
10+
run: syntax error: ifname must contain 7 or 21 components
11+
- FAILED
12+
13+
IFNAME: bootif0:8b:3f:d2:1c:d6:bc:ab
14+
run: syntax error: ifname must contain 7 or 21 components
15+
- FAILED
16+
17+
rc=0
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
#!/bin/bash -eu
2+
3+
. features/network/data/bin/network-cmdline-sh-functions
4+
5+
testcase()
6+
{
7+
printf 'IFNAME: %s\n' "$1"
8+
9+
local interface='' macaddr=''
10+
11+
ifname_to_var "$1"
12+
13+
printf ' - interface: %s\n' "$interface"
14+
printf ' - macaddr : %s\n' "$macaddr"
15+
printf '\n'
16+
}
17+
18+
failed()
19+
{
20+
printf ' - FAILED\n'
21+
printf '\n'
22+
}
23+
24+
# expect success
25+
(testcase "bootif0:8b:3f:d2:1c:d6:bc") || failed
26+
(testcase "bootif0:00:00:10:29:fe:80:00:00:00:00:00:00:b8:ce:f6:03:00:99:4c:42") || failed
27+
28+
# expect fail
29+
(testcase "bootif0:8b:3f:d2:1c:d6") || failed
30+
(testcase "bootif0:8b:3f:d2:1c:d6:bc:ab") || failed

0 commit comments

Comments
 (0)