linux内核file_operations的赋值流程跟踪

我们知道linux系统中文件有很多种,包括普通文件,目录文件,设备文件,管道文件,套接字文件等.文件在内核中用file结构体表示,file对象中有个重要成员 f_op指针,它指向file_operations,该结构体定义了一系列文件操作的函数指针集合,例如open,read,write,ioctl,mmap等.当对文件进行操作时,最终是调用对应的函数指针进行操作.

linux中支持很多种文件系统,每个文件系统使用之前都必须要先注册才能使用,文件系统类型用结构体file_system_type表示,注册文件系统使用register_filesystem(struct file_system_type * fs),它的作用是将文件系统类型添加到全局链表file_systems中.下面我以linux主流磁盘文件系统类型ext4的注册流程进行分析.


//下面是定义一个ext4文件系统类型

static struct file_system_type ext4_fs_type = {
.owner = THIS_MODULE,
.name = "ext4",
.mount = ext4_mount,
.kill_sb = kill_block_super,
.fs_flags = FS_REQUIRES_DEV,
};


在用户空间执行mount系统调用进行挂载文件系统时会调用ext4_mount(),基本流程为:do_mount()->do_new_mount()->do_kern_mount()->vfs_kern_mount()->mount_fs()->ext4_fs_type.mount()->ext4_mount(),感兴趣的读者请自行分析.

static struct dentry *ext4_mount(struct file_system_type *fs_type, int flags,
      const char *dev_name, void *data)
{
return mount_bdev(fs_type, flags, dev_name, data, ext4_fill_super);
}

mount_bdev函数原型声明如下:

struct dentry *mount_bdev(struct file_system_type *fs_type,
int flags, const char *dev_name, void *data,
int (*fill_super)(struct super_block *, void *, int)) {

}

注意上面函数mount_bdev的最后一个参数ext4_fill_super,它是一个函数指针,指向函数ext4_fill_super.

mount_bdev中会调用ext4_fill_super()函数,代码片段如下:

struct dentry *mount_bdev(struct file_system_type *fs_type,
int flags, const char *dev_name, void *data,
int (*fill_super)(struct super_block *, void *, int))
{

.........

s->s_flags = flags | MS_NOSEC;
s->s_mode = mode;
strlcpy(s->s_id, bdevname(bdev, b), sizeof(s->s_id));
sb_set_blocksize(s, block_size(bdev));
error = fill_super(s, data, flags & MS_SILENT ? 1 : 0);
if (error) {
deactivate_locked_super(s);
goto error;
}


s->s_flags |= MS_ACTIVE;
bdev->bd_super = s;

}

下面看ext4_fill_super的执行流程代码片段:

static int ext4_fill_super(struct super_block *sb, void *data, int silent) {

.....

/*
* The jbd2_journal_load will have done any necessary log recovery,
* so we can safely mount the rest of the filesystem now.
*/


root = ext4_iget(sb, EXT4_ROOT_INO);
if (IS_ERR(root)) {
ext

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
设备驱动程序与内核的接口通过数据结构 file_operations 完成。 在 Linux 中,每个设备驱动程序都对应一个 file_operations 结构体,它用于定义设备驱动程序的操作方法和回调函数。file_operations 结构体通常包含以下字段: - 文件打开方法(open):用于打开设备文件,通常会进行设备初始化等操作。 - 文件读取方法(read):用于从设备中读取数据。 - 文件写入方法(write):用于向设备中写入数据。 - 文件定位方法(llseek):用于定位文件读写指针的位置。 - 文件控制方法(ioctl):用于执行设备的控制操作。 - 文件释放方法(release):用于释放设备资源,通常会进行设备关闭等操作。 设备驱动程序通过实现 file_operations 结构体中定义的方法和回调函数来提供对设备的访问。当应用程序打开设备文件并执行读写等操作时,内核会根据文件描述符找到对应的 file_operations 结构体,并调用相应的方法来完成具体的操作。因此,file_operations 结构体是设备驱动程序与内核的接口之一,它定义了设备驱动程序的操作方法和内核的调用方式,是设备驱动程序实现的关键。 需要注意的是,file_operations 结构体只是设备驱动程序与内核的接口之一,与文件系统的 inode_operations、super_block_operations、dentry_operations 等不同。file_operations 结构体用于定义设备驱动程序的操作方法和回调函数,而 inode_operations、super_block_operations、dentry_operations 等则用于定义文件系统的操作方法和回调函数。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值