zoukankan      html  css  js  c++  java
  • Ext4中内存使用技巧的一点思考

           今天在分析Ext4文件系统的时候,看到两个函数ext4_kvzalloc()/ext4_kvfree(),想到以前在使用kzalloc()/kmalloc()带来的内存分配失败问题,不得不感叹社区牛人的思路是多么的......(海量褒义词)

    1. kvzalloc分配分析

           请看代码:
    void *ext4_kvzalloc(size_t size, gfp_t flags)
    {
        void *ret;

        ret = kzalloc(size, flags | __GFP_NOWARN);
        if (!ret)
            ret = __vmalloc(size, flags | __GFP_ZERO, PAGE_KERNEL);
        return ret;
    }
           在ext4_kvzalloc中,首先执行kzalloc执行物理地址连续的内存空间分配,并且增加内存分配行为描述符__GFP_NOWARN(内存分配失败不会产生警告信息);如果分配成功,则返回;否则调用vmalloc执行物理地址不一定连续的内存空间分配(vmalloc是分配大小为page的整数倍,大于一个page的内存空间申请,vmalloc将一个page一个page的进行申请分配)。
           既然有了如此混合的分配方式,那么必然有可以解决这种混合方式的内存释放机制。因此就有了ext4_kvfree();

    2. kvfree释放分析

           在ext4_kvfree()中必然可以判断该内存是由哪种机制分配的,是kzalloc还是vmalloc,那么内核又提供的什么机制哪?
           答案是is_vmalloc_addr(),通过is_vmalloc_addr()判断是否为vmalloc分配的:
    static inline int is_vmalloc_addr(const void *x)
    {
    #ifdef CONFIG_MMU
        unsigned long addr = (unsigned long)x;

        return addr >= VMALLOC_START && addr < VMALLOC_END;
    #else
        return 0;
    #endif
    }
    (具体为什么可以这么判断,需要分析内存空间的布局,也许您可以查到我写过的资料,也许查不多,无论怎么样,请参阅以下地址:
          那么kvfree()的实现就非常明确了
    void ext4_kvfree(void *ptr)
    {
        if (is_vmalloc_addr(ptr))
            vfree(ptr);
        else
            kfree(ptr);

    }
          不管您怎么认为,至少我认为这种方案非常非常好......
          但是,个人还是建议在其中首先判断ptr指针是否为NULL。
        if (unlikely(ZERO_OR_NULL_PTR(ptr)))
            return;

    3. kvzalloc/kvfree应用分析

         这种机制,ext4把它使用到哪个或哪些场景中哪?主要有以下连个场景
         1. 分配s_group_info array;它所需内存大小是受磁盘存储大小影响的,存储越大,所需内存越大;
         2. 分配flex_groups array;它所需内存大小也是受磁盘存储大小影响的,存储越大,所需内存越大;
         两者的共同特点时,所需内存大小很不确定,也许很多歌页,也许一个页,如果很多个页,那么分配失败率会大大增高。

  • 相关阅读:
    asp.net string有多行文字
    asp.net设置gridview页码显示遇到的问题
    asp.net button浏览器端事件和服务器端事件
    GridView 控制默认分页页码间距 及字体大小
    复合主键与联合主键(转载)
    vsCode 列选择、列选中、选中列、选中多列(转载)
    可能有用的技术社区(转载)
    SQL 用于各种数据库的数据类型(转载) sqlserver 数据类型 取值范围 长度
    TypeError: value.getTime is not a function (elementUI报错转载 )
    工作1年3个月总结(201707-201810 )
  • 原文地址:https://www.cnblogs.com/youngerchina/p/5624519.html
Copyright © 2011-2022 走看看