zoukankan      html  css  js  c++  java
  • 解析Linux中的VFS文件系统之文件系统的注册(二)

    继上一篇文章:http://www.cnblogs.com/linhaostudy/p/7397024.html

    3. 文件系统的注册

    这里的文件系统是指可能会被挂载到目录树中的各个实际文件系统,所谓实际文件系统,即是指VFS 中的实际操作最终要通过它们来完成而已,并不意味着它们一定要存在于某种特定的存储设备上。比如在笔者的 Linux 机器下就注册有 "rootfs"、"proc"、"ext2"、"sockfs" 等十几种文件系统。

    3.1 文件系统的数据结构

    在 Linux 源代码中,每种实际的文件系统用以下的数据结构表示(include/linux/fs.h):

     1 struct file_system_type {
     2     const char *name;
     3     int fs_flags;
     4     struct dentry *(*mount) (struct file_system_type *, int,
     5                const char *, void *);
     6     void (*kill_sb) (struct super_block *);
     7     struct module *owner;
     8     struct file_system_type * next;
     9     struct hlist_head fs_supers;
    10 
    11     struct lock_class_key s_lock_key;
    12     struct lock_class_key s_umount_key;
    13     struct lock_class_key s_vfs_rename_key;
    14 
    15     struct lock_class_key i_lock_key;
    16     struct lock_class_key i_mutex_key;
    17     struct lock_class_key i_mutex_dir_key;
    18 };

    注册过程实际上将表示各实际文件系统的 struct file_system_type 数据结构的实例化,然后形成一个链表,内核中用一个名为 file_systems 的全局变量来指向该链表的表头。

    -------------------------------------------------------------------------------- 

    name:文件系统的名字,这个名字唯一的标识一种文件系统;

    next:为文件系统的链表指针;

    fs_supers:对于每一个mount的文件系统,系统都会为它创建一个super_block数据结构,该结构保存文件系统本省以及挂载点相关的信息。由于可以同时挂载多个同一文件系统类型的文件系统(比如/ 和/home都挂载了ext3文件系统),因此同一个文件系统类型会对应多个super block,@fs_supers就把这个文件系统类型对应的super block链接起来。

    owner是指向module的指针,仅当文件系统类型是以模块方式注册时,owner才有效。

    mount:这个函数非常重要,它VFS能够和底层文件系统交互的起始点,该函数是不能放在super_block结构中的,因为super_block是在get_sb执行之后才能建立的。get_sb从底层文件系统获取super_block的信息,是和底层文件系统相关的。

    -------------------------------------------------------------------------------- 

    3.2 注册 rootfs 文件系统

     在众多的实际文件系统中,之所以单独介绍 rootfs 文件系统的注册过程,实在是因为该文件系统 VFS 的关系太过密切,如果说 ext2/ext3 是 Linux 的本土文件系统,那么 rootfs 文件系统则是 VFS 存在的基础。一般文件系统的注册都是通过 module_init 宏以及 do_initcalls() 函数来完成(读者可通过阅读module_init 宏的声明及 archi386vmlinux.lds 文件来理解这一过程),但是 rootfs 的注册却是通过 init_rootfs() 这一初始化函数来完成,这意味着 rootfs 的注册过程是 Linux 内核初始化阶段不可分割的一部分。

    在fs/filesystem.c中69行

     1 int register_filesystem(struct file_system_type * fs)
     2 {
     3     int res = 0;
     4     struct file_system_type ** p;
     5 
     6     BUG_ON(strchr(fs->name, '.'));
     7     if (fs->next)
     8         return -EBUSY;
     9     write_lock(&file_systems_lock);
    10     p = find_filesystem(fs->name, strlen(fs->name));
    11     if (*p)
    12         res = -EBUSY;
    13     else
    14         *p = fs;
    15     write_unlock(&file_systems_lock);
    16     return res;
    17 }

    fs/ramfs/inode.c中270行

     1 static int __init init_ramfs_fs(void)
     2 {
     3     return register_filesystem(&ramfs_fs_type);
     4 }
     5 module_init(init_ramfs_fs)
     6 
     7 int __init init_rootfs(void)
     8 {
     9     int err;
    10 
    11     err = bdi_init(&ramfs_backing_dev_info);
    12     if (err)
    13         return err;
    14 
    15     err = register_filesystem(&rootfs_fs_type);
    16     if (err)
    17         bdi_destroy(&ramfs_backing_dev_info);
    18 
    19     return err;
    20 }

    init_rootfs() 通过调用 register_filesystem(&rootfs_fs_type) 函数来完成 rootfs 文件系统注册的,其中rootfs_fs_type 定义如下:

    1 struct file_system_type rootfs_fs_type = { 
    2     name:        "rootfs", 
    3     read_super:    ramfs_read_super, 
    4     fs_flags:    FS_NOMOUNT|FS_LITTER, 
    5     owner:        THIS_MODULE, 
    6  }

    注册之后的 file_systems 链表结构如下图2所示:

     

  • 相关阅读:
    TCP Socket 粘包
    Toast连续弹出的问题
    SDK Build Tools revision (19.0.3) is too low for project Minimum required is 19.1.0
    数据结构精要------直接选择和堆排序算法
    hdoj 2199 Can you solve this equation? 【二分枚举】
    云端数据遭觊觎 安全问题不容忽视
    leetcode || 58、Length of Last Word
    【安全加密技术】非对称加密
    无处不在的微创新——验证码的故事
    IDLE经常使用快捷键汇总
  • 原文地址:https://www.cnblogs.com/linhaostudy/p/7405199.html
Copyright © 2011-2022 走看看