Linux——根文件系统的制作(jffs2 and ubifs)

一、根文件系统简介

根文件系统首先是一种文件系统,该文件系统不仅具有普通文件系统的存储数据文件的功能,但是相对于普通的文件系统而言它还是内核启动时所挂载(mount)的第一个文件系统,系统引导启动程序会在根文件系统挂载之后从中把一些初始化脚本(如inittab、rcS)和服务加载到内存中去运行。

根文件系统包括了Linux启动时所必须的目录和关键性的文件,例如Linux启动时都需要有init目录下的相关文件,在 Linux挂载分区时Linux一定会找/etc/fstab这个挂载配置文件等,根文件系统中还包括了应用程序(如ls、mkdir、rm、ifconfig等命令)和 GNU C 库(glibc、eglibc或uclibc)等。任何包括这些Linux 系统启动所必须的文件都可以称为根文件系统。Linux启动时,第一个挂载的必须是根文件系统;若系统不能从指定设备上挂载根文件系统,则系统会出错而退出启动。成功之后可以自动或手动挂载其他的文件系统。因此,一个系统中可以同时存在不同的文件系统

在 Linux 中将一个文件系统与一个存储设备关联起来的过程称为挂载(mount)。使用 mount 命令将一个文件系统附着到当前文件系统层次结构中(根)。在执行挂载时,要提供文件系统类型、文件系统和一个挂载点。根文件系统被挂载到根下“/”后,在根目录下就有根文件系统的各个目录,文件:/bin /sbin /mnt等,再将其他分区挂接到/mnt目录上,/mnt目录下就有这个分区的各个目录,文件。

Linux操作系统可以支持多种多样不同的文件系统,如windows下的FAT32、NTFS,Linux服务器使用的ext2、ext3、ext4、btrfs、xfs、reiser4、ufs、hfs(苹果系统),Linux操作系统自身使用的伪文件系统如swap、proc、sysfs、tmpfs等,也有一些设备的文件系统如iso9660(光盘)、nfs(网络文件系统)等,当然还包括我们嵌入式设备上用的不同的文件系统:initramfs(在内存中运行的文件系统)、jffs2(一种基于Norflash的文件系统,也支持小页的nandflash)、ubifs(目前Android手机上的Nandflash普遍使用的文件系统)、yaffs2(早期专门用来支持大页Nandflash的文件系统,具备可移植性,可在单片机裸机情况下使用)、cramfs(一种基于内存的只读的文件系统)、squashfs(在openwrt路由器上广泛使用的俄文件系统)、romfs(一种只读、支持片上执行XIP的文件系统,在uClinux中广泛使用)等。下面是几种常用的嵌入式根文件系统的对比:

    initramfs 该文件系统直接将根文件系统直接打包进Linux内核里(只有这种文件系统具有该功能),这样内核和根文件系统绑定在一块成为一个单独的文件,他在Linux系统启动后加载到内存中运行,所以速度快,但浪费内存,系统升级的时候内核和根文件系统一起升级比较方便。但因为他是基于内存的文件系统,所以系统掉电后针对根文件系统下所有文件的修改掉电都会丢失,如果要升级根文件系统只有重新编译、烧录Linux内核;

    jffs2 专门针对Nandflash设计的文件系统,小页的Nandflash也可以使用,只是效率不高;因为根文件系统存放在Flash上,所以根文件系统路径下的文件修改后掉电仍然存在;

    yaffs2 早期专门针对大页Nandflash设计的文件系统,他的源码独立于Linux内核维护着,所以可以在单片机等裸机环境下使用(只有该文件系统可以),linux内核想用它必须要打上补丁;在分区较大时,nandflash的挂载时间较长,现在逐渐被ubifs广泛替代;

    ubifs 专门针对Nandflash设计的一种文件系统,他在内核的MTD一层上面又建立了UBI一层,挂载速度、磨损均衡、读写速度非常快,目前nandflash上应用得最广的一种根文件系统;

 

Linux操作系统之所以能够支持这么多种不同的文件系统,主要是通过叫做VFS的中间层对这些文件系统提供了完美的支持。对于用户来说,这些文件系统几乎是透明的,在大部分情况下,用户通过libc和kernel的VFS交互,不需要关心底层文件系统的具体实现,但是有时应用程序也需要考虑底层文件系统限制(比如fat vfat不支持链接,比如各个文件系统支持最大文件限制不同)。VFS主要有以下特性:

    向上,对应用层提供一个标准的文件操作接口,如open()、read()、write()、ioct()、close()等;

    对下,对所有文件系统提供一个统一的标准接口,以便其他操作系统的文件系统可以方便的移植到Linux上;

    VFS内部则通过一系列高效的管理机制,比如inode cache, dentry cache 以及文件系统的预读等技术,使得底层文件系统不需沉溺到复杂的内核操作,即可获得高性能;

    此外VFS把一些复杂的操作尽量抽象到VFS内部,使得底层文件系统实现更简单。

二、mtd-utils工具源码编译

Linux内核MTD对同一Flash分区提供了两种设备文件给用户层使用,一种是/dev/mtdblockX块设备,该设备用来建立文件系统并挂载起来使用;另外一种相对应的/dev/mtdX字符设备,其里面添加了一些ioctl,支持很多命令,如MEMGETINFO,MEMERASE等。而mtd-util就是以这些ioctl为基础而实

现的工具,实现一些关于Flash的操作,如flash_erase、flash_eraseall、flashcp、nandwrite等命令,此外在PC上制作根文件系统所需要的一些工具也在里面,如制作JFFS2根文件系统用的mkfs.jffs2、制作UBIFS根文件系统工具mkfs.ubifs以及开发板上操作UBI文件系统的命令。

这里 只介绍PC端的源码编译来获取mkfs.jffs2和mkfs.ubifs工具,如果相应的工具需要放在ARM开发板上运行则需要使用交叉编译器编译。mtd_utils需要lzo、zlib和e2fsprogs这三个库,所以在编译mtd_utils之前先需要编译这三个库。Linux下使用源码安装工具时,如果有Makefile则直接用make命令编译,如果没有Makefile文件,则一般有个configure的脚本,该源码结构的编译三步曲:./configure、make、make install

