How to Create JFFS2 Images

Summary

JFFS2 is a filesystem that was designed to be used on solid-state memory devices (such as NAND or NOR). It performs automatic wear-leveling to increase the life of the chip, and is aware of bad-blocks on NAND flash.

The typical method for deploying a JFFS2 filesystem is to create a JFFS2 image, optionally add summary information (for faster mount time), and then burn the image directly to flash using nand_write or flashcp.

Alternatively, you may create the filesystem directly on the flash chip. This guide provides both methods.

Using an externally built image

Prerequisites

Using JFFS2 with your Linux kernel requires the following:

  • Kernel with JFFS2 Support
    • CONFIG_JFFS2_FS=y
  • mkfs.jffs2 (Part of mtd-utils)
  • Filesystem that will be contained in the image

In addition to the above requirements, if you wish to use JFFS2 summary support, you must have the following:

  • Kernel with JFFS2 Summary Support
    • CONFIG_JFFS2_SUMMARY=y (optional)
  • sumtool (Part of mtd-utils) (optional)

Procedure

  1. Find geometry of the chip. Details for how to do this are found on the HOWTO Find NAND Parameters page.
  2. Create a JFFS2 image on the host using the mkfs.jffs2 utility. This is part of mtd-utils, and is typically packaged in a Timesys Reference Distribution. You will need to specify the following options:
    • -l or -b — Specify big or little endian, depending on your processor. See your processor datasheet for more information.
    • -q — Squash file permissions and make everything owned by root. This is a fairly typical option for root filesystems, although you may not wish to use it.
    • -n — No clean markers. Don't add clean markers to every block. Use this for filesystems destined for NAND flash.
    • -e SIZE — Erase Block Size. If the SIZE specified is below 4096, the units are assumed to be KiB, otherwise they are in bytes. This corresponds to the physical erase block size in the HOWTO Find NAND Parameters document.
    • -s SIZE — Page size. This corresponds to the Page size (or min i/o size) in the HOWTO Find NAND Parameters document.
    • -pSIZE — Image padding size. Pads the image with 0xFF so that it is SIZE bytes. If SIZE is not specified, it will pad to the end of the last erase block. NOTE: Do not put a space between the -p flag and SIZE, as the option parser will silently ignore the SIZE if you do.
    • -r ROOT — Root directory that you wish to use as the base of the image.
    • -o IMAGE — Path for mkfs.jffs2 output.
  3. Optionally, use the sumtool utility (also part of mtd-utils) to add summary information to the package. You will need to specify the following options:
    • -l or -b — Specify big or little endian, depending on your processor. See your processor datasheet for more information.
    • -n — No clean markers. Don't add clean markers to every block. Use this for filesystems destined for NAND flash.
    • -p — Pad image to 0xFF until the end of the final erase block. If you specified @-p@ for mkfs.jffs2, you should use this option.
    • -i=IMAGE — Path for mkfs.jffs2 image. This is the filesystem that the summary information will be added to.
    • -o=IMAGE — Path for sumtool output. This will be a JFFS2 image with summary information.
  4. Burn this image to flash using one of the following methods:
    • For most boards, you can use mtd-utils to burn it to a flash partition. This requires Linux running on the target system, however.
    • On Atmel boards, you can use SAM-BA to burn it to flash from the host machine.
    • Some bootloaders, such as LogicLoader, can copy a file from a flash card (SD or CF) directly to flash.
    • If you have a properly created configuration file, you can also use a debugger such as the BDI2000 to burn it to the board from the host machine.

Examples

To create a JFFS2 image that fills the entire NAND flash on the Atmel AT91SAM9260-EK:

bash> mkfs.jffs2 -lqn -e128 -s2048 -p0x10000000 -r <directory> -o <jffs2 file>

will create the JFFS2 image <jffs2 file>.

To add summary information:

bash> sumtool -nlp -i <jffs2 file> -o <jffs2 with summary file>

will create the JFFS2 image with summary information <jffs2 with summary file>.

Creating an Image on Flash

You can also create an empty filesystem on an MTD partition directly from the kernel command line.

  1. Determine the flash partition.
  2. Erase all data on the partition using the flash_erase tool, described here: HOWTO_Use_MTD.
  3. Mount the partition. The kernel will take care of setting up the necessary data structures for you.
  4. Once this partition is mounted, you can treat it like any other filesystem.

Mounting a JFFS2 Filesystem

