1、quick notes

littlefs是block-based文件系统。flash被划分成多个相同大小的block
block pointer是32bits,0xFFFFFFFF表示空指针
除了逻辑block size(通常是erase block size),littlefs还有program block size和read block size,后面两个block size主要是用于flash 读写时的对齐
littlefs采用little-endian order

2、Directories/Metadata pairs

metadata pair是littlefs的基石,提供了原子更新的能力。superblock也是存储在metadata pair中。metadata pair存储在两个block中,一个block在另一个block erase的时候提供备份。同一个metadata pair中的两个block并不要求是连续的,可以分散在不同的位置,通过指针链接。

每一个metadata block类似于一个可以追加的log,包含多个commit。commit可以按照顺序追加到metadata block中而不需要erase操作。同时,后续的commit可以取代旧的commit,只有最新的commit才被认为是有效的。

每个metadata block包含一个32-bit的revision count,后面跟着多个commit。每个commit包含一个或多个entry,每个commit的最后是32-bit的CRC。entry不一定是word-aligned。但是每个commit都是program block size对齐的,因此commit与commit之间可能存在padding。

metadata block的主要域:

1)revision count:32bit长。每擦除一次就增加1,如果两个metadata block都包含有效的数据,则使用最新的revision count所在的block。

2)CRC:32bit长。使用0x04c11db7多项式,初始值为0xFFFFFFFF。

3)entry:每个entry以32-bit的tag开始,后面跟着可变长度的数据。

metadata block支持前向和后向的迭代。为了减少重复空间,相邻entry的tag通过XOR连接起来,初始值是0xffffffff。

每个entry中还包含一个valid bit用于指示当前entry和commit有效。

下图是包含4个entry的block。

  .---------------------------------------.
.-|  revision count   |      tag ~A       |        \
| |-------------------+-------------------|        |
| |                 data A                |        |
| |                                       |        |
| |-------------------+-------------------|        |
| |      tag AxB      |       data B      | <--.   |
| |-------------------+                   |    |   |
| |                                       |    |   +-- 1st commit
| |         +-------------------+---------|    |   |
| |         |      tag BxC      |         | <-.|   |
| |---------+-------------------+         |   ||   |
| |                 data C                |   ||   |
| |                                       |   ||   |
| |-------------------+-------------------|   ||   |
| |     tag CxCRC     |        CRC        |   ||   /
| |-------------------+-------------------|   ||
| |     tag CRCxA'    |      data A'      |   ||   \
| |-------------------+                   |   ||   |
| |                                       |   ||   |
| |              +-------------------+----|   ||   +-- 2nd commit
| |              |     tag CRCxA'    |    |   ||   |
| |--------------+-------------------+----|   ||   |
| | CRC          |        padding         |   ||   /
| |--------------+----+-------------------|   ||
| |     tag CRCxA''   |      data A''     | <---.  \
| |-------------------+                   |   |||  |
| |                                       |   |||  |
| |         +-------------------+---------|   |||  |
| |         |     tag A''xD     |         | < |||  |
| |---------+-------------------+         |  ||||  +-- 3rd commit
| |                data D                 |  ||||  |
| |                             +---------|  ||||  |
| |                             |   tag Dx|  ||||  |
| |---------+-------------------+---------|  ||||  |
| |CRC      |        CRC        |         |  ||||  /
| |---------+-------------------+         |  ||||
| |           unwritten storage           |  ||||  more commits
| |                                       |  ||||       |
| |                                       |  ||||       v
| |                                       |  ||||
| |                                       |  ||||
| '---------------------------------------'  ||||
'---------------------------------------'    |||'- most recent A||'-- most recent B|'--- most recent C'---- most recent D

从上图中可以看出,第一个entry的tag是本entry的原始tag和0xFFFFFFFF进行XOR计算的结果。每个commit的最后一个entry是CRC,包含前一个entry的tag与CRC进行XOR计算的结果,例如1st commit中的entry C之后有tag CxCRC。

