blob: 9f3b587536e23faeb38cad2a505e3ba041e91592 [file] [log] [blame]
Milton D. Miller II0e775142016-01-20 14:57:54 -06001#!/bin/sh
2
3echo update: "$@"
4
Milton Millerd16a7b02016-06-15 18:47:38 -05005echoerr() {
Patrick Williams51d6af42023-04-14 14:19:55 -05006 echo 1>&2 "ERROR: $*"
Milton Millerd16a7b02016-06-15 18:47:38 -05007}
8
Milton D. Miller II0e775142016-01-20 14:57:54 -06009cd /
10if ! test -r /proc/mounts || ! test -f /proc/mounts
11then
12 mkdir -p /proc
13 mount -t proc proc proc
14fi
15if ! test -d /sys/class
16then
17 mkdir -p /sys
18 mount -t sysfs sys sys
19fi
20if ! test -c /dev/null
21then
22 mkdir -p /dev
23 mount -t devtmpfs dev dev
24fi
Milton Millere1cbebe2016-05-23 16:00:19 -050025
Milton Miller810dc702016-05-23 19:17:55 -050026# mtd number N with mtd name Name can be mounted via mtdN, or mtd:Name
27# (with a mtd aware fs) or by /dev/mtdblockN (with a mtd or block fs).
28mtdismounted() {
29 m=${1##mtd}
30 if grep -s "mtdblock$m " /proc/mounts || grep -s "mtd$m " /proc/mounts
31 then
32 return 0
33 fi
Patrick Williams51d6af42023-04-14 14:19:55 -050034 n=$(cat "/sys/class/mtd/mtd$m/name")
Milton Miller810dc702016-05-23 19:17:55 -050035 if test -n "$n" && grep -s "mtd:$n " /proc/mounts
36 then
37 return 0
38 fi
39 return 1
40}
41
42# Detect child partitions when the whole flash is to be updated.
43# Ignore mtdNro and mtdblockN names in the class subsystem directory.
44childmtds() {
Patrick Williams51d6af42023-04-14 14:19:55 -050045 for m in "/sys/class/mtd/$1/mtd"*
Milton Miller810dc702016-05-23 19:17:55 -050046 do
47 m=${m##*/}
48 if test "${m%ro}" = "${m#mtdblock}"
49 then
Patrick Williams51d6af42023-04-14 14:19:55 -050050 echo "$m"
Milton Miller810dc702016-05-23 19:17:55 -050051 fi
52 done
53}
Milton D. Miller II0e775142016-01-20 14:57:54 -060054
Milton Miller1944aac2016-05-23 18:22:11 -050055toobig() {
Patrick Williams51d6af42023-04-14 14:19:55 -050056 if test "$(stat -L -c "%s" "$1")" -gt "$(cat "/sys/class/mtd/$2/size")"
Milton Miller1944aac2016-05-23 18:22:11 -050057 then
58 return 0
59 fi
60 return 1
61}
62
Milton D. Miller II0e775142016-01-20 14:57:54 -060063findmtd() {
64 m=$(grep -xl "$1" /sys/class/mtd/*/name)
65 m=${m%/name}
66 m=${m##*/}
Patrick Williams51d6af42023-04-14 14:19:55 -050067 echo "$m"
Milton D. Miller II0e775142016-01-20 14:57:54 -060068}
69
Andrew Jeffery25a50222016-02-23 23:47:23 +103070blkid_fs_type() {
71 # Emulate util-linux's `blkid -s TYPE -o value $1`
72 # Example busybox blkid output:
73 # # blkid /dev/mtdblock5
74 # /dev/mtdblock5: TYPE="squashfs"
75 # Process output to extract TYPE value "squashfs".
Patrick Williams51d6af42023-04-14 14:19:55 -050076 blkid "$1" | sed -e 's/^.*TYPE="//' -e 's/".*$//'
Andrew Jeffery25a50222016-02-23 23:47:23 +103077}
78
79probe_fs_type() {
Patrick Williams51d6af42023-04-14 14:19:55 -050080 fst=$(blkid_fs_type "$1")
81 echo "${fst:=jffs2}"
Andrew Jeffery25a50222016-02-23 23:47:23 +103082}
83
Milton D. Miller II0e775142016-01-20 14:57:54 -060084rwfs=$(findmtd rwfs)
85
Milton Millerba65b7b2016-02-05 12:07:53 -060086rwdev=/dev/mtdblock${rwfs#mtd}
Milton Millerba65b7b2016-02-05 12:07:53 -060087rwopts=rw
88rorwopts=ro${rwopts#rw}
89
Milton D. Miller IIc3697de2016-02-28 16:07:46 -060090rwdir=/run/initramfs/rw
Milton Millerba65b7b2016-02-05 12:07:53 -060091upper=$rwdir/cow
Milton D. Miller IIfa8316d2016-02-29 10:32:58 -060092save=/run/save/${upper##*/}
Milton D. Miller II0e775142016-01-20 14:57:54 -060093
Milton D. Miller IIa987d622016-02-29 21:34:43 -060094mounted=
Milton Miller4015b7a2016-05-23 17:41:34 -050095doflash=y
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -060096doclean=
Milton D. Miller IIecf68d52016-02-29 23:11:27 -060097dosave=y
98dorestore=y
Milton D. Miller II7141eb02016-02-29 21:44:22 -060099toram=
Milton Miller1944aac2016-05-23 18:22:11 -0500100checksize=y
Milton Miller810dc702016-05-23 19:17:55 -0500101checkmount=y
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600102
Milton D. Miller IIee91f8d2016-02-29 11:39:11 -0600103whitelist=/run/initramfs/whitelist
104image=/run/initramfs/image-
Milton Miller4e878612016-06-16 16:44:12 -0500105imglist=
Milton D. Miller IIee91f8d2016-02-29 11:39:11 -0600106
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600107while test "$1" != "${1#-}"
108do
109 case "$1" in
Milton Miller30137fa2016-06-15 16:02:23 -0500110 --help)
111 cat <<HERE
112Usage: $0 [options] -- Write images in /run/initramfs to flash (/dev/mtd*)
113 --help Show this message
114 --no-flash Don't attempt to write images to flash
115 --ignore-size Don't compare image size to mtd device size
116 --ignore-mount Don't check if destination is mounted
117 --save-files Copy whitelisted files to save directory in RAM
118 --no-save-files Don't copy whitelisted files to save directory
119 --copy-files Copy files from save directory to rwfs mountpoint
120 --restore-files Restore files from save directory to rwfs layer
121 --no-restore-files Don't restore saved files from ram to rwfs layer
122 --clean-saved-files Delete saved whitelisted files from RAM
123 --no-clean-saved-files Retain saved whitelisted files in RAM
124HERE
125
126 exit 0 ;;
127
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600128 --no-clean-saved-files)
129 doclean=
130 shift ;;
131 --clean-saved-files)
132 doclean=y
133 shift ;;
Milton D. Miller IIecf68d52016-02-29 23:11:27 -0600134 --no-save-files)
135 dosave=
136 shift ;;
137 --save-files)
138 dosave=y
139 shift ;;
140 --no-restore-files)
141 dorestore=
142 shift ;;
143 --restore-files)
144 dorestore=y
145 shift ;;
Milton Miller4015b7a2016-05-23 17:41:34 -0500146 --no-flash)
147 doflash=
148 shift ;;
Milton Miller1944aac2016-05-23 18:22:11 -0500149 --ignore-size)
150 checksize=
151 shift ;;
Milton Miller810dc702016-05-23 19:17:55 -0500152 --ignore-mount)
153 checkmount=
154 doflash=
155 shift ;;
Milton D. Miller II7141eb02016-02-29 21:44:22 -0600156 --copy-files)
157 toram=y
158 shift ;;
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600159 *)
Milton Miller30137fa2016-06-15 16:02:23 -0500160 echoerr "Unknown option $1. Try $0 --help."
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600161 exit 1 ;;
162 esac
163done
164
Patrick Williams51d6af42023-04-14 14:19:55 -0500165if test "$dosave" = "y"
Milton D. Miller II0e775142016-01-20 14:57:54 -0600166then
Milton D. Miller IIa987d622016-02-29 21:34:43 -0600167 if test ! -d $upper -a -n "$rwfs"
168 then
169 mkdir -p $rwdir
Patrick Williams51d6af42023-04-14 14:19:55 -0500170 mount "$rwdev" $rwdir -t "$(probe_fs_type "$rwdev")" -o "$rorwopts"
Milton D. Miller IIa987d622016-02-29 21:34:43 -0600171 mounted=$rwdir
172 fi
Milton D. Miller II0e775142016-01-20 14:57:54 -0600173
Patrick Williams51d6af42023-04-14 14:19:55 -0500174 while read -r f
Milton D. Miller II0e775142016-01-20 14:57:54 -0600175 do
Milton Milleradeceff2016-06-16 16:58:21 -0500176 # Entries shall start with /, no trailing /.. or embedded /../
177 if test "/${f#/}" != "$f" -o "${f%/..}" != "${f#*/../}"
178 then
179 echo 1>&2 "WARNING: Skipping bad whitelist entry $f."
180 continue
181 fi
182 if ! test -e "$upper/$f"
Milton D. Miller II0e775142016-01-20 14:57:54 -0600183 then
184 continue
185 fi
Milton Millerba65b7b2016-02-05 12:07:53 -0600186 d="$save/$f"
Milton Milleradeceff2016-06-16 16:58:21 -0500187 while test "${d%/}" != "${d%/.}"
188 do
189 d="${d%/.}"
190 d="${d%/}"
191 done
Milton D. Miller II0e775142016-01-20 14:57:54 -0600192 mkdir -p "${d%/*}"
Milton Milleradeceff2016-06-16 16:58:21 -0500193 cp -rp "$upper/$f" "${d%/*}/"
Milton D. Miller IIee91f8d2016-02-29 11:39:11 -0600194 done < $whitelist
Milton D. Miller II0e775142016-01-20 14:57:54 -0600195
Milton D. Miller IIa987d622016-02-29 21:34:43 -0600196 if test -n "$mounted"
197 then
198 umount $mounted
199 fi
Milton D. Miller II0e775142016-01-20 14:57:54 -0600200fi
201
Milton Miller4e878612016-06-16 16:44:12 -0500202imglist=$(echo $image*)
203if test "$imglist" = "$image*" -a ! -e "$imglist"
204then
205 # shell didn't expand the wildcard, so no files exist
206 echo "No images found to update."
207 imglist=
208fi
209
210for f in $imglist
Milton D. Miller II0e775142016-01-20 14:57:54 -0600211do
Patrick Williams51d6af42023-04-14 14:19:55 -0500212 m=$(findmtd "${f#"$image"}")
Milton D. Miller II0e775142016-01-20 14:57:54 -0600213 if test -z "$m"
214 then
Gunnar Mills2a85f602017-10-25 21:25:57 -0500215 echoerr "Unable to find mtd partition for ${f##*/}."
Milton Millere1cbebe2016-05-23 16:00:19 -0500216 exit 1
Milton D. Miller II0e775142016-01-20 14:57:54 -0600217 fi
Milton Miller1944aac2016-05-23 18:22:11 -0500218 if test -n "$checksize" && toobig "$f" "$m"
219 then
220 echoerr "Image ${f##*/} too big for $m."
221 exit 1
222 fi
Patrick Williams51d6af42023-04-14 14:19:55 -0500223 for s in $m $(childmtds "$m")
Milton Miller810dc702016-05-23 19:17:55 -0500224 do
Patrick Williams51d6af42023-04-14 14:19:55 -0500225 if test -n "$checkmount" && mtdismounted "$s"
Milton Miller810dc702016-05-23 19:17:55 -0500226 then
227 echoerr "Device $s is mounted, ${f##*/} is busy."
228 exit 1
229 fi
230 done
Milton D. Miller II0e775142016-01-20 14:57:54 -0600231done
232
Milton Miller4015b7a2016-05-23 17:41:34 -0500233if test -n "$doflash"
234then
Milton Miller4e878612016-06-16 16:44:12 -0500235 for f in $imglist
Milton Miller4015b7a2016-05-23 17:41:34 -0500236 do
Patrick Williams51d6af42023-04-14 14:19:55 -0500237 if test ! -s "$f"
Milton Miller4015b7a2016-05-23 17:41:34 -0500238 then
Patrick Williams51d6af42023-04-14 14:19:55 -0500239 echo "Skipping empty update of ${f#"$image"}."
240 rm "$f"
Milton Miller4015b7a2016-05-23 17:41:34 -0500241 continue
242 fi
Patrick Williams51d6af42023-04-14 14:19:55 -0500243 m=$(findmtd "${f#"$image"}")
244 echo "Updating ${f#"$image"}..."
245 flashcp -v "$f" "/dev/$m" && rm "$f"
Milton Miller4015b7a2016-05-23 17:41:34 -0500246 done
247fi
Milton D. Miller II0e775142016-01-20 14:57:54 -0600248
Patrick Williams51d6af42023-04-14 14:19:55 -0500249if test -d "$save" -a "$toram" = "y"
Milton D. Miller II7141eb02016-02-29 21:44:22 -0600250then
251 mkdir -p $upper
Patrick Williams51d6af42023-04-14 14:19:55 -0500252 cp -rp "$save/." "$upper/"
Milton D. Miller II7141eb02016-02-29 21:44:22 -0600253fi
254
Patrick Williams51d6af42023-04-14 14:19:55 -0500255if test -d "$save" -a "$dorestore" = "y"
Milton D. Miller II0e775142016-01-20 14:57:54 -0600256then
Milton D. Miller IIfacb7182016-02-28 16:20:19 -0600257 odir=$rwdir
258 rwdir=/run/rw
Patrick Williams51d6af42023-04-14 14:19:55 -0500259 upper=$rwdir${upper#"$odir"}
Milton D. Miller IIfacb7182016-02-28 16:20:19 -0600260
261 mkdir -p $rwdir
Patrick Williams51d6af42023-04-14 14:19:55 -0500262 mount "$rwdev" $rwdir -t "$(probe_fs_type "$rwdev")" -o $rwopts
263 mkdir -p "$upper"
264 cp -rp "$save/." "$upper/"
Milton Millerba65b7b2016-02-05 12:07:53 -0600265 umount $rwdir
Milton D. Miller IIfacb7182016-02-28 16:20:19 -0600266 rmdir $rwdir
Milton D. Miller II0e775142016-01-20 14:57:54 -0600267fi
268
Patrick Williams51d6af42023-04-14 14:19:55 -0500269if test "$doclean" = "y"
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600270then
Patrick Williams51d6af42023-04-14 14:19:55 -0500271 rm -rf "$save"
Milton D. Miller IId0b0c6a2016-02-28 16:32:14 -0600272fi
273
Milton Millerdbacf102016-02-05 13:56:18 -0600274exit