2.1 创建mtd-utils的工作路径

cd fl2440/

mkdir -p x86_tools/mtd_utils

mtd-utils编译依赖lzo、zlib和libuuu这几个库,所以我们在编译它之前先要编译这些库。另外,为了在运行mkfs.jffs2和mkfs.ubifs这些命令时不依赖这些动态库,我们采用静态编译、然后静态链接生成这两个命令。(因为我们的centos安装系统默认的是动态库,所以我们要自己安装静态库)

2.2 编译lzo库

cd fl2440/x86_tools/mtd_utils/

wget  http://www.oberhumer.com/opensource/lzo/download/lzo-2.10.tar.gz

tar -xzf lzo-2.10.tar.gz

cd lzo-2.10

.cofigure --help查看configure帮助信息,看他支持哪些参数。

 

./configure --prefix=`pwd`/../install --enable-static --disable-shared   --prefix指定安装路径 --enable-static指定生成静态库 --disableshared 指定不要生成动态库

make && make install

2.3 编译zlib库

cd fl2440/x86_tools/mtd_utils/

wget https://github.com/madler/zlib/archive/v1.2.10.tar.gz -O zlib-1.2.10.tar.gz

tar -xzf zlib-1.2.10.tar.gz cd zlib-1.2.10

./configure --prefix=`pwd`/../install --static //每个config的文件命令是不一样的,需要./configure --help 查看

make && make install

find -iname "*.a"   //查找静态库

2.4 编译e2fsprogs库(libuuid)

cd fl2440/x86_tools/mtd_utils/

wget  https://github.com/tytso/e2fsprogs/archive/v1.43.7.tar.gz -O e2fsprogs-1.43.7.tar.gz

tar -xzf e2fsprogs-1.43.7.tar.gz

cd e2fsprogs-1.43.7/

./configure --prefix=`pwd`/../install -- enable-elf-shlibs --enable-libuuid

make ; make install-libs

2.5 编译mtd-utils并安装mkfs.jffs2和mkfs.ubifs

cd fl2440/x86_tools/mtd_utils/

wget ftp://ftp.infradead.org/pub/mtdutils/mtd-utils-1.5.2.tar.bz2

tar -xjf mtd-utils-1.5.2.tar.bz2

export CFLAGS+=" -I../install/include/ "   //指定头文件

export LDFLAGS+=" -L../install/lib/ -static"    //链接

make WITHOUT_XATTR=1   //这个参数决定了c文件的编译,不加的话会报错XATTR这个库找不到。(第二幅图)

后来编译出现这种错误(这是在有桌面的环境下):

 

这是因为我们安装的CentOS库是动态库,而我们这里使用的是静态库,所以导致出现这样的错误。

然后我再虚拟机上执行了下面的命令:

sudo yum install glibc-static libstdc++-static -y //安装了静态库然后执行就可以了

 

这个宏定义在mkfs.jffs2.c文件中。

sudo cp mkfs.jffs2 /bin/

sudo cp mkfs.ubifs/mkfs.ubifs /bin/

sudo cp mkfs.ubifs/mkfs.ubifs /bin/

三、内核调整Nandflash分区表

FL2440上使用K9F2G08这个256MB的Nandflash,就像PC上的硬盘一样,我们也需要对整个

Nandflash进行分区。只不过这个分区的过程是通过在Linux的源码修改来调整,接下来我们按照下面这个分区表来调整Linux系统的分区表。(一旦对分区进行调整,一定要记得将相关联的分区格式化,否则会出现错误)。

(Nandflash一读就读一个页,nand eraser一擦就擦一个块)

cd fl2440/linux/linux-3.0

vim arch/arm/plat-s3c24xx/common-smdk.c

/* NAND parititon from 2.4.18-swl5 */

static struct mtd_partition smdk_default_nand_part[] = {

[0] = {

    .name = "mtdblock0 u-boot 1MB",

    .offset = 0,

    .size = SZ_1M*1, /* 0x0000000 ~ 0x0100000 */

            },

[1] = {

    .name = "mtdblock1 kernel 15MB",

    .offset = MTDPART_OFS_NXTBLK,

    .size = SZ_1M*15, /* 0x0100000 ~ 0X1000000 */

        },

[2] = {

    .name = "mtdblock2 rootfs 40MB",

    .offset = MTDPART_OFS_NXTBLK,

    .size = SZ_1M*40,

    },

[3] = {

    .name = "mtdblock3 apps 80MB",

    .offset = MTDPART_OFS_NXTBLK,

    .size = SZ_1M*80,

        },

[4] = {

    .name = "mtdblock4 data 80MB",

    .offset = MTDPART_OFS_NXTBLK,

    .size = SZ_1M*80,

        },

[5] = {

    .name = "mtdblock5 backup 40MB",

    .offset = MTDPART_OFS_NXTBLK,

    .size = SZ_1M*40,

        }

};

static struct s3c2410_nand_set smdk_nand_sets[] = {

重新编译Linux内核并启动,这时我们就会发现内核启动时打印出新的分区信息

NAND device: Manufacturer ID: 0xec, Chip ID: 0xda (Samsung NAND 256MiB 3,3V 8-bit)

Scanning device for bad blocks

Bad eraseblock 740 at 0x000005c80000

Creating 6 MTD partitions on "NAND":

0x000000000000-0x000000100000 : "mtdblock0 u-boot 1MB"

0x000000100000-0x000001000000 : "mtdblock1 kernel 15MB"

0x000001000000-0x000003800000 : "mtdblock2 rootfs 40MB"

0x000003800000-0x000008800000 : "mtdblock3 apps 80MB"

0x000008800000-0x00000d800000 : "mtdblock4 data 80MB"

0x00000d800000-0x000010000000 : "mtdblock5 backup 40MB"

UBI: attaching mtd2 to ubi0

UBI: physical eraseblock size:   131072 bytes (128 KiB)

UBI: logical eraseblock size:    129024 bytes

UBI: smallest flash I/O unit:    2048

四、jffs2根文件系统制作

4.1 jffs2文件系统简介

JFFS2全名是 Journalling Flash File System Version2,是Redhat公司开发的Flash的文件系统,其

前身是JFFS, 最早只支援Norflash, 自2.6版以后开始支援NAND Flash,其功能就是管理在MTD设备上实现的日志型文件系统,极适合使用于嵌入式系统。与其他的存储设备存储方案相比,JFFS2并不准备提供让传统文件系统也可以使用此类设备的转换层。它只会直接在MTD设备上实现日志结构的文件系统。JFFS2会在安装的时候,扫描MTD设备的日志内容,并在RAM中重新建立文件系统结构本身。除了提供具有断电可靠性的日志结构文件系统,JFFS2还会在它管理的MTD设备上实现“损耗平衡”和“数

据压缩”等特性。下面是JFFS2的不足之处:

 