3、metadata tag

在littlefs中,32-bit的tag代表了所有的metadata类型,包含file entry, directory, global state和CRC。

32-bit的tag格式如上图。32-bit的tag是按照big-endian存储的。这也是littlefs中唯一按照big-endian存储的数据结构。主要是因为valid bit必须是commit的第一个bit,按照big-endian存储会简化代码。0x00000000和0xffffffff都是非法的tag。metadata tag各个域的详细解释如下:

1)valid bit(1-bit):指示tag是否valid

2)type3(11-bits):tag的类型。11bit又分为3bit的type1,又叫abstract type和8bit的chunk。0x000是非法的type

3)type1(3-bit):又叫abstract type

4)chunk(8-bits)和前面的abstract type组合表示多种不同的含义。type1+chunk+id组成一个唯一的id。

5)id(10-bits):metadata block中的每个文件都有一个唯一的id用于连接文件和tag。0x3ff用来表示不和文件关联的tag,比如目录和global metadata

6)length(10-bits):data的长度,0x3ff表示这个tag被删除

4、metadata type

1)0x401 LFS_TYPE_CREATE

创建新文件时会使用这个id。但是inline file不需要这个tag。创建所做的全部工作就是移动使用此ID的任何文件。从这个意义上说,创建类似于插入虚构的文件数组中。

2)0x4ff LFS_TYPE_DELETE

删除文件时使用此id。和create相反,此标记将移至与该id相邻的任何文件,类似于从虚构的文件数组中删除。

3)0x0xx LFS_TYPE_NAME

使用此id关联文件名和文件类型。chunk域表格8-bit的文件类型。

name tag的域如下图:

a)file type(8-bits):文件类型

b)file name:文件名,ASCII字符串。

4)0x001 LFS_TYPE_REG

初始化id+name为普通文件。

5)0x002 LFS_TYPE_DIR

初始化id+name为目录。littlefs中目录是通过metadata pair链表的形式存储的,每个pair都包含任意数量的文件,文件按照字母顺序排列。一个指向目录的指针存储在tag结构中。

6)0x0ff LFS_TYPE_SUPERBLOCK

初始化id为superblock。super block存储右格式化的配置信息和文件系统识别信息。superblock entry是存储在block0和block1上的一个metadata pairs,并且最后一个通过metadata pair会重复一次作为根目录。

superblock entry的内容存储在type为superblock的name tag和inline tag里。name tag包含『littlefs』字符串,而inline tag包含版本和配置信息。name tag和inline tag的示意图如下:

各域的定义:

a)magic string(8-bytes):『littlefs』字符串

b)version(32-bits):高16 bit为主版本号,低16 bit为次版本号

c)block size(32-bits):logical block size

d)block count(32-bits):number of blocks

e)name max(32-bits):文件名的最大长度

f)file max(32-bits):文件的最大长度

g)attr max(32-bits):文件属性的最大长度

superblock必须是metadata pair的第一个entry(id 0),也必须是第一个写入到block的entry。这意味着superblock可以通过地址偏移的方式直接读取。

7)0x2xx LFS_TYPE_STRUCT

通过id来关联数据结构。数据结构的具体布局取决于数据结构的type(存储在chunk域)。

8)0x200 LFS_TYPE_DIRSTRUCT

目录数据结构。littlefs中目录是通过metadata pair链表的形式存储的,每个pair都包含任意数量的文件,文件按照字母顺序排列。

目录结构tag只包含指向本目录的第一个metadata pair的指针。目录的大小只能通过遍历获取。指向本目录另一个metadata pair的指针存储在tail tag中。目录tag的布局如下:

a)metadata pair(8-bytes):指向本目录的第一个metadata pair。

9)0x201 LFS_TYPE_INLINESTRUCT

inline结构。inline结构主要用于存储小文件。文件直接存储在metadata pair中。文件的数据存储在tag的data字段中。

a)inline data:直接存储在metadata pair的文件数据。

