EXT4inode分配策略

上传人:ali****an 文档编号:119066648 上传时间:2020-01-04 格式:PDF 页数:9 大小:563.95KB
返回 下载 相关 举报
EXT4inode分配策略_第1页
第1页 / 共9页
EXT4inode分配策略_第2页
第2页 / 共9页
EXT4inode分配策略_第3页
第3页 / 共9页
EXT4inode分配策略_第4页
第4页 / 共9页
EXT4inode分配策略_第5页
第5页 / 共9页
点击查看更多>>
资源描述

《EXT4inode分配策略》由会员分享,可在线阅读,更多相关《EXT4inode分配策略(9页珍藏版)》请在金锄头文库上搜索。

1、2016/10/10EXT4 inode 分配策略 http:/beanli.github.io/EXT4Inodeorlov/1/9 EXT4 inode EXT4 inode 分配策略 2016-04-18 | 分类 linux | 标签 linux 前言 EXT4文件系统的inode是非常多的,按照Inodes Per Block Group 4096而言,1T空间能提供出32M个inode左右,当我们创建一个目 录,或者创建一个文件时,EXT4会怎么选择inode呢? 在2002年发表的The Orlov block allocator一文中提到,影响文件系统性能的因素有很多,但是文件

2、在磁盘上的分布非常关键。有一 个总体的原则:相关的数据寻处位置相近。因为位置相近甚至连续,那么花在磁盘寻道上的时间机会少,从而提高性能。 但是实际情况下,还有一种特殊情况,对于文件系统的顶层目录,尽量要伸展开,分离开,否则顶层目录挤在一起,底层目录更 具局部性原理也挤在一起,最终就会导致文件系统,从远到近地线性展开,很多文件与其父目录的位置隔得很远,从而损坏性 能。 因此,一个很重要的原则是,顶层目录尽量在整个存储空间铺开,而目录树深处的目录相关的目录尽量靠近。这个原则是不难理 解的。Linux采用了一种叫做Orlov allocator的算法来负责选择inode的位置。该算法时由 Grigo

3、ry Orlov提出,在EXT2和EXT3 就开始 使用该算法,但是EXT4由于支持flex_bg,所以算法上也有了一点点变化或者变异 内核实现 对于EXT4文件系统,无论是创建文件(create),还是创建目录,还是创建软链接,都会牵扯到inode分配(如图所示)。茫茫无 数inode,到底选用那一个? 这个_ext4_new_inode是EXT4非常重要的一个函数,它的内容有400行之多,占据了fs/ext4/ialloc.c的四分之一以上的篇幅。本文重 点介绍选择inode分配给新的文件或目录的这个流程。 其实我们不难想到,由于EXT4支持flex block group这种战斗小组,选

4、择inode可以分解成3步 1. which flex block group 2. which block group 3. which inode 这些步骤中,第一步决定了目录是分散还是聚集在一起。文件和目录的规则是不同的: if (S_ISDIR(mode) ret2 = find_group_orlov(sb, dir, else ret2 = find_group_other(sb, dir, 从上面代码也不难看出,对于目录和文件,选择group的规则是不同的。对于目录而言,使用find_group_orlov函数来寻找合适的 2016/10/10EXT4 inode 分配策略 ht

5、tp:/beanli.github.io/EXT4Inodeorlov/2/9 group,该函数使用了前面提到的orlov allocator算法,而对于文件,软链接等则 使用了find_group_other来寻找合适的group。 目录的inodeinode分配 首先介绍目录文件的inode分配,目录inode分配,调用的是find_group_orlov函数。 static int find_group_orlov(struct super_block *sb, struct inode *parent, ext4_group_t *group, umode_t mode, const

6、 struct qstr *qstr) ext4_group_t parent_group = EXT4_I(parent)i_block_group; struct ext4_sb_info *sbi = EXT4_SB(sb); /*获取块组的个数,存放到real_ngroups变量中*/ ext4_group_t real_ngroups = ext4_get_groups_count(sb); int inodes_per_group = EXT4_INODES_PER_GROUP(sb); unsigned int freei, avefreei, grp_free; ext4_fs

7、blk_t freeb, avefreec; unsigned int ndirs; int max_dirs, min_inodes; ext4_grpblk_t min_clusters; ext4_group_t i, grp, g, ngroups; struct ext4_group_desc *desc; struct orlov_stats stats; int flex_size = ext4_flex_bg_size(sbi); struct dx_hash_info hinfo; ngroups = real_ngroups; /*如果文件系统打开了flex_bg选项,就以

8、逻辑块组为单位分配*/ if (flex_size 1) ngroups = (real_ngroups + flex_size 1) sbis_log_groups_per_flex; parent_group = sbis_log_groups_per_flex; freei = percpu_counter_read_positive( avefreei = freei / ngroups; freeb = EXT4_C2B(sbi, percpu_counter_read_positive( avefreec = freeb; do_div(avefreec, ngroups); nd

9、irs = percpu_counter_read_positive( if (S_ISDIR(mode) int ret = 1; if (qstr) hinfo.hash_version = DX_HASH_HALF_MD4; hinfo.seed = sbis_hash_seed; ext4fs_dirhash(qstrname, qstrlen, grp = hinfo.hash; else grp = prandom_u32(); parent_group = (unsigned)grp % ngroups; for (i = 0; i = best_ndir) continue;

10、if (stats.free_inodes avefreei) continue; if (stats.free_clusters i_last_alloc_group; if (flex_size 1) parent_group = sbis_log_groups_per_flex; for (i = 0; i = max_dirs) continue; if (stats.free_inodes min_inodes) continue; if (stats.free_clusters i_block_group; for (i = 0; i = avefreei) *group = gr

11、p; 2016/10/10EXT4 inode 分配策略 http:/beanli.github.io/EXT4Inodeorlov/4/9 return 0; if (avefreei) /* * The freeinodes counter is approximate, and for really small * filesystems the above test can fail to find any blockgroups */ avefreei = 0; goto fallback_retry; return 1; 这么一大段代码,概括来讲可以描述为以下情况 1. 采用spr

12、ead out 策略让目录散开 2. 根据局部性原理,让兄弟目录,父子目录尽可能的靠近 当然这两种搜索都可能失败,那么就忘记战斗小组,各个块组地毯式搜索。 OK,我们开始进入代码细节。首先如果文件系统使用了flex_bg就以战斗小组为单位分配,率先需要确定inode所在的战斗小组, 即ngroup的值为文件系统中包含的所有逻辑块组的个数,当然了,如果并没有采用flex_bg,就退化成普通的块组。 接下来,对文件系统的总体使用情况做一个评估,我们如果是伸展开的策略,那么我们希望我们的inode分布在一个试用情况低于 平均水平的逻辑块组。这样各个逻辑块组使用才能均衡。 freei = percpu_counter_read_positive( avefreei = freei / ngroups; freeb = EXT4_C2B(sbi, percpu_counter_read_positive( avefreec = freeb; do_div(avefreec, ngroups); ndirs = percpu_counter_read_positive( 接下来的情况是何时采用伸展开的策略,何时采用靠近的策略。 if (S_ISDIR(mode) int ret = 1; if (qstr)

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 高等教育 > 其它相关文档

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号