    JFFS2 的挂载(mount)过程需要对Flash从头到尾的扫描,这个过程是很慢的,我们在测试中发现,挂载一个 16M 的闪存有时需要半分钟以上的时间

    JFFS2 在分区的空间使用率比较大后,数据的读写非常缓慢

 

    JFFS2 对磨损平衡是用概率的方法来解决的,这很难保证磨损平衡的确定性。在某些情况下,可

    能造成对擦写块不必要的擦写操作;在某些情况下,又会引起对磨损平衡调整的不及时。

    JFFS2没有write-back机制,不能将资料暂存于缓存(cache), 以致于flash I/O的动作频繁。

JFFS2是针对早起的Norflash和小页(页大小<4K)的Nandflash设计的,并不适合大页的Nandflash。所以我们一般在Norflash上使用JFFS2文件系统,而现在普遍使用的大页Nandflash并不适用它。

4.2 根文件系统镜像文件制作

我们可以使用mtd-utils源码编译出来的mkfs.jffs2工具,将根文件系统树目录制作成jffs2根文件系统

镜像。在开始制作镜像之前,我们先看看mkfs.jffs2的使用说明:

mkfs.jffs2 -h

mkfs.jffs2: error!: Usage: mkfs.jffs2 [OPTIONS]

Make a JFFS2 file system image from an existing directory tree

 

Options:

  -p, --pad[=SIZE]        Pad output to SIZE bytes with 0xFF. If SIZE is     // 指 定jffs2文件系统镜像的填充大小

                          not specified, the output is padded to the end of

                          the final erase block

  -r, -d, --root=DIR      Build file system from directory DIR (default: cwd)      // 指定根文件系统目录树的路径

  -s, --pagesize=SIZE     Use page size (max data node size) SIZE.                    //指定Nandflash的页大小

                          Set according to target system's memory management

                          page size (default: 4KiB)

  -e, --eraseblock=SIZE   Use erase block size SIZE (default: 64KiB)                 // 指定Nandflash的块大小

  -c, --cleanmarker=SIZE  Size of cleanmarker (default 12)

  -m, --compr-mode=MODE   Select compression mode (default: priority)

  -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 available 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

下载我们开始使用根文件系统树制作JFFS2根文件系统镜像:

cd fl2440/linux/

du -sh rootfs

mkfs.jffs2 -n -s 2048 -e 128KiB -d ./rootfs -o rootfs-jffs2.bin  // 制作根文件系统时不进行填充

mkfs.jffs2 -n -s 2048 -e 128KiB -d ./rootfs -o rootfs-jffs2.bin --pad=0xa00000   

    -n 指明不添加清除标记(nand flash 有自己的校检块,存放相关的信息),如果挂载后会出现下面类似警告信息,则加上-n 就会消失:

CLEANMARKER node found at 0x0042c000 has totlen 0xc != normal 0x0

    -s 指定Nandflash的页大小为2KB

    -e 指定Nandflash的擦除块大小为128KB

    -d 指定根文件系统目录树的路径 为./rootfs

    -o 指定制作生成的根文件系统镜像文件名为 rootfs-jffs.bin,该文件需要u-boot烧录到Nandflash的相应分区

