Iopsysupgrade
This is the low level command that reads iopsysWrt Y3 images and writes to flash. The program is designed to use as little memory as possible and thus write the data to flash as soon as it is possible.
The iopsysWrt system is desigend around the concept of two independent releases stored in FLASH memory and an upgrade will never alter any data in the running system.
The integrity of the image like checksum and signature can by definition not be checked untill all data is received but to be able to stream the data directly to FLASH iopupgrade assumes the data is correct and does the check in the end. This means that if any error is detected the data written is now incorrect and iopupgrade does invalidate the data so it is not used by misstake.
This also means that after a failed upgrade the system is now running with only one valid system.
This program is not intended to be run directly by a user. There is a
wrapper called iopu
that is the intended command to use that in turn
calls iopupgrade.
Arguments
./iopupgrade [OPTION]..
Options:
-f, --file=NAME image file to use. If not specified stdin is used.
-M, --match=key=val,.... image headers needs to have this value
-q, --force do not do board name check
-u, --ubivol=NAME UBI volume device file to write rootfs to.
-U, --ubifs=NAME Extract ubifs image to file.
-k, --kernel=DEV Program the linux kernel to MTD device number
-s, --sequence=NUM Sequence number to add to cferam.000
-c, --cfe=num,num program CFE to MTD devices num,num.
Only the mtd partition number should be given.
-C, --cfe_dump=NAME Extract the CFE image to file
-m, --cfe_ver=num,num New CFE version needs to be large than this MAJOR,MINOR
Else it wll not be programmed. Omit this option to write
any version
-N, --nvram=offset Offset in cfe where the nvram is stored.
-p, --print Print headers.
-v Verbose output.
-d, --debug=NUM Set debug level. Higher = more output
-h Show this help screen.
Example commands
task | command |
---|---|
Help | iopupgrade -h |
Print headers | iopupgrade -f last.y3 -p |
match board name | iopupgrade -f last.y3 -M "board=DG400,dsl=A" |
Broadcom target related examples
task | command |
---|---|
Extract cfe to file | iopupgrade -f last.y3 -C cfe_data |
Broadcom CFE
Broadcom devices has a rather complicated way to write the boatloader(CFE) in that it is splitt in two segments and that it stores user settable variables inside itself. iopupgrade is not trying to figure out what to do itself but relies on beeing tooled exactly what to do.
The device number for the MTD partitions used and the offset for the start of NVRAM needs to be provided.
program CFE | command |
---|---|
ARM based | iopupgrade -f last.y3 -c3,4 -N 1408 |
MIPS based | iopupgrade -f last.y3 -c3,4 -N 6694 |
Broadcom kernel
Like the CFE the kernel also require modification to the data before it can be written to storeage. First the MTD partition needs to be set and then there also is a sequence number that needs to be set as that number signals to to CFE what kernel to actually boot from. The kernel with the larget number is the one used.
program kernel to mtd0 and set sequence number to 2
kernel | command |
---|---|
program kernel | iopupgrade -f last.y3 -k 0 -s 2 |
UBIFS root filesystem
task | command |
---|---|
extract ubifs image to file | iopupgrade -f last.y3 -U ubifs.img |
burn to ubi volume | iopupgrade -f last.y3 -u ubi0_0 |
Internals / Development
The program is structured around a main function that really do not know anyhting about the data format or task that is to be perforemd. It is instead structured around several different stages. The different parts that implements the actual functions just fills in a struct with function pointers for handlers of the different stages.
The diffrente stages is
stage | description | calls function |
---|---|---|
0 | Command line parsing | opt() |
1 | read in header | init() |
2 | read data loop | data() |
3 | no more data available | finish() |
4 | post | post() |
There is one more function called usage() that is called when -h/--help is detected on command line.
All functions is called once ecept the data() one that could be called as many times as there is bytes in the input file depending on how the data is provided to the program. Largets size is currently set to 1024 bytes.
post()
Post function is a bit special and it's currently needed only by the CFE module. CFE can not be programmed until after the checksum and signature is calculated so CFE stores the data in an internal buffer until the image data can be verified in the finish() function and writes it out in post().
Testing on development/host computer insted of on target
its possible to do development and testing on a normal linux laptop but in order to do this ipsysWrt imagewrite propgram needs to be installed and nandsim kernel module nees to be loaded.
mtd-utils for host
git clone git@public.inteno.se:mtd-utils
cd mtd-utils/
git checkout iopsys_target
make
Put PATH to imagewrite into $PATH its called from iopupdate
Nand simulator
here are a few command examples to get nandsim working
Nandsim. using 256MB 2048 pages.
sudo modprobe nandsim first_id_byte=0x2c second_id_byte=0xf1 third_id_byte=0x80 fourth_id_byte=0x15 fifth_id_byte=0x82 parts=8,40,40,5,5
sudo modprobe nandsim first_id_byte=0x20 second_id_byte=0xaa third_id_byte=0x0c fourth_id_byte=0x15 parts=8,40,40,5,5
For UBI to work with our existing images the vid offset needs to be set to 2048
sudo modprobe ubi
sudo ubiattach -p /dev/mtd5 -O 2048
sudo modprobe ubifs
here are some more usefull commands in no particular order
sudo ubimkvol /dev/ubi0 -N "rootfs_0" -s 60MiB
sudo ubimkvol /dev/ubi0 -N "rootfs_1" -s 60MiB
sudo ubiupdatevol /dev/ubi0_0 ubifs.img
sudo ubiupdatevol -t /dev/ubi0_0
sudo chmod 777 /dev/mtd*
flash_eraseall /dev/mtd0