博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
linux 2.6.32文件系统 fd与file*之间的关系
阅读量:6416 次
发布时间:2019-06-23

本文共 2447 字,大约阅读时间需要 8 分钟。

给定如下一定情况:

crash> filesPID: 7739   TASK: ffff8817facd2100  CPU: 11  COMMAND: "slabtop"ROOT: /    CWD: / FD       FILE            DENTRY           INODE       TYPE PATH  0 ffff881810117680 ffff880c115a5cc0 ffff881811fa7a78 CHR  /dev/null  1 ffff880af6bf2200 ffff88180c64e440 ffff88180dc02438 REG  /dev/shm/zxdfs/moni_sys.log  2 ffff88180ef619c0 ffff881811a263c0 ffff880c0eabf118 CHR  /dev/console  3 ffff880c9ddbba80 ffff8818014b1540 ffff88100a8117f8 REG  /proc/slabinfo---------------请注意,第二列就是对应的file*,第三列就是dentry,第四列就是对应的inode,用来验证

比如对于fd为3,如何快速获取对应的file* 信息?虽然这个命令输出的时候,第二列就是对应的file*,第三列就是dentry,第四列就是对应的inode,但是今天我们通过代码找到的file*是否正确。

对于fd来说,一般会根据 fget_light-->fcheck_files来获取file*,(注意,这里无关fget 还是 fget_light,因为最终都是调用fcheck_files)

结构就是当前进程task中的:

struct files_struct *files = current->files;
然后根据这个files_struct成员,找到fdt指针:
static inline struct file * fcheck_files(struct files_struct *files, unsigned int fd){    struct file * file = NULL;    struct fdtable *fdt = files_fdtable(files);    if (fd < fdt->max_fds)        file = rcu_dereference(fdt->fd[fd]);    return file;}

fdt中的fd数组中,就是按照fd下标存放的file*指针,如下:

crash> taskPID: 7739   TASK: ffff8817facd2100  CPU: 11  COMMAND: "slabtop"crash> struct task_struct.files ffff8817facd2100  files = 0xffff88130c8bec00crash> struct fdtable.fd 0xffff88126d2f4900  fd = 0xffff880c976ad000crash> rd 0xffff880c976ad000 4ffff880c976ad000:  ffff881810117680 ffff880af6bf2200   .v......."......ffff880c976ad010:  ffff88180ef619c0 ffff880c9ddbba80   ................

所以对于fd为3来说,取到的file*指针就是ffff880c9ddbba80   ,(这个指针也和我们files命令打印的一致)我们来验证一下这个file*指针:

crash> struct file.f_path.dentry ffff880c9ddbba80  f_path.dentry = 0xffff8818014b1540crash> struct dentry.d_iname 0xffff8818014b1540  d_iname = "slabinfo\000_offset\000ndler.py\000m\000\000\000\000"

d_iname就是对应的文件路径最后一段文件名,说明我们取的file*指针是对了,有了file* 指针,我们就可以将对应的vfs的其他结构全部串起来。

 不过需要注意的是,操作这个fdt的时候,需要关注rcu锁,具体可以查看files.txt里面的说明,获取到的file*指针,如果

if (atomic_long_inc_not_zero(&file->f_count))

*fput_needed = 1;

这个满足的话,是需要put的,否则file*指针不能用。也就是说,当file->f_count为0时,是不直接增加计数的,这个和pagecache中的lockless用法一样。

取到的file指针,用rcu保证有效性,然后这个get之后,用file->f_count来保证计数的有效性。

其实,crash中的files命令,除了能快速查看到对应的file*,dentry,inode等,带参数的files 命令还有更多的输出:

crash> files -d ffff8818014b1540     DENTRY           INODE           SUPERBLK     TYPE PATHffff8818014b1540 ffff88100a8117f8 ffff880c1188cc00 REG  /.root_tmpfs/proc/slabinfo

具体可以hlep files 来验证。

转载于:https://www.cnblogs.com/10087622blog/p/9540565.html

你可能感兴趣的文章
java随机范围内的日期
查看>>
spring事务学习(转账案例)(二)
查看>>
[官方教程] [ES4封装教程]1.使用 VMware Player 创建适合封装的虚拟机
查看>>
http协议与http代理
查看>>
【iOS开发-91】GCD的同步异步串行并行、NSOperation和NSOperationQueue一级用dispatch_once实现单例...
查看>>
Redis+Spring缓存实例
查看>>
Storm集群安装详解
查看>>
centos7.x搭建svn server
查看>>
原码编译安装openssh6.7p1
查看>>
项目实战:自定义监控项--监控CPU信息
查看>>
easyui-datetimebox设置默认时分秒00:00:00
查看>>
蚂蚁分类信息系统5.8多城市UTF8开源优化版
查看>>
在django1.2+python2.7环境中使用send_mail发送邮件
查看>>
“Metro”,移动设备视觉语言的新新人类
查看>>
PHP源代码下载(本代码供初学者使用)
查看>>
Disruptor-NET和内存栅栏
查看>>
Windows平台ipod touch/iphone等共享笔记本无线上网设置大全
查看>>
播放加密DVD
查看>>
产品设计体会(3013)项目的“敏捷沟通”实践
查看>>
RHEL6.3基本网络配置(1)ifconfig命令
查看>>