    --pad=0xa00000 将制作的根文件系统镜像(rootfs-jffs2.bin)文件大小用0xFF填充为--pad指定的值。如果在制作根文件系统的不填充的话,Linux挂载启动根文件系统时将会出现下面警告信息。

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x006430dc: 0x5555instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x006430e0: 0x5555instead

我们在之前的Linux内核Nandflash分区修改里将rootfs分区大小设置为40M,所以这里的--pad值应该为0x280000。但如果使用0x2800000,则根文件系统镜像的大小就为40M,这样u-boot下载烧录的时间较长,另外如果在Nandflash上烧录该镜像文件的分区存在坏块的话,则在u-boot里用nandwrite烧录时会跳过坏块溢出到下一个分区空间中去,从而占用了下一个空间的使用,系统就会出错。这里我们将填充大小值设置为10M是也可以解决上面jffs2_scan_eraseblock抛出的警告信息,之所以将填充大小设置为10M是因为不进行填充时制作的根文件系统镜像大小为6.3M,这个值的大小根据分区大小和根文件系统目录树的实际大小进行调整。

export TERM=vt100

make menuconfig

General setup --->

[ ] Automatically append version information to the version string 取消这个

选项减少内核大小

[ ] Support for paging of anonymous memory (swap) Nandflash不需要

swap分区,如果是PC上的硬盘则需要swap分区

<*> Kernel .config support

[ ] Initial RAM filesystem and RAM disk (initramfs/initrd) support 一定要

取消initramfs的支持,否则内核找到initramfs则直接使用initramfs启动

[*] Configure standard kernel features (expert users) ---> 添加这个选项

[*] Embedded system 添加这个选项

File systems --->

< > Second extended fs support 取消PC端用的ext2文件系统支持,减少内

核大小

< > Ext3 journalling file system support 取消PC端用的ext3文件系统支持,减少内

核大小

< > The Extended 4 (ext4) filesystem 取消PC端用的ext4文件系统支持,减少内

核大小

< > Kernel automounter version 4 support (also supports v3) 取消这个选项减少内

核大小

< > FUSE (Filesystem in Userspace) support 取消这个选项减少内

核大小

CD-ROM/DVD Filesystems --->

< > ISO 9660 CDROM file system support 取消这个光驱光盘选项,减少内

核大小

< > UDF file system support 取消这个光驱光盘选项,减少内

核大小

DOS/FAT/NT Filesystems --->

<*> MSDOS fs support

<*> VFAT (Windows-95) fs support 添加Windows的FAT文件系统支

持,U盘或SD卡中会使用

(437) Default codepage for FAT

(iso8859-1) Default iocharset for FAT

<*> NTFS file system support 添加Windows的NTFS文件系统支

,U盘或SD卡中会使用

[ ] NTFS debugging support

[*] NTFS write support

Pseudo filesystems --->

<*> Userspace-driven configuration filesystem 添加sysfs伪文件系统

支持

[*] Miscellaneous filesystems --->

<*> Journalling Flash File System v2 (JFFS2) support 添

加JFFS2文件系统支持

(0) JFFS2 debugging verbosity (0 = quiet, 2 = noisy)

[*] JFFS2 write-buffering support

[ ] Verify JFFS2 write-buffer reads

[*] JFFS2 summary support (EXPERIMENTAL)

[ ] JFFS2 XATTR support (EXPERIMENTAL)

[ ] Advanced compression options for JFFS2

其他文件系统如果不需要的话都不要选

< > Compressed ROM file system support (cramfs) 如果不用的

话,取消cramfs文件系统的支持

< > SquashFS 4.0 - Squashed file system support 如果不用的

话,取消SquashFS文件系统的支持

< > ROM file system support 如果不用的

话,取消ROM文件系统的支持

[*] Network File Systems --->

<*> NFS client support

[*] NFS client support for NFS version 3

[*] NFS client support for the NFSv3 ACL protocol extension

[ ] NFS client support for NFS version 4

[*] Root file system on NFS

将其他不需要的网络文件系统都不要选

< > NFS server support

< > Ceph distributed file system (EXPERIMENTAL)

< > CIFS support (advanced network filesystem, SMBFS successor)

< > NCP file system support (to mount NetWare volumes)

< > Coda file system support (advanced network fs)

< > Andrew File System support (AFS) (EXPERIMENTAL)

Partition Types --->

[ ] PC BIOS (MSDOS partition tables) support 取消这个选项减少内

核大小

-*- Native language support ---> U盘的挂载可能需要下面这些语言编码的支

持,譬如简体中文的CP936和GB2312等

(iso8859-1) Default NLS Option

<*> Codepage 437 (United States, Canada)

<*> Simplified Chinese charset (CP936, GB2312)

<*> Traditional Chinese charset (Big5)

<*> ASCII (United States)

<*> NLS ISO 8859-1 (Latin 1; Western European Languages)

<*> NLS UTF-8

其他语言如果不需要全部不要选

4.4 u-boot系统烧录和环境变量配置

因为使用jffs2根文件系统启动的Linux内核不包含根文件系统,所以u-boot烧录Linux系统时需要同时烧录linux内核镜像(linuxrom-s3c2440.bin)和根文件系统镜像(rootfs-jffs2.bin),此外还要通过bootargs环境变量告诉Linux内核根文件系统所在的位置。这里Linux内核、根文件系统的烧录地址、bootargs传参应该与Linux内核里的Nandflash分区表相一致

    u-boot的烧录地址应该是 0,大小不超过1M。该分区对应Linux内核分区表的/dev/mtdblock0;

    Linux内核的烧录地址应该是0x100000(1M的偏移量处),大小不超过15M。该分区对应Linux内核分区表的/dev/mtdblock1;

