]> git.ozlabs.org Git - petitboot/blob - utils/pb-udhcpc
ui: implement timers with waitsets
[petitboot] / utils / pb-udhcpc
1 #!/bin/sh
2 #
3 # Petitboot udhcpc user script.  Should be run by udhcpc when
4 # there is a change in the dhcp configuration.  For more info
5 # see the udhcpc man page and the Linux kernel source file
6 # Documentation/filesystems/nfsroot.txt.
7 #
8
9 PBOOT_USER_EVENT_SOCKET="/tmp/petitboot.ev"
10 log="/var/log/petitboot/pb-udhcpc.log"
11
12 resolve_url() {
13         file="$1"
14
15         # URL? use as-is.
16         tmp=${file#://*}
17         if [ "$tmp" != "$file" ]
18         then
19                 echo "$file"
20         fi
21
22         # Otherwise, TFTP using an appropriate host. Start with the
23         # DHCP 'tftp' option:
24         host=${tftp}
25
26         # next, try the DHCP next-server-address
27         [ -z "$host" ] && host=${siaddr}
28
29         # finally, use the DHCP server we got this lease from:
30         [ -z "$host" ] && host=${serverid}
31
32         echo "tftp://$host/$file"
33 }
34
35 do_pxe() {
36         basedir=$1
37
38         params="conf@/net/${interface} method=dhcp"
39
40         # first, try by MAC
41         mac=$(cat /sys/class/net/$interface/address)
42         pb-event $params url=$basedir/$mac
43
44         # try decreasing fragments of IP lease
45         ip_hex=$(printf '%02X%02X%02X%02X' $(echo $ip | tr '.' ' '))
46         for i in $(seq 8 -1 1)
47         do
48                 frag=${hex_ip:0:$i}
49                 pb-event $params url=$basedir/$frag
50         done
51
52         # last, use default
53         pb-event $params url=$basedir/default
54 }
55
56 pb_add () {
57
58         # Look for an explicit config file location in the DHCP config-file
59         # parameter
60         if [ -n ${conffile} ]
61         then
62                 url=$(resolve_url ${conffile})
63                 pb-event conf@/net/${interface} url=$url method=dhcp
64                 return
65         fi
66
67         # Otherwise, we'll need the boot-file parameter. Looks like udhcpc
68         # will give us different names, depending if the parameter was in
69         # the header, or specified by options
70         [ -n "$bootfile" ] && bootfile=${boot_file}
71
72         if [ -z "$bootfile" ]
73         then
74                 return
75         fi
76
77         # PXE behaviour is to download the config file based on a file
78         # structure relative to the pxelinux binary
79         file=${bootfile}
80         [ -z "$file" ] && file=${boot_file}
81         if [ -n "$file" ]
82         then
83                 basedir=${file%%/*}
84                 do_pxe $basedir
85         fi
86
87         # Finally, add an option for the boot_file parameter
88         k_server_ip=${rootpath%%:*}
89         k_root_dir=${rootpath#*:}
90
91         args=
92         if [ -n $rootpath ]
93         then
94                 [ ${k_server_ip} != ${rootpath} ] || k_server_ip=${serverid}
95                 args="root=/dev/nfs ip=any nfsroot=${k_server_ip}:${k_root_dir}"
96         fi
97
98         pb-event add@/net/${interface} \
99                 name=netboot \
100                 image=tftp://${siaddr}/${boot_file} \
101                 args="$args"
102 }
103
104 pb_remove () {
105         pb-event remove@/net/${interface} name=netboot
106 }
107
108 case "$1" in
109 bound | renew)
110         pb_add
111         ;;
112 deconfig)
113         pb_remove
114         ;;
115 *)
116         ;;
117 esac
118
119 printf "--- $1 ---\n" >> ${log}
120 set >> ${log}
121 printf "---------------\n" >> ${log}