4. 常见嵌入式文件系统类型

在嵌入式 Linux 系统中,根文件系统(rootfs)并不是“随便选一个能挂载的格式”即可。不同存储介质(NOR/NAND/eMMC/SD/DRAM)、不同读写需求(只读、频繁写、掉电保护)、不同启动阶段(initramfs 先起、再切到真实 rootfs)都会直接影响文件系统选型。本节把常见类型放在同一张“介质—特性—场景”坐标系里对比,帮助你建立可落地的选型依据。

一、核心原理:先看介质,再看读写模型

嵌入式文件系统大致分为三类:块设备型(ext4、squashfs、initramfs/tmpfs 在内存中)、裸 NAND/NOR 型(jffs2、ubifs、yaffs2)。块设备型依赖通用块层与页缓存,适合 eMMC/SD/UFS;裸闪存型直接管理擦除块、坏块与磨损均衡,适合 SPI NOR 与 NAND。

关键差异在于:是否支持原地写、是否有日志/日志结构、是否压缩、是否可写、是否依赖 MTD 子系统。例如 squashfs 是只读压缩文件系统,适合固化 rootfs;ubifs 是 NAND 上的日志结构文件系统,支持压缩与掉电一致性;tmpfs 完全驻留内存,掉电即失,适合 /tmp、/run 等临时目录。

嵌入式文件系统选型坐标:介质 × 读写 × 可靠性 存储介质 SPI NOR 小容量、可 XIP NAND 坏块、需 ECC eMMC / SD 块设备、大容量 DRAM 内存盘、易失 文件系统类型 ext4 日志、可读写、通用 squashfs 只读、高压缩 jffs2 NOR/NAND、日志结构 ubifs NAND、压缩、UBI yaffs2 NAND、日志结构 initramfs 内存、早期启动 tmpfs 内存、临时、掉电即失 典型场景 eMMC 根文件系统 ext4 固件只读 rootfs squashfs NAND 可写分区 ubifs / jffs2 早期挂载与救援 initramfs /tmp、/run tmpfs

二、方法流程:从需求到选型的四步判断

  1. 确定介质类型:eMMC/SD 走块设备路线,优先 ext4;SPI NOR/NAND 走 MTD 路线,优先 jffs2/ubifs/yaffs2。
  2. 确定读写属性:只读固件用 squashfs;需要频繁写且要求掉电一致性,用 ubifs 或 ext4(带 journal)。
  3. 确定容量与压缩需求:容量紧张时 squashfs/ubifs 的压缩能显著节省空间;ext4 不压缩。
  4. 确定启动阶段:内核早期需要先挂一个最小根,用 initramfs;随后 switch_root 到真实 rootfs。
选型口诀:块设备看 ext4,只读压缩看 squashfs,NAND 可写看 ubifs,老平台 NOR 看 jffs2,内存临时看 tmpfs,早期启动看 initramfs。

三、案例/场景:典型组合与命令

场景 A:i.MX6 + eMMC,系统分区只读、数据分区可写。常见做法是 rootfs 用 squashfs 或 ext4,数据分区用 ext4。挂载示例:

# 只读挂载 squashfs 根
mount -t squashfs -o ro /dev/mmcblk0p2 /mnt/rootfs

# 可写数据分区
mount -t ext4 -o rw,noatime /dev/mmcblk0p3 /data

# 查看当前文件系统类型
df -T
cat /proc/mounts

场景 B:SPI NAND 上保存配置与日志。使用 ubifs 前需先做 UBI 镜像:

mkfs.ubifs -r rootfs -m 2048 -e 126976 -c 2048 -o rootfs.ubifs
ubinize -o rootfs.ubi -m 2048 -p 128KiB ubinize.cfg
# ubinize.cfg 中 volume 类型可设为 static 或 dynamic

场景 C:initramfs 作为早期根,负责加载驱动并挂载真实 rootfs:

# 内核配置
CONFIG_BLK_DEV_INITRD=y
CONFIG_INITRAMFS_SOURCE="initramfs.cpio.gz"
# 启动后 switch_root
switch_root /newroot /sbin/init

四、对比清单与误区复盘

类型介质可写压缩掉电一致性典型用途
ext4eMMC/SD是否日志,较好通用根/数据分区
squashfs块设备/MTD否是只读,天然安全只读固件 rootfs
jffs2NOR/NAND是是日志结构,较好小容量 NOR 配置区
ubifsNAND是是日志结构 + UBI,好NAND 可写分区
yaffs2NAND是否日志结构,较好老 NAND 平台
initramfsDRAM是(内存)是(cpio 压缩)掉电即失早期启动、救援
tmpfsDRAM是否掉电即失/tmp、/run、/dev/shm
常见误区:把 ext4 直接用在裸 NAND 上。裸 NAND 有坏块和擦除块限制,必须经过 MTD/UBI 转换层,否则会快速损坏。另一个误区是把 tmpfs 当持久存储,重启后数据全部丢失。还有jffs2 用于大容量 NAND,挂载时间和内存占用会明显变差,此时应优先 ubifs。

复盘时建议按“介质 → 读写 → 容量 → 启动阶段”四步重新核对:如果 rootfs 只读且要省空间,squashfs 往往优于 ext4;如果数据分区需要频繁写且介质是 NAND,ubifs 比 jffs2 更合适;如果只是临时文件,tmpfs 最轻量。选型没有绝对最优,只有与硬件、启动流程和可靠性目标最匹配的组合。