    根文件系统镜像的烧录地址应该是0x1000000(16M的偏移量处),大小不超过40M。该分区对应Linux内核分区表的/dev/mtdblock2;

烧录命令:

tftp 30008000 linuxrom-s3c2440.bin     先将Linux内核下载到内存地址30008000上去

nand erase 100000 F00000               将Nandflash上Linux内核分区(即1M开始总共15M的空间)全部擦除

nand write 30008000 100000 400000      将Linux内核写入到Nandflash上的Linux内核分区上去

tftp 30008000 rootfs-jffs2.bin         先将根文件系统下载到内存地址30008000上去

nand erase 1000000 2800000             将Nandflash上根文件系统分区(即16M开始总共40M的空间)全部擦除

nand write 30008000 1000000 $filesize  将根文件系统写入到Nandflash上的根文件系统分区上去

u-boot设置烧录快捷方式

set blx 'tftp 30008000 linuxrom-s3c2440.bin;nand erase 100000 F00000;nand write 30008000 100000 400000'

 

set bjffs2 'tftp 30008000 rootfs-jffs2.bin;nand erase 1000000

2800000;nand write 30008000 1000000 $filesize'

以后我们在u-boot里想烧录根文件系统和Linux内核时,可以直接使用run blx 或 run bjffs2 命令完成

设置bootcmd和bootargs参数:

开发板上电或重启运行u-boot时,如果不按任意键u-boot将进入正常加载模式,这时他将读取环境变量bootcmd来启动引导Linux内核。Linux内核是被烧录到Nandflash的0x100000位置上,所以uboot启动系统需要从该位置读取内核文件到内存相应位置中去,并且读取字节数应该不小于烧录的Linux镜像文件大小,否则系统将启动失败。根文件系统则通过bootargs参数告诉Linux内核,Linux内核在启动后根据该参数挂载相应的根文件系统,如果bootargs参数出错也将导致系统启动失败。如图:

set bootcmd 'nand read 30008000 100000 400000; bootm 30008000

set bootargs 'console=tty0 console=ttyS0,115200  root=/dev/mtdblock2 rootfstype=jffs2 init=/linuxrc mem=64M rw noinitrd loglevel=7'

 

bootargs的参数解析如下:

console=tty0 指定内核控制终端为LCD,内核启动信息输出到LCD上;

console=ttyS0,115200 指定内核控制终端也为第一个串口,使用波特率115200,这样内核启动信息也打印到第一个串口上;

root=/dev/mtdblock2 指定根文件系统存放在mtdblock2上,该值应该与u-boot烧录位置、Linux内核分区保持一致;如果错误则Linux内核会因找不到根文件系统而启动失败;

rootfstype=jffs2 指定根文件系统类型为jffs2,如果该参数错误则内核启动失败;

init=/linuxrc 指定init进程执行/linuxrc这个程序,他会解析并执行/etc/inittab下的命令;

mem=64M u-boot告诉Linux内核有64M的内存;

rw 根文件系统以读写的形式挂载;

noinitrd 没有使用initrd;

loglevel=7 定义内核printk的打印级别为7,即所有信息都通过console打印出来;

烧录过程

run blx     烧录Linux内核镜像

run bjffs2

这里写终止的地址根据文件的大小而不同

4.5 启动和登录测试:

boot   直接使用boot命令启动,或重启开发板将自动启动

登录测试:

因为JFFS2是建立在Nandflash上的根文件系统,在该文件系统路径下所有的文件修改掉电后都不会丢

失。所以我们在根路径下创建haha文件后,把开发板重启发现该文件还存在。

4.6 普通分区jffs2挂载

jffs2除了可以制作成根文件系统使用以外,我们也可以在系统成功启动后,将其他分区以jffs2文件系统类型挂载使用。

dmesg | grep mtdblock 通过dmesg命令查看内核的分区情况

cat /proc/partitions 查看Linux内核分区表

ls -l /dev/mtdblock* 查看分区对应的块设备

这里我们以 mtdblock5 为例将其以jffs2文件系统格式挂载到 /info 挂载点上:

flash_eraseall /dev/mtd5 将mtdblock5分区全部擦除

这里出现了错误,找不到flash_eraseall,这是因为我在编译busybox时没有选中这个命令选项。如图:

将这个选项选上即可。

再运行命令:

flash_eraseall /dev/mtd5

mount -t jffs2 /dev/mtdblock5 /info/

mount

系统重启后,并不会自动挂载/dev/mtdblock5到/info路径下,这时我们还是需要用命令手动挂载才能看到/info路径下的haha文件存在。

我们知道,,Linux系统启动的最后启动init进程,而读init进程就是根据/etc/inittab这个文件来在不同的运行级别启动相应的进程或执行相应的操作,所以我们只需要将挂载操作写进inittab文件里面即可。

通过系统文件提供的信息,我们找到了fstab文件

cat /etc/fstab

我们在fstab里面将/dev/mtdblock5添加挂载进去,重启挂载就可以了

这种方式不能实现mtdblock的挂载,因为第一次执行mount-a挂载的时候由于/dev目录下面还没有设备文件生成,所以执行挂载/dev/mtdblock2会提示 No such file or directory,执行完第一次mount -a后,由于/dev 目录已经挂载ramfs,再调用/sbin/mdev -s自动生成设备文件,此时才会存在/dev/mtdblock2,生成/dev/mtdblock2设备文件后再次调用,mount -a或者直接mount才会成功。

建议在inittab文件中加入如下一行:

null::wait:/bin/mount -t jffs2 /dev/mtdblock2 /mnt

未添加之前

添加后:

五、ubifs根文件系统制作

5.1 ubifs文件系统简介

UBIFS(Unsorted Block Image File System,无排序区块图像文件系统)是用于固态存储设备上,并与LogFS相互竞争,作为JFFS2的后继文件系统之一。由于Nand Flash容量的暴涨,JFFS2、Yaffs2等皆无法操控大的Nand Flash空间,IBM、Nokia工程师Thomas Gleixner、Artem Bityutskiy等人2006年发起,致力于开发性能卓越、扩展性高的FLASH专用文件系统,以解决嵌入式环境下以FLASH作为MTD设备使用时的技术瓶颈。真正开始开发于2007年,并于2008年10月第一次加入稳定版本于Linux核心2.6.27版,在设计与性能上均较优于YAFFS2、JFFS2,更实用于MLC NAND FLASH。因为UBIFS是直接工作在Raw Flash设备上(如Nandflash),所以他不能工作在SD卡、U盘这些常用的存储设备上,目前的安卓手机上绝大部分都是使用的UBIFS文件系统。关于UBIFS的更多信息请参考: http://www.linux-mtd.infradead.org/doc/ubifs.html

传统的flash文件系统如Jffs2、yaffs2等是工作在MTD设备层之上,而UBIFS则建立在UBI卷层之上,UBI卷层工作在MTD设备层之上。也可以说,UBIFS涉及三个子系统

    MTD 子系统,提供对flash芯片Raw的访问接口。 MTD子系统提供了MTD device的概念,比如/dev/mtdx(字符设备)和/dev/mtdblockX(块设备);

    UBI Subsystem,它工作在MTD设备之上,提供了UBI逻辑卷(类似于Linux服务器上的LVM概念),对上层屏蔽了一些直接使用MTD设备需要处理的问题,如wear-leveling(磨损平衡算法)和volume management(坏块管理)功能等;

    UBIFS文件系统,工作于UBI之上。它提供文件的open、read、write等操作;

作为新一代文件系统新贵,他具有如下特性:

    可扩展性: UBIFS对Flash 尺寸有着很好的扩展性; 也就是说文件系统挂载时间,内存消耗以及I/O速度都不依赖于Flash的大小; UBIFS可以很好的运行在GB级的 flashe设备; 当然UBI本身还是有扩展性的问题,无论如何 UBI/UBIFS都比JFFS2的可扩展性好,如果UBI成为瓶颈,可以改进UBI而不需改变UBIFS本身;

    快速挂载:不像JFFS2,UBIFS在挂载阶段不需要扫描整个文件系统,UBIFS mount的时间只是毫秒级,时间不依赖于Flash的大小;然而UBI的初始化时间依赖Flash的大小,因此必须把这个时间考虑在内。

    write-back 支持:文件的改变并不是立刻提交到flash media上,而是cache这些修改,直到达到写入的条件,这减少了I/O的数目因此改善I/O性能和系统性能。回写本身也是文件系统的标准技术,由于数据没有立刻写入flash, 回写带来了突然掉电就会存在数据丢失的风险。相反, JFFS2不支持write-back, JFFS2文件系统的所有变化都是立刻同步到flash介质上。同JFFS2的writethrough(立即写入内存)相比可以显著的提高文件系统的吞吐量。

    容忍不清洁的重启:UBIFS是日志文件系统,所以容忍突然关闭和不清洁的重启。UBIFS会回放日志并从不切底的重启中恢复过来。这时挂载时间会有点慢。但由于只是需要重做日志,而不需要扫描储存介质,所以性能影响不大。

