#!/bin/sh # # Open Protium Reflash. This script will take a firmware image consisting # of a compressed linux kernel image, concatentated with a jffs2 root # filesystem image. The kernel MTD device is discovered by locating # the MTD partition with the tag "kernel" and the filesystem MTD device # is dicovered by locating the MTD partition with the tag "filesystem." # There is no TOC inside the firmware images so there is no direct way # to validate that the sizes of the parts in the firmware match the # existing MTD partitions. So there could be a mismatch. However, a # a mismatch size will be detect as this script mounts the newly laid # done filesystem, a mismatch guarantees this to fail. That being said # the script does validate the total size to prevent overwriting # uboot. Furthermore the script makes sure the fsdev is not in use and # that the various images are block aligned. flimg=$1 if [ -z "$flimg" ]; then echo "Usage: reflash " exit 1 fi if [ \! -f $flimg -o \! -r $flimg ]; then # # not a file or not readable # echo "error: Image file [$flimg] not available" exit 1 fi dmesg | grep StorCenter >/dev/null 2>&1 if [ $? -ne 0 ]; then exit 0 fi blksize=512 mtd=/proc/mtd mtab=/proc/mounts mntdir=/tmp/fs.$$ ktag=kernel fstag=filesystem kdev=` grep $ktag $mtd | awk -F: '{print $1}' | sed -e 's?mtd?/dev/mtdblock/?g'` fsdev=`grep $fstag $mtd | awk -F: '{print $1}' | sed -e 's?mtd?/dev/mtdblock/?g'` flsize=`ls -l $flimg | awk '{print $5}'` ksize=`grep $ktag $mtd | awk '{print "0x" $2}'` fssize=`grep $fstag $mtd | awk '{print "0x" $2}'` # # Size comes out of dc in exp notation and test wont accept a hex number # so dumo it in hex then use awk to convert to decimal # size=0x`dc 16 o $ksize $fssize + p` size=`echo $size | awk '{printf ("%d",$1)}'` # # Make sure we are block aligned # kblks=`dc $ksize $blksize / p` r=`dc $ksize $blksize % p` if [ $r -ne 0 ]; then echo "error: Kernel partition is not block aligned." exit 1 fi # # Make sure we are block aligned # fsblks=`dc $fssize $blksize / p` r=`dc $fssize $blksize % p` if [ $r -ne 0 ]; then echo "error: Filesystem partition is not block aligned." exit 1 fi # # Check to see that we have enough room # if [ $flsize -gt $size ]; then echo "error: Image size is bigger then available space." exit 1 fi # # Is fsdev mounted? # grep $fsdev $mtab > /dev/null 2>&1 if [ $? -eq 0 ]; then echo "error: $fsdev mounted" exit 1 fi # # If root is a jffs2 then close enough, im out # grep jffs2 $mtab > /dev/null 2>&1 if [ $? -eq 0 ]; then echo "error: $fsdev may be mounted" exit 1 fi # # Mount fsdev and save fsdev/linuxrc # mkdir $mntdir /tmp/$$ mount -t jffs2 $fsdev $mntdir if [ $? -ne 0 ]; then echo "error: Unable to mount $fsdev" exit 1 fi echo "Preserving /linuxrc in /tmp/$$" cp $mntdir/linuxrc* /tmp/$$ umount $mntdir echo "Image:" echo " Name : $flimg" echo " Length: $flsize" echo echo "Kernel:" echo " Device: $kdev" echo " Length: $ksize" echo " Blocks: $kblks" echo echo "Filesystem:" echo " Device: $fsdev" echo " Length: $fssize" echo " Blocks: $fsblks" echo echo 'Ready to flash, Continue? (yes/no)' read continue if [ "z$continue" != "zyes" ]; then rm -rf $mntdir /tmp/$$ exit 0 fi # # Lets do the flash # echo Preserving existing flash in: $flimg.sav.$$ dd of=$flimg.sav.$$ if=$kdev bs=$blksize count=$kblks dd of=$flimg.sav.$$ if=$fsdev bs=$blksize count=$fsblks seek=$kblks echo Flashing new firmware.... dd if=$flimg of=$kdev bs=$blksize count=$kblks dd if=$flimg of=$fsdev bs=$blksize count=$fsblks skip=$kblks sync sleep 5 # # Mount fsdev and restore fsdev/linuxrc # mount -t jffs2 $fsdev $mntdir if [ $? -ne 0 ]; then echo "error: Unable to re-mount $fsdev" exit 1 fi echo "Restoring /linuxrc" cp /tmp/$$/linuxrc* $mntdir umount $mntdir rm -rf $mntdir /tmp/$$