mediatek: mt7623: re-write sysupgrade uImage.FIT on MMC
[openwrt/staging/thess.git] / target / linux / mediatek / mt7623 / base-files / lib / upgrade / platform.sh
1
2 REQUIRE_IMAGE_METADATA=1
3 RAMFS_COPY_BIN='fwtool'
4
5 # Full system upgrade including preloader for MediaTek SoCs on eMMC or SD
6 mtk_mmc_full_upgrade() {
7 local diskdev partdev diff oldrecovery
8
9 if grep -q root=/dev/mmcblk0p2 /proc/cmdline; then
10 oldrecovery=1
11 else
12 oldrecovery=2
13 fi
14
15 export_bootdevice && export_partdevice diskdev 0 || {
16 echo "Unable to determine upgrade device"
17 return 1
18 }
19
20 #Keep the persistent random mac address (if it exists)
21 mkdir -p /tmp/recovery
22 export_partdevice recoverydev $oldrecovery
23 if mount -o rw,noatime "/dev/$recoverydev" -tvfat /tmp/recovery; then
24 [ -f "/tmp/recovery/mac_addr" ] && cp /tmp/recovery/mac_addr /tmp/
25 umount /tmp/recovery
26 fi
27 sync
28
29 if [ "$SAVE_PARTITIONS" = "1" ]; then
30 get_partitions "/dev/$diskdev" bootdisk
31
32 #extract the boot sector from the image
33 get_image "$@" | dd of=/tmp/image.bs count=1 bs=512b
34
35 get_partitions /tmp/image.bs image
36
37 #compare tables
38 diff="$(grep -F -x -v -f /tmp/partmap.bootdisk /tmp/partmap.image)"
39 else
40 diff=1
41 fi
42
43 if [ -n "$diff" ]; then
44 get_image "$@" | dd of="/dev/$diskdev" bs=4096 conv=fsync
45
46 # Separate removal and addition is necessary; otherwise, partition 1
47 # will be missing if it overlaps with the old partition 2
48 partx -d - "/dev/$diskdev"
49 partx -a - "/dev/$diskdev"
50 else
51 # iterate over each partition from the image and write it to the boot disk
52 while read part start size; do
53 part="$(($part - 2))"
54 if export_partdevice partdev $part; then
55 echo "Writing image to /dev/$partdev..."
56 get_image "$@" | dd of="/dev/$partdev" ibs="512" obs=1M skip="$start" count="$size" conv=fsync
57 else
58 echo "Unable to find partition $part device, skipped."
59 fi
60 done < /tmp/partmap.image
61
62 #copy partition uuid
63 echo "Writing new UUID to /dev/$diskdev..."
64 get_image "$@" | dd of="/dev/$diskdev" bs=1 skip=440 count=4 seek=440 conv=fsync
65 fi
66
67 export_partdevice recoverydev 2
68 if mount -o rw,noatime "/dev/$recoverydev" -t vfat /tmp/recovery; then
69 [ -f "/tmp/mac_addr" ] && cp /tmp/mac_addr /tmp/recovery
70
71 if [ "$diskdev" = "mmcblk0" -a -r /tmp/recovery/eMMCboot.bin ]; then
72 echo 0 > /sys/block/mmcblk0boot0/force_ro
73 dd if=/tmp/recovery/eMMCboot.bin of=/dev/mmcblk0boot0 conv=fsync
74 sync
75 echo 1 > /sys/block/mmcblk0boot0/force_ro
76 fi
77 sync
78 umount /tmp/recovery
79 fi
80 }
81
82 platform_do_upgrade() {
83 local board=$(board_name)
84
85 case "$board" in
86 bananapi,bpi-r2)
87 sync
88 export_bootdevice
89 export_partdevice fitpart 3
90 [ "$fitpart" ] || return 1
91 export UPGRADE_MMC_PARTDEV="/dev/$fitpart"
92 export UPGRADE_MMC_IMAGE_BLOCKS=$(($(get_image "$1" | fwtool -i /dev/null -T - | dd of=$UPGRADE_MMC_PARTDEV bs=512 2>&1 | grep "records out" | cut -d' ' -f1)))
93 [ "$UPGRADE_MMC_IMAGE_BLOCKS" ] || return 0
94 dd if=/dev/zero of=$UPGRADE_MMC_PARTDEV bs=512 seek=$UPGRADE_MMC_IMAGE_BLOCKS count=8
95 ;;
96
97 unielec,u7623-02-emmc-512m)
98 local magic="$(get_magic_long "$1")"
99 if [ "$magic" = "53444d4d" ]; then
100 mtk_mmc_full_upgrade "$1"
101 else # Old partial image starting with uImage
102 # Keep the persistent random mac address (if it exists)
103 recoverydev=mmcblk0p1
104 mkdir -p /tmp/recovery
105 mount -o rw,noatime /dev/$recoverydev /tmp/recovery
106 [ -f "/tmp/recovery/mac_addr" ] && \
107 mv -f /tmp/recovery/mac_addr /tmp/
108 umount /tmp/recovery
109
110 # 1310720 is the offset in bytes from the start of eMMC and to
111 # the location of the kernel (2560 512 byte sectors)
112 get_image "$1" | dd of=/dev/mmcblk0 bs=1310720 seek=1 conv=fsync
113
114 mount -o rw,noatime /dev/$recoverydev /tmp/recovery
115 [ -f "/tmp/mac_addr" ] && mv -f /tmp/mac_addr /tmp/recovery
116 sync
117 umount /tmp/recovery
118 fi
119 ;;
120 *)
121 default_do_upgrade "$1"
122 ;;
123 esac
124 }
125
126 PART_NAME=firmware
127
128 platform_check_image() {
129 local board=$(board_name)
130 local magic="$(get_magic_long "$1")"
131 local diskdev partdev diff
132
133 [ "$#" -gt 1 ] && return 1
134
135 case "$board" in
136 bananapi,bpi-r2)
137 [ "$magic" != "d00dfeed" ] && {
138 echo "Invalid image type."
139 return 1
140 }
141 ;;
142 unielec,u7623-02-emmc-512m)
143 # Can always upgrade to the new-style full image
144 [ "$magic" = "53444d4d" ] && return 0
145
146 # Legacy uImage directly at 0xA00 on the eMMC.
147 [ "$magic" != "27051956" ] && {
148 echo "Invalid image type."
149 return 1
150 }
151 rootpart=$(cat /proc/cmdline)
152 rootpart="${rootpart##*root=}"
153 rootpart="${rootpart%% *}"
154 [ "$rootpart" != "/dev/mmcblk0p2" ] && {
155 echo "Cannot downgrade to legacy image."
156 return 1
157 }
158 return 0
159 ;;
160 *)
161 echo "Sysupgrade is not supported on your board yet."
162 return 1
163 ;;
164 esac
165
166 return 0
167 }
168
169 platform_copy_config_mmc() {
170 if [ ! -e "$UPGRADE_BACKUP" ] ||
171 [ ! -e "$UPGRADE_MMC_PARTDEV" ] ||
172 [ ! "$UPGRADE_MMC_IMAGE_BLOCKS" ]; then
173 return
174 fi
175 dd if="$UPGRADE_BACKUP" of="$UPGRADE_MMC_PARTDEV" bs=512 seek=$UPGRADE_MMC_IMAGE_BLOCKS
176 sync
177 }
178
179 platform_copy_config() {
180 case "$(board_name)" in
181 bananapi,bpi-r2)
182 platform_copy_config_mmc
183 ;;
184 unielec,u7623-02-emmc-512m)
185 # platform_do_upgrade() will have set $recoverydev
186 if [ -n "$recoverydev" ]; then
187 mkdir -p /tmp/recovery
188 mount -o rw,noatime "/dev/$recoverydev" -t vfat /tmp/recovery
189 cp -af "$UPGRADE_BACKUP" "/tmp/recovery/$BACKUP_FILE"
190 sync
191 umount /tmp/recovery
192 fi
193 ;;
194 esac
195 }