YAFFS2 And NAND Flash

NAND is a certain type of flash chip types. It differs in some points to the somewhat older NOR flash commonly used in all Broadcom devices. See here for more information.

YAFFS was written to satisfy the special needs of NAND flash. Originally JFFS2 was taken as basis, which itself improved (not least in form of JFFS3) to better support NAND flash, too.

The second release of YAFFS especially points to supporting newer NAND flash chips with 2k page size and up to 128MB capacity.

Installing FreeWRT Into RouterBoard's NAND Flash

Installation is done nearly the same way as with CompactFlash. So to get direct access to the NAND flash (to be able to mount it e.g.), there needs to be an already running version of FreeWRT somewhere. It's up to your choice if that's a CompactFlash disk or a NFSRoot for netbooting. You just have to make sure there is enough free space on either medium to hold the RootFS tarball.

After booting into the existing Operating System, just mount the second (i.e. root) partition:

mount /dev/mtdblock1 /mnt

The filesystem type should be selected automatically, in doubt you can also use -t yaffs2. If you're getting errors about unerased or retired blocks, you must erase the flash before use, as the data on it is somehow corrupted.

Then you need to unpack the tarball into the mounted partition. It's your choice if you like to specify the target as parameter to tar, or if you just cd into the dir first. Following is the first method:

tar xzf /rootfs-2.6-rb-yaffs2.tar.gz -C /mnt

After unpacking, all there is left to do is executing the script called 'instprep-rb.sh' in the newly created RootFS's topdir. In our example this is as follows:

./mnt/instprep-rb.sh

This script will do a few things at once:

  • copies over the necessary device nodes from /dev (there is no 'mknod' in the default installation)
  • recursively changes the owner of all entries to root
  • mounts the first flash partition, copies the kernel into it and unmounts it again

After this is done, you can unmount the partition and reboot. After giving 'boot from NAND' as default boot medium inside RouterBOOT, FreeWRT should come up from flash.

Erasing The NAND Flash

Probably the most simple way of doing this is via RouterBOOT. Besides for version 1.5 (which you can't download anyway), there is a menu option 'format nand' doing the job. Alternatively the binaries 'flash_erase' and 'flash_eraseall', contained in the mtd-utils project work fine, too.

Caveats

Here are some things you can check if your device disagrees with you about how it should behave.

You can simply mount the first partition and check if there is a file named "kernel" (yes, actually it is your kernel). RouterBOOT searches for it with exactly this name in the first partition's filesystem's root directory.

Mount the second flash partition and check the RootFS. E.g. check if there are device nodes in /dev.

If you have a bare RootFS and don't know whether it is for use with NFS, CompactFlash? or YAFFS2, just open the script 'instprep-rb.sh' in the filesystem's topdir. The variable 'MYTARGET' holds the filesystem type the RootFS (and especially it's kernel) is ment for. (The value is written into it at install time.)

YAFFS2 And NAND Quirks

Both memory type and filesystem have some special properties one should be aware of to not getting surprised someday.

Page and erase size: as already mentioned above, page sizes can vary from 512Bytes to 2kBytes. The erase size for large page devices though is 128kBytes. To prevent excessive wear, if less than a full erase block is written to flash and deleted after, the block is not erased immediately. This not done until the whole block is full of invalid data. This gets visible when writing a few small files to disk. Used space (as reported by 'df') increases a lot with the first file (more than it's size), and doesn't increase at all when all other files are written.

Checkpoints: To improve mount time, yaffs2 has a feature called 'checkpoints'. These Checkpoints are blocks of meta information held in the filesystem itself. You could statically reserve a count of blocks for this meta information (by editing the source code ;), but FreeWRT let's this count in/decrease dynamically. So if you write lot's of data to your partition, the overhead increases reasonably (only viewable after remounting, as Checkpoints get written at unmount time). But as more data gets written to disk, these Checkpoints are one after another forgotten, and the space covered by them gets available for normal data.

http://www.linux-mtd.infradead.org/doc/nand.html
http://www.linux-mtd.infradead.org/tech/mtdnand/index.html
http://www.aleph1.co.uk/yaffsoverview