10)0x202 LFS_TYPE_CTZSTRUCT

CTZ skip-list结构。CTZ skip-list结构用来存储大文件。文件存储在反向的skip-list中,一个指针指向skip-list的head。通过skip-list head和文件size信息就足够读取文件了。skip-list的示意图:

对于skip-list可以简单描述如下:

一个block中指针的最大数量由文件的最大长度和block size确定。对于32 bits的文件长度,最小的block size是104 bytes。

CTZ tag的示意图如下:

a)file head(32 bits):指向位于skip-list的head的block

b)file size(32 bits):文件大小

11)0x3xx LFS_TYPE_USERATTR

用户属性结构。

user_attr各域:

a)attr type(8-bits):user attribute类型

b)attr data:user attribute数据

12)0x6xx LFS_TYPE_TAIL

metadata pair的tail指针。tail指针用来把所有的metadata pairs连接成链表。chunk域包含tail指针的类型。tail指针分为hardtail和softtail。

hardtail:下一个metadata pair属于当前目录

softtail:下一个metadata pair不属于当前目录,只是为了方便文件系统的遍历

通常,metadata pair列表包含所有的metadata pair。但是有些操作导致out of sync,比如掉电,这是『global state』中的sync标志置位。当sync标志置位时:

a)metadata pair链表可能包含孤儿目录

b)metadata pair链表中可能包含和bad block关联的metadata pair,而这个bad block已经被替换了

一旦发现sync被置位,线索链表必须进行校验,如果littlefs是只读的则可以不用。

tail tag 的布局:

各域:

a)tail type(8-bits):tail指针的类型

b)metadata pair(8-bytes):指向下一个metadata pair

13)0x600 LFS_TYPE_SOFTTAIL

softtail类型的tail结构,说明下一个metadata pair不属于当前目录,只有在文件系统遍历时才会使用。

14)0x601 LFS_TYPE_HARDTAIL

hardtail类型的tail结构,说明下一个metadata pair属于当前目录。在littlefs中,目录是按照字母顺序排列的,因此下一个metadata pair中包含的文件名只能比当前的要大。

15)0x7xx LFS_TYPE_GSTATE

『global state』结构。

『global state』的大小和格式依赖于type,type存储在chunk域。目前只支持MOVE STATE.

16)0x7ff LFS_TYPE_MOVESTATE

提供『global state』中的move state相关的delta结构。move state主要存储可能会导致文件系统out of sync的操作信息。比如在metadata pairs之间移动文件或者对metadata pair链表本身的操作。

对于move操作,move state包含tag+源metadata pair信息。如果tag不为0,说明在move的过程中可能发生可掉电或者复位,而文件存在于两个不同的位置。对于这种情况,源文件应该被删除。

对于metadata pair链表本身的操作,单独的sync标志用来指示修改,如果sync被置位,线索链表需要校验,

move state tag的布局:

各域:

a)sync bit(1-bit):指示metadata pair线索链表处于in-sync。如果sync被置位,则链表在使用前需要校验

b)move type(11-bits):move的类型。0x000表示没有任何move,0x4ff表示源文件需要删除,其他的值均非法

c)move id(10-bits):需要move的file id

d)metadata pair(8-bytes):指向含有move的metadata pair

17)0x5xx LFS_TYPE_CRC

crc tag。crc表示了commit的结束,同时也提供校验信息。

data字段的前32-bit包含crc32的值。crc32计算时使用的多项式是0x04c11db7,初值是0xffffffff。对于第一个commit,计算crc时会包含revision count。

crc tag的布局:

a)valid state(1-bit):指出下一个tag的valid bit的值。这样可以确保metadata block中未写入的区域会被识别为无效区域。

b)crc(32-bits)

c)padding:program size对齐
————————————————
版权声明:本文为CSDN博主「nstcl」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/nstcl/article/details/108077923