    快速I/O:即使回写功能被禁能(例如在挂载时加入“-o sync”的参数),UBIFS也表现良好,接近jffs2。在同步I/O方面UBIFS是极难与jffs2相抗争的。因为jffs2在flash维护数据索引结构,不需要额外的开销,而UBIFS需要。然而UBIFS依然是很快,因为它依靠日志。它不需要把数据物理地从一个地方移动到另一个地方,仅把有关信息加入文件系统的索引以及为新日志挑选一个擦除块。

    快速压缩:与jffs2相似,UBIFS支持数据压缩储存。对于单个文件的储存,UBIFS可以使能/禁能压缩功能。

    自恢复功能:有数据索引有损坏的情况下,UBIFS可以恢复过来。在UBIFS每一块信息有描述整个信息的数据头。在扫描介质的情况下这数据头信息可以重建。而在FAT文件系统,发生这样的事件是致命的。

    数据的完整性:UBIFS在每次写入数据时都会对数据进行核实,以确保数据的完整性。UBIFS不会容忍任何不可用的数据或元数据。然而为了加快数据的读写速度,用户可以关闭CRC检查。

5.2 根文件系统镜像文件制作

我们可以使用mtd-utils源码编译出来的mkfs.jffs2工具,将根文件系统树目录制作成jffs2根文件系统镜

像。在开始制作镜像之前,我们先看看mkfs.jffs2的使用说明:

mkfs.ubifs -h

Usage: mkfs.ubifs [OPTIONS] target

Make a UBIFS file system image from an existing directory tree

Examples:

Build file system from directory /opt/img, writting the result in the ubifs.img

file

mkfs.ubifs -m 512 -e 128KiB -c 100 -r /opt/img ubifs.img

The same, but writting directly to an UBI volume

mkfs.ubifs -r /opt/img /dev/ubi0_0

Creating an empty UBIFS filesystem on an UBI volume

mkfs.ubifs /dev/ubi0_0

Options:

-r, -d, --root=DIR build file system from directory DIR, 指定根文件系统目录

树的路径

-m, --min-io-size=SIZE minimum I/O unit size Nand Flash的最小读写单元,一般为page size。

-e, --leb-size=SIZE logical erase block size 逻辑擦除块的大小

-c, --max-leb-cnt=COUNT maximum logical erase block count 逻辑擦除块的个数,与分区大小有关

-o, --output=FILE output to FILE 输出的根文件系统镜像文件

-j, --jrn-size=SIZE journal size

-R, --reserved=SIZE how much space should be reserved for the super-user

-x, --compr=TYPE compression type - "lzo", "favor_lzo", "zlib" or

"none" (default: "lzo")

-X, --favor-percent may only be used with favor LZO compression and defines

how many percent better zlib should compress to make

mkfs.ubifs use zlib instead of LZO (default 20%)

-f, --fanout=NUM fanout NUM (default: 8)

-F, --space-fixup file-system free space has to be fixed up on first mount

(requires kernel version 3.0 or greater)

-k, --keyhash=TYPE key hash type - "r5" or "test" (default: "r5")

-p, --orph-lebs=COUNT count of erase blocks for orphans (default: 1)

-D, --devtable=FILE use device table FILE

-U, --squash-uids squash owners making all files owned by root

-l, --log-lebs=COUNT count of erase blocks for the log (used only for

debugging)

-y, --yes assume the answer is "yes" for all questions

-v, --verbose verbose operation

-V, --version display version information

-g, --debug=LEVEL display debug information (0 - none, 1 - statistics,

2 - files, 3 - more details)

-h, --help display this help text

Note, SIZE is specified in bytes, but it may also be specified in Kilobytes,

Megabytes, and Gigabytes if a KiB, MiB, or GiB suffix is used.

If you specify "lzo" or "zlib" compressors, mkfs.ubifs will use this compressor

for all data. The "none" disables any data compression. The "favor_lzo" is not

really a separate compressor. It is just a method of combining "lzo" and "zlib"

compressors. Namely, mkfs.ubifs tries to compress data with both "lzo" and "zlib"

compressors, then it compares which compressor is better. If "zlib" compresses 20

or more percent better than "lzo", mkfs.ubifs chooses "lzo", otherwise it chooses

"zlib". The "--favor-percent" may specify arbitrary threshold instead of the

default 20%.

The -F parameter is used to set the "fix up free space" flag in the superblock,

which forces UBIFS to "fixup" all the free space which it is going to use. This

option is useful to work-around the problem of double free space programming: if

the

flasher program which flashes the UBI image is unable to skip NAND pages

containing

only 0xFF bytes, the effect is that some NAND pages are written to twice - first

time

when flashing the image and the second time when UBIFS is mounted and writes

useful

data there. A proper UBI-aware flasher should skip such NAND pages, though. Note,

this

flag may make the first mount very slow, because the "free space fixup" procedure

takes time. This feature is supported by the Linux kernel starting from version

3.0.

mkfs.ubifs -x lzo -m 2048 -e 129024 -c 300 -r ./rootfs -o rootfs-ubifs.img

    -x lzo   指定使用lzo压缩方法,默认lzo,还支持zlib,zlib压缩率高些,但是lzo压缩解压缩快。

     

    -m 2048 Nand Flash的最小读写单元,一般为page size,K9F2G08的页大小为2048字节

    -r ./rootfs 指定根文件系统目录树的路径

    -o rootfs-ubifs.img  指定制作出的根文件系统镜像文件名

    -e 129024   指定LEB(Logical Erase Block,逻辑擦除块)大小。大家知道 Nandflash读写单位为页,擦除单位为块,一个设备有多个块,一个块有多个页,K9F2G08  Nandflash一个块是64个页,而一个页大小为2048字节。这样一个PEB(Physical Eraseblock  Size,物理擦除块)大小就是2048*64=131072,-e的算法是物理擦除块大小-1*页大小,这里 就是131072-1*2048=129024

     

