关于我们

麒麟动态

当前位置  >  首页  >  关于我们  >  麒麟动态  >  正文

定位Linux内核bug,麒麟软件修复方案获社区认可

发布时间:2023-09-15    浏览次数:4749次    作者:麒麟软件



近日,麒麟软件的工程师定位到Linux内核中的一项bug,并将问题描述、复现步骤、触发条件、可能的优化方案等信息同步到上游内核社区。



问题现象描述

在服务器上将数据盘格式化成ext4文件系统时,如果强制指定blocksize 64K大小,在同一目录下文件数量达到千万级别时,可能导致系统ext4文件系统异常,文件写入失败等问题。



问题定位

经过层层定位,发现ext4 get_dx_countlimit()函数有三处代码可能导致问题的产生。下图函数主要是在校验fakedirent -> rec_len的长度,在不符合规范的情况下可能返回空值。



ext4 中目录采用了B+树(htree)结构来加速查找过程。这其中将节点划分为了根节点和中间节点,而fakedirent 是每个节点的第一个entry,用于记录整个节点的大小。



对此, rec_len的可能取值有以下两种情况:


• rec_len = blocksize(表明属于中间节点 struct dx_node)


• 等于12个byte大小(表明属于根节点 struct dx_root)


在 rec_len 不属于以上两种取值时,程序会报错并返回空值。


通过问题定位,发现故障文件中rec_len的值为0xffff,这是由于blocksize 为64K时,rec_len的值应当为0x10000, 但是由于字节大小限制,会使用rec_len = 0xffff 来代表 rec_len = 0x10000。


而在最初的代码中,对rec_len进行校验时存在异常,可能导致问题出现。



问题复现

在实验环境模拟现场复现,通过在同类服务器上数据盘在格式化成ext4时强制制定blocksize 64K大小,同时在一个目录下创建 2000 万个文件夹,成功复现问题现象,此时文件夹无法进行读取,系统日志内出现了 ext4 文件系统的报错。


同时,按照同样的复现步骤,使用其他发行版本和 Linux 社区最新内核,指定 blocksize 64K大小,也成功复现了这一问题,证明这一问题同时存在于社区以及主流的Linux系统上。



问题修复

基于上述分析及定位,麒麟软件推出修复方案,并将该方案第一时间推送社区(点击阅读原文可访问社区链接),提醒所有ext4用户在此场景下都会遭遇相同的问题。


同时,麒麟软件建议问题修复前:


• 在业务部署时格式化存放数据硬盘,采用默认值blocksize 4K, 避免强制设置64K


• 在业务层面进行优化, 避免在同一个目录写入千万级别的文件


若已经有机器出现了该文件系统错误,最佳的方案是通过fsck-r对文件系统进行修复、再升级修复的内核包。考虑到fsck修复存在数据丢失风险以及数据的重要性,不建议出现问题后多次执行fsck操作。
目前,社区已认可该方案,银河麒麟高级服务器操作系统 V10 SP1 已更新内核修复此问题,其他版本也将合入社区补丁。


通讯员 | 闫相臣、张诗达

来    源 | 产品与社区发展中心、研发中心

审    核 | 市场与政府事务部


往期回顾



上一篇: 麒麟软件亮相第八届“一带一路”高峰论坛 下一篇: 鹏腾生态闪耀世界计算大会

试用

服务

动态

联系