From the Linux Command Line

You can use the mount command to mount a JFFS2 filesystem, much like any other partition. Assuming you are using /dev/mtd1 and wish to mount at /mnt, use the following instructions:

mount -t jffs2 /dev/mtdblock1 /mnt

Using a JFFS2 Filesystem as RFS

Once the image is created and burned to flash, you can mount it as a root filesystem by specifying certain parameters on the kernel command line. Add the following line to your command line to boot a JFFS2 filesystem as your RFS:

rootfstype=jffs2 root=/dev/mtdblockN rw

Where N is the MTD partition containing the RFS. You can determine your MTD partition scheme from the Linux source code for your specific board, or by looking at the console output from the kernel during boot time.

AT91 NAND: 8-bit, Software ECC
Scanning device for bad blocks
Creating 2 MTD partitions on "at91_nand":
0x00000000-0x00400000 : "Bootstrap" 
0x00400000-0x10000000 : "Partition 1" 

This example, taken from the kernel console output, shows that there are two partitions on the NAND flash chip. If there are no other MTD devices on the board, then these will correspond to /dev/mtdblock0 and /dev/mtdblock1, respectively. If you wanted to boot from "Partition 1", you would burn the RFS to /dev/mtd1, or NAND offset 0x00400000, depending on the tool.

Additional Resources

Common NAND Parameters

A list of parameters for common NAND chips can be found on the HOWTO Find NAND Parameters page.

mkfs.jffs2 Help Text

mkfs.jffs2: Usage: mkfs.jffs2 [OPTIONS]
Make a JFFS2 filesystem image from an existing directory tree

Options:
  -p, --pad[=SIZE]        Pad output to SIZE bytes with 0xFF. If SIZE is
                          not specified, the output is padded to the end of
                          the final erase block
  -r, -d, --root=DIR      Build filesystem from directory DIR (default: cwd)
  -s, --pagesize=SIZE     Use page size (max data node size) SIZE (default: 4KiB)
  -e, --eraseblock=SIZE   Use erase block size SIZE (default: 64KiB)
  -c, --cleanmarker=SIZE  Size of cleanmarker (default 12)
  -m, --compr-mode=MODE   Select compression mode (default: priortiry)
  -x, --disable-compressor=COMPRESSOR_NAME
                          Disable a compressor
  -X, --enable-compressor=COMPRESSOR_NAME
                          Enable a compressor
  -y, --compressor-priority=PRIORITY:COMPRESSOR_NAME
                          Set the priority of a compressor
  -L, --list-compressors  Show the list of the avaiable compressors
  -t, --test-compression  Call decompress and compare with the original (for test)
  -n, --no-cleanmarkers   Don't add a cleanmarker to every eraseblock
  -o, --output=FILE       Output to FILE (default: stdout)
  -l, --little-endian     Create a little-endian filesystem
  -b, --big-endian        Create a big-endian filesystem
  -D, --devtable=FILE     Use the named FILE as a device table file
  -f, --faketime          Change all file times to '0' for regression testing
  -q, --squash            Squash permissions and owners making all files be owned by root
  -U, --squash-uids       Squash owners making all files be owned by root
  -P, --squash-perms      Squash permissions on all files
  -h, --help              Display this help text
  -v, --verbose           Verbose operation
  -V, --version           Display version information
  -i, --incremental=FILE  Parse FILE and generate appendage output for it

Sumtool Help Text

Usage: sumtool [OPTIONS] -i inputfile -o outputfile
Convert the input JFFS2 file to a SUM-ed JFFS2 file

Options:
  -e, --eraseblock=SIZE     Use erase block size SIZE (default: 64KiB)
                            (usually 16KiB on NAND)
  -c, --cleanmarker=SIZE    Size of cleanmarker (default 12).
                            (usually 16 bytes on NAND, and will be set to
                            this value if left at the default 12). Will be
                            stored in OOB after each physical page composing
                            a physical erase block.
  -n, --no-cleanmarkers     Don't add a cleanmarker to every eraseblock
  -o, --output=FILE         Output to FILE 
  -i, --input=FILE          Input from FILE 
  -b, --bigendian           Image is big endian
  -l  --littleendian        Image is little endian
  -h, --help                Display this help text
  -v, --verbose             Verbose operation
  -V, --version             Display version information
  -p, --pad                 Pad the OUTPUT with 0xFF to the end of the final
                            eraseblock

Notes about Padding

External Links