    -c 300   指定该分区最大逻辑擦除块数量,该值随着根文件系统分区的大小和该分区的坏块数调整。该值很重要,不能大也不能小,太小也要大于image大小,太大mount有问题。计算起点是分区的物理块数量,比如40MiB的mtd分区,物理擦除块数量是40*1024*1024/2048/64 = 320个,需要减去2个volume table的块,1个wear-leveling块,1个atomic LEB change块,以及一些坏块处理的保留块。因为一个分区上有多少个坏块是随机的,一般做法是做一个坏块容忍数,比如16个,不要担心这个会浪费空间,ubinize的autoresize选项就是解决这个问题的。在这里我们最终的逻辑擦除块个数计算公式为: 320-

    2(volume table)-1(Wear-leveling)-1(atomic LEB change)-16(坏块容量数)=300

    UBIFS官方关于逻辑擦除块大小的说明

    参考: http://www.linux-mtd.infradead.org/doc/ubi.html#L_overhead

UBIFS是建立在UBI之上的文件系统,因此使用mkfs.ubifs制作的根文件系统镜像不能直接使用u-boot

的nand write命令烧录,而需要在u-boot下使用ubi命令在根文件系统所在分区建立ubi卷之后才能烧

录。但这种烧录方式比较麻烦,这时我们可以使用另外ubinize命令对rootfs-ubifs.img文件进行处理后

就可以在u-boot上直接用nand write命令写入到根文件系统分区了。该命令的使用方法如下:

ubinize -h

 

-o, --output=   output file name处理后输出的镜像文件名

-p, --peb-size= size of the physical eraseblock of the flash物理擦除块大小this UBI image is created for in this UBI image is created for in bytes, kilobytes (KiB), or megabytes (MiB) (mandatory parameter)

-m, --min-io-size=      minimum input/output unit size of the flashnandflash页大小  in bytes

-s, --sub-page-size=   minimum input/output unit used for UBI headers, e.g. sub-page size in case of NAND flash (equivalent to the minimum input/output unit size by default)

-O, --vid-hdr-offset=   offset if the VID header from start of the  physical eraseblock (default is the next  minimum I/O unit or sub-page after the EC  header)

-e, --erase-counter=    the erase counter value to put to EC headers  (default is 0)

-x, --ubi-ver=               UBI version number to put to EC headers  (default is 1)

-v, --verbose                             be verbose

-h, --help                                  print help message

-V, --version                             print program version

vim ubinize.ini

[ubifs-volume]

mode=ubi

image=rootfs-ubifs.img      指定mkfs.ubifs制作生成的根文件系统镜像文件路径;

vol_id=0                               指定根文件系统树的卷标为0,u-boot的bootargs参数需要根据它来设置;

vol_size=38707200              指定该UBI逻辑卷的大小,该值计算公式一般为 逻辑擦除块大小*逻辑擦除块个数 =129024*300=38707200。该值一般不用写,默认值是image大小。写了这个作用是帮助检查image是否超过了 分区限制,制作时候就提示,否则mount会出错。逻辑擦除块个数的值是经过计算的最大值了,不过autoresize 参数会自适应大小,不会浪费空间的,后面Linux系统内核启动过程中可以看到这个现象。

vol_type=dynamic                

vol_name=rootfs                 

vol_flags=autoresize           指定UBI卷的名称,u-boot的bootargs参数需要根据它来设置;   

vol_alignment=1                 

UBI Subsystem                    在系统启动时自动调整逻辑擦除块的个数

ubinize -o rootfs-ubifs.bin -m 2048 -p 131072 -s 512 -O 512  ubinize.ini

    o rootfs-ubifs.bin        指定ubinize处理后输出的image文件名,该文件可以由u-boot的nand write命令

    直接烧录

     

    -m 2048                      指定minimum input/output unit大小,为nandflash的页大小。

    -p 131072                   指定物理擦除块大小: 64 Page*2048 Byte/Page = 131072

     

    -s 512                         指定sub-page-size大小,页大小为2048字节的nandflash对应值为512;对于其他的 Nandflash可以在Linux内核跑起来后挂载ubifs后查看该值

     

    -O 512                        指定vid-hdr-offset值,默认为sub-page-size的值,可以省略不用。

du -h rootfs-ubifs.bin

 

7.7M    rootfs-ubifs.bin

经过 ubinize 命令处理过后的根文件系统镜像文件 rootfs-ubifs.bin 就可以直接在u-boot下使用nand write 命令烧录到相应的根文件系统分区上去了。

关于Minim Flash input/output、sub-pages、UBI Header的说明

参考: http://www.linux-mtd.infradead.org/doc/ubi.html#L_min_io_unit

5.3 内核配置和编译

Linux内核需要重新make menuconfig配置做如下修改,编译并生成的Linux内核镜像文件才能支持UBIFS文件系统。

cd fl2440/linux/linux-3.0

export TERM=vt100

make menuconfig

General setup --->

            [ ] Initial RAM filesystem and RAM disk (initramfs/initrd) support 一定要取消initamfs,否则内核找到initramfs根文件系统的话就直接使用他启动了。

Device Drivers --->

           <*> Memory Technology Device (MTD) support --->

           < > RedBoot partition table parsing

           < > FTL (Flash Translation Layer) support

           < > NFTL (NAND Flash Translation Layer) support

           <*> Enable UBI - Unsorted block images ---> 因为UBIFS文

件系统建立在UBI一层上,所以只有这里选择了UBI之后,下面的文件系统里才会有UBIFS的选项

                                                                            (4096) UBI wear-leveling threshold (NEW)

                                                                            (1) Percentage of reserved eraseblocks for bad

eraseblocks handling (NEW)

                                                                            < > MTD devices emulation driver (gluebi) (NEW)

                                                                            [ ] UBI debugging (NEW)

File systems --->

                [*] Miscellaneous filesystems --->

               <*> UBIFS file system support 选择支持UBIFS文件系统

                                        [*] Extended attributes support

                                        [*] Advanced compression options

                                        [*] LZO compression support (NEW)

                                        [*] ZLIB compression support (NEW)

                                        [ ] Enabe debugging support (NEW)

重新编译生成 linuxrom-s3c2440.bin

5.4 u-boot系统烧录和环境变量配置

因为使用UBIFS根文件系统启动的Linux内核不包含根文件系统,所以u-boot烧录Linux系统时需要

同时烧录linux内核镜像(linuxrom-s3c2440.bin)和根文件系统镜像(rootfs-ubifs.bin),此外还要通过

bootargs环境变量告诉Linux内核根文件系统所在的位置。这里Linux内核、根文件系统的烧录地址、

bootargs传参应该与Linux内核里的Nandflash分区表相一致:

