Linux内核阅读--文件路径查找(二)

本文探讨Linux内核如何进行文件路径查找,从根目录开始,利用dentry结构进行逐级查找。在并发访问时,为解决锁冲突,Linux采用RCU算法确保读安全性。当读操作失败或查询需要下放至文件系统层时,会切换到加锁和引用计数策略。核心代码分析展示了这一过程。
摘要由CSDN通过智能技术生成

Linux文件路径查找的基本策略,是从查找根(一般是根目录或当前目录)开始,逐级向下查找。具体到代码中,每个查找的节点被表示为path,path的定义如下。

struct path {
       struct vfsmount *mnt;
       struct dentry *dentry;
};
我们可以看到,linux用挂载点和目录项来唯一表示一个路径节点。 目录查找,就是不断的从父路径节点找到子目录节点的过程。在路径的查找中,可能会遇到一些跳转,比如遇到挂载点,遇到符号链接,遇到"..",就需要跳转到相应的位置继续查询。

如果没有遇到需要跳转的情况,则主要依赖dentry中保存的信息进行路径查找。dentry中的信息,一个是inode、superblock等文件系统相关的信息,这些信息可以用来从磁盘中查询子目录。除了文件系统信息,dentry也维护了一个Cache,用来存储之前查询过的目录项。

一般来说,dentry有很大的机率被同时访问。并发访问的时候,为了维护dentry结构的内部一致性,每次查找子目录项,都需要对父目录加锁。在高并发的情形下,因为'/'之类的目录很容易被访问文,锁冲突的概率比较大,路径查找的性能就会降低。

linux的解决方案是采用RCU算法,dentry的数据结构被设计为读安全的,即在不加锁的情况下读,可能读到老数据,但不会造成飞指针指之类的恶性事故。linux在每个dentry记录一个版本号,在查询之前会将这个版本号记录下来,等查询操作完成之后,再对比一个版本号有无变化,没有变化,说明这次读操作访问的数据结构是一致的,结果有效。

因为每次路径查找,往往都是对最后一个节点进行修改,最容易冲突的dentry节点往往是最不常被修改的,因此这种算法可以比较有效的解决锁冲突问题。不过这里存在一个问题,如果读操作失败该如何处理?难道要接着重试么?这种重试会不会造成死循环?

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值