littlefs系列:Technical Specification相关推荐

  1. php 规格,PHP 设计模式系列之 specification规格模式_PHP

    Plus.php left = $left; $this->right = $right; } /** * 返回两种规格的逻辑与评估 * * @param Item $item * * @ret ...

  2. littlefs系列:重要的数据结构

    1.文件类型 // File types enum lfs_type {// file typesLFS_TYPE_REG = 0x001,LFS_TYPE_DIR = 0x002,// intern ...

  3. Lightweight Machine to Machine Technical Specification: Core(LwM2M 技术规范:核心)v1.1

    1.范围 本文档LwM2M CORE技术规范描述了LwM2M消息传递层. 随附规范LwM2M TRANSPORT规范[LwM2M-TRANSPORT]详细描述了消息传递层到所选传输的映射. 传输层和消 ...

  4. littlefs系列:Files

    1 文件的存储 从前面的分析知道CTZ skip-list是一种高效的数据存储方法,因此在metadata pair中存储右skip-list,metadata pair的作用类似于inode. 然而 ...

  5. hdu-----(4514)湫湫系列故事——设计风景线(树形DP+并查集)

    湫湫系列故事--设计风景线 Time Limit: 6000/3000 MS (Java/Others)    Memory Limit: 65535/32768 K (Java/Others) To ...

  6. 【腾讯第二届校园编程马拉松】HDU-4525,威威猫系列故事——吃鸡腿

    原题传送门:威威猫系列故事--吃鸡腿 题目如下(添加了部分陷阱提示,以加粗加下划线显示) Problem Description 威威猫不是一只普通的猫,普通的猫喜欢吃鱼,但威威猫最喜欢吃鸡腿.他每天 ...

  7. HDU 4502 吉哥系列故事——临时工计划(动态规划)

    吉哥系列故事--临时工计划                                                                                      T ...

  8. HDU 4505 小Q系列故事——电梯里的爱情

    小Q系列故事--电梯里的爱情                                                                                   Tim ...

  9. hdu 4501 小明系列故事——买年货 多重背包

    小明系列故事--买年货                                                                          Time Limit: 500 ...

最新文章

  1. Tile Racer — 3D 赛车游戏
  2. poj3259(SPFA算法)
  3. 7000更换控制器电源步骤_恒温恒湿试验箱几大故障的检查步骤及解决方法说明...
  4. 标记注解 java_【java】细说 JAVA中 标注 注解(annotation)
  5. EhCache复制:RMI与JGroups
  6. 项目管理学习 总结(一)
  7. DFS csu1719 Boggle
  8. origin画图初步入门
  9. tomcat热部署(springboot项目)
  10. linux 搭建文件服务器(vsftpd)
  11. PS长阴影生成工具 Long_Shadow_Generator_v1.2_for_CS6.zxp
  12. 明道云实现产品BOM清单的快速搭建
  13. 沉痛哀悼我们的电骡和BT中国联盟
  14. 关于Unity中unitypackage文件的图标显示及打开方式异常问题的解决
  15. python网易云_Python数据可视化:网易云音乐歌单
  16. PMP考试科目有什么?
  17. 产品经理之UED用户体验设计
  18. 数据分析(1):对比分析法
  19. CTF解题思路:图片隐写
  20. spin_lock 自旋锁

热门文章

  1. Cross Domian iFrame Exceptions 跨域iFrame屏蔽例外
  2. Unity3d shader 教程一 准备
  3. 计算机主机电池馈电,电脑主板电池没电了会出现什么情况?电脑主板电池没电的解决方法...
  4. 【未解决】蓝牙键盘,蓝牙鼠标,蓝牙音箱的冲突问题
  5. 诗词创作[2] 赠春
  6. wps怎么下载仿宋gb2312_仿宋gb2312字体
  7. vue请求拦截 给所有的api接口的请求 params 带上一个存储的值及qs的安装
  8. html 样式大全,2017最新css样式大全
  9. 人工智能这么火,你知道是谁创立的吗?
  10. 崩坏星穹铁道PC、安卓、iOS三端配置要求