    u-boot的烧录地址应该是 0,大小不超过1M。该分区对应Linux内核分区表的/dev/mtdblock0;

    Linux内核的烧录地址应该是0x100000(1M的偏移量处),大小不超过15M。该分区对应Linux内核分区表的/dev/mtdblock1;

    根文件系统镜像的烧录地址应该是0x1000000(16M的偏移量处),大小不超过40M。该分区对应Linux内核分区表的/dev/mtdblock2;

开发板上电或重启运行u-boot时,如果不按任意键u-boot将进入正常加载模式,这时他将读取环境变量bootcmd来启动引导Linux内核。Linux内核是被烧录到Nandflash的0x100000位置上,所以uboot启动系统需要从该位置读取内核文件到内存相应位置中去,并且读取字节数应该不小于烧录的Linux镜像文件大小,否则系统将启动失败。根文件系统则通过bootargs参数告诉Linux内核,Linux内核在启动后根据该参数挂载相应的根文件系统,如果bootargs参数出错也将导致系统启动失败。

set bootcmd 'nand read 30008000 100000 400000; bootm 30008000'

set blx 'tftp 30008000 linux-s3c2440.bin;nand erase 100000  F00000;nand write 30008000 100000 400000'

(前面设置过就忽略掉)

set bubifs 'tftp 30008000 rootfs-ubifs.bin;nand erase 1000000  2800000;nand write 30008000 1000000 $filesize'

set bootargs 'console=tty0 console=ttyS0,115200 ubi.mtd=2  root=ubi0:rootfs rootfstype=ubifs mem=64M noinitrd rw loglevel=7' /*注意这里要设置rootfstype的类型,因为前面我们设置的rootfstype类型是jiffs的,没改变话,开发板会一直刷新,ubi.mtd=2  root=ubi0:rootfs rootfstype=ubifs这句话表示在mtdblock2上建立了ubi的卷标0,它的名字是rootfs,文件类型是ubifs*/

save

run blx 烧录Linux内核镜像

run bubifs 烧录根文件系统镜像

5.5 启动和登录测试

boot 直接使用boot命令启动,或重启开发板将自动启动

出现了前面jiffs2没有填充一直刷屏的问题

Empty flash at 0x0035eabc ends at 0x0035eac0

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360000: 0x4255 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360004: 0x0001 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360018: 0x1927 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x0036003c: 0x3de4 instead

Empty flash at 0x00360040 ends at 0x00360200

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360200: 0x4255 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360204: 0x0101 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x0036023c: 0x0df5 instead

Empty flash at 0x00360240 ends at 0x00360800

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360800: 0x1831 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360804: 0xdad2 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00360808: 0x0391 instead

Further such events for this erase block will not be printed

Empty flash at 0x00361dc4 ends at 0x00361dc8

Empty flash at 0x003638ec ends at 0x003638f0

Empty flash at 0x00365964 ends at 0x00365968

Empty flash at 0x00366d9c ends at 0x00366da0

Empty flash at 0x003677b4 ends at 0x003677b8

Empty flash at 0x003681f4 ends at 0x003681f8

Empty flash at 0x00368cc4 ends at 0x00368cc8

Empty flash at 0x003697dc ends at 0x003697e0

Empty flash at 0x0036a2a4 ends at 0x0036a2a8

Empty flash at 0x0036ad1c ends at 0x0036ad20

Empty flash at 0x0036cf7c ends at 0x0036cf80

Empty flash at 0x0036dc34 ends at 0x0036dc38

Empty flash at 0x0036ea1c ends at 0x0036ea20

Empty flash at 0x00370294 ends at 0x00370298

Empty flash at 0x00370b5c ends at 0x00370b60

Empty flash at 0x00371534 ends at 0x00371538

Empty flash at 0x00373414 ends at 0x00373418

Empty flash at 0x00375c0c ends at 0x00375c10

Empty flash at 0x003785bc ends at 0x003785c0

Empty flash at 0x0037adbc ends at 0x0037adc0

Empty flash at 0x0037b74c ends at 0x0037b750

Empty flash at 0x0037c114 ends at 0x0037c118

Empty flash at 0x0037df2c ends at 0x0037df30

Empty flash at 0x0037e9bc ends at 0x0037e9c0

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380000: 0x4255 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380004: 0x0001 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380018: 0x1927 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x0038003c: 0x3de4 instead

Empty flash at 0x00380040 ends at 0x00380200

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380200: 0x4255 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380204: 0x0101 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x0038023c: 0xc6ca instead

Empty flash at 0x00380240 ends at 0x00380800

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380800: 0x1831 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380804: 0x65d5 instead

jffs2_scan_eraseblock(): Magic bitmask 0x1985 not found at 0x00380808: 0x03bd instead

Further such events for this erase block will not be printed

Empty flash at 0x00382fec ends at 0x00382ff0

Empty flash at 0x00384354 ends at 0x00384358

Empty flash at 0x00384ebc ends at 0x00384ec0

Empty flash at 0x003866c4 ends at 0x003866c8

这是因为我在inittab中添加了一项

null::wait:/bin/mount -t jffs2 /dev/mtdblock2 /mnt

导致我每次烧录ubifs与挂载的根文件jffs2的根文件冲突,因为我将jffs2系统挂载到了根文件下,所以导致ubifs出

错。

但是我将那据删除以后还是存在上述问题,于是将3008000内存里的内容删除nanderase 30008000,文件系统烧录成功。这里有两种原因:一我们在内核里对分区重新做了调整,因此必须将相关联的分区格式化,否则就会出错;二:文件系统类型的改变也一定要擦除分区,否则新的文件系统烧录不进去。

将文件系统下载到开发板的文件夹下,然后在inittab下添加代码挂载,(ubifs 又该如何挂载,后面再解释)

null::wait:/bin/mount -t jffs2 /dev/mtdblock2 /mnt  //参照修改
————————————————
版权声明:本文为CSDN博主「@遇见O_o」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/buhuiguowang/article/details/79942084

你可能感兴趣的:(Linux——根文件系统的制作(jffs2 and ubifs))