Linux proc 的文件系统的源码分析
2011-11-25 10:29
393 查看
proc 的文件系统是linux 里面常用的基于内存的文件系统。linux的内核版本 2.6.18
重要的struct:
struct proc_dir_entry {
unsigned int low_ino;
unsigned short namelen;
const char *name;
mode_t mode;
nlink_t nlink;
uid_t uid;
gid_t gid;
loff_t size;
struct inode_operations * proc_iops;
const struct file_operations * proc_fops;
get_info_t *get_info;
struct module *owner;
struct proc_dir_entry *next, *parent, *subdir;
void *data;
read_proc_t *read_proc;
write_proc_t *write_proc;
atomic_t count;/* use count */
int deleted;
/* delete flag */
void *set;
};
其中3个核心的函数指针
const struct file_operations * proc_fops; 当文件系统操作proc文件系统的时候,read,write,open所调用的函数
proc 文件系统同时定义了默认的proc file operations的时候
static struct file_operations proc_file_operations = {
.llseek
= proc_file_lseek,
.read = proc_file_read,
.write
= proc_file_write,
};
在使用默认的proc file operations 的时候,需要定义自己的read_proc/write_proc的函数
read_proc_t *read_proc; 写自己的read的函数
write_proc_t *write_proc; 写自己的write的函数
1.初始化
在Main.c里面调用了 root.c 里的函数 proc_root_init(); 初始化了一些基本的proc目录下的文件,例如 cpuinfo, stat....
2.创建proc文件
a . struct proc_dir_entry *create_proc_entry(const char *name, mode_t mode, struct proc_dir_entry *parent)
参数 name 是要创建的 proc 文件名。
mode 是该entry性质,例如 DIR(目录)/LNK(链接)/REG(文件)
parent 指定该文件的上层 proc 目录项,如果为 NULL,表示创建在 /proc 根目录下。
在create_proc_entry函数里会设置文件的名字,文件的权限,传入上层的 proc_dir_entry,是为了构建父节点和子节点的关系
在proc_register方法里面会改变父子的proc_dir_entry链表指向构建父和子的树状结构,也就是struct proc_dir_entry *next, *parent, *subdir;
dp->next = dir->subdir;
dp->parent = dir;
dir->subdir = dp;
同时也指定了默认的const struct file_operations * proc_fops,为proc_file_operations
b. static inline struct proc_dir_entry *create_proc_read_entry(const char *name,
mode_t mode, struct proc_dir_entry *base,
read_proc_t *read_proc, void * data)
创建函数体传进的指定的read proc文件的方法 read_proc_t *read_proc;
实际上这个函数存在的意义不是很大,直接可以使用create_proc_entry来替代,在多做一件事情,就是指定proc_dir_entr->read_proc=read_proc;
如果不想默认的proc file 的操作函数,你也可以自己指定自己的操作函数,只要用create_proc_entry返回的proc_dir_entry结构体里直接指定proc_fops指针指向自己的定义的结构体,就可以了
比如:
static struct file_operations proc_my_operations = {
.open = my_open,
.read = my_read,
.write = my_write
.llseek
= my_lseek,
.release
= my_release,
};
/proc/stat /proc/interrupts ... 显示系统运行状态的设计技巧
象stat,interrupts 的这样反应系统状态的文件,
首先系统的状态实际上都是已经在系统的内存中,
其次如果没有别的进程对该文件监视,是不需要往这个文件里写内容的
哪怕在时间中断中去写这个文件(内存的一次复制),也是没有必要的,第一有系统的开销,第二没有人关注它,第三不可控性
所以对于系统状态的监听,应该是由外部(想监听的系统)来触发的,不需要内核时时刻刻去写系统状态文件,那么这样的设计就很简单了,内核只要在open的函数里去写当时的状态就足够了。
也就是对外部系统按照自己的频率去打开这个文件,内核复制状态到proc文件中,然后进程读出内容到自己的用户空间,然后关闭这个文件。关闭这个动作就非常重要,如果不关闭,那么里面的内容将不会在跟新。
重要的struct:
struct proc_dir_entry {
unsigned int low_ino;
unsigned short namelen;
const char *name;
mode_t mode;
nlink_t nlink;
uid_t uid;
gid_t gid;
loff_t size;
struct inode_operations * proc_iops;
const struct file_operations * proc_fops;
get_info_t *get_info;
struct module *owner;
struct proc_dir_entry *next, *parent, *subdir;
void *data;
read_proc_t *read_proc;
write_proc_t *write_proc;
atomic_t count;/* use count */
int deleted;
/* delete flag */
void *set;
};
其中3个核心的函数指针
const struct file_operations * proc_fops; 当文件系统操作proc文件系统的时候,read,write,open所调用的函数
proc 文件系统同时定义了默认的proc file operations的时候
static struct file_operations proc_file_operations = {
.llseek
= proc_file_lseek,
.read = proc_file_read,
.write
= proc_file_write,
};
在使用默认的proc file operations 的时候,需要定义自己的read_proc/write_proc的函数
read_proc_t *read_proc; 写自己的read的函数
write_proc_t *write_proc; 写自己的write的函数
1.初始化
在Main.c里面调用了 root.c 里的函数 proc_root_init(); 初始化了一些基本的proc目录下的文件,例如 cpuinfo, stat....
2.创建proc文件
a . struct proc_dir_entry *create_proc_entry(const char *name, mode_t mode, struct proc_dir_entry *parent)
参数 name 是要创建的 proc 文件名。
mode 是该entry性质,例如 DIR(目录)/LNK(链接)/REG(文件)
parent 指定该文件的上层 proc 目录项,如果为 NULL,表示创建在 /proc 根目录下。
在create_proc_entry函数里会设置文件的名字,文件的权限,传入上层的 proc_dir_entry,是为了构建父节点和子节点的关系
struct proc_dir_entry *create_proc_entry(const char *name, mode_t mode, struct proc_dir_entry *parent) { struct proc_dir_entry *ent; nlink_t nlink; if (S_ISDIR(mode)) { if ((mode & S_IALLUGO) == 0) mode |= S_IRUGO | S_IXUGO; nlink = 2; } else { if ((mode & S_IFMT) == 0) mode |= S_IFREG; if ((mode & S_IALLUGO) == 0) mode |= S_IRUGO; nlink = 1; } ent = proc_create(&parent,name,mode,nlink); if (ent) { if (S_ISDIR(mode)) { ent->proc_fops = &proc_dir_operations; ent->proc_iops = &proc_dir_inode_operations; } if (proc_register(parent, ent) < 0) { kfree(ent); ent = NULL; } } return ent; }
在proc_register方法里面会改变父子的proc_dir_entry链表指向构建父和子的树状结构,也就是struct proc_dir_entry *next, *parent, *subdir;
dp->next = dir->subdir;
dp->parent = dir;
dir->subdir = dp;
同时也指定了默认的const struct file_operations * proc_fops,为proc_file_operations
b. static inline struct proc_dir_entry *create_proc_read_entry(const char *name,
mode_t mode, struct proc_dir_entry *base,
read_proc_t *read_proc, void * data)
创建函数体传进的指定的read proc文件的方法 read_proc_t *read_proc;
实际上这个函数存在的意义不是很大,直接可以使用create_proc_entry来替代,在多做一件事情,就是指定proc_dir_entr->read_proc=read_proc;
如果不想默认的proc file 的操作函数,你也可以自己指定自己的操作函数,只要用create_proc_entry返回的proc_dir_entry结构体里直接指定proc_fops指针指向自己的定义的结构体,就可以了
比如:
static struct file_operations proc_my_operations = {
.open = my_open,
.read = my_read,
.write = my_write
.llseek
= my_lseek,
.release
= my_release,
};
/proc/stat /proc/interrupts ... 显示系统运行状态的设计技巧
象stat,interrupts 的这样反应系统状态的文件,
首先系统的状态实际上都是已经在系统的内存中,
其次如果没有别的进程对该文件监视,是不需要往这个文件里写内容的
哪怕在时间中断中去写这个文件(内存的一次复制),也是没有必要的,第一有系统的开销,第二没有人关注它,第三不可控性
所以对于系统状态的监听,应该是由外部(想监听的系统)来触发的,不需要内核时时刻刻去写系统状态文件,那么这样的设计就很简单了,内核只要在open的函数里去写当时的状态就足够了。
也就是对外部系统按照自己的频率去打开这个文件,内核复制状态到proc文件中,然后进程读出内容到自己的用户空间,然后关闭这个文件。关闭这个动作就非常重要,如果不关闭,那么里面的内容将不会在跟新。
相关文章推荐
- Hadoop源码分析笔记(十二):名字节点--文件系统目录树
- Linux内核源码分析--文件系统(二、高速缓存区)
- Hadoop源码分析笔记(四):Hadoop文件系统简介
- 文件系统(一)--super.c bitmap.c inode.c 源码分析
- Linux proc文件分析以及系统信息获取
- UBIFS文件系统源码分析
- Linux内核源码分析--文件系统(六、Super.c)
- Glusterfs文件系统简介和源码简单分析
- FATFS文件系统+源码分析——学习笔记
- 【Flume】【源码分析】flume中sink到hdfs,文件系统频繁产生文件,文件滚动配置不起作用?
- 文件系统(四)--pipe.c read_write.c stat.c fcntl.c ioctl.c源码分析
- 【Flume】【源码分析】flume中sink到hdfs,文件系统频繁产生文件,文件滚动配置不起作用?
- Linux内核源码分析--文件系统(九、File_dev.c)
- f2fs——新型flash友好文件系统gc部分源码分析
- Linux内核源码分析--文件系统(四、Bitmap.c)
- 文件系统(二)--buffer.c namei.c truncate.c open.c源码分析
- Linux内核源码分析-安装实际根文件系统- prepare_namespace
- 话说文件系统——aufs源码分析(三)
- Linux内核源码分析-安装普通文件系统-mount系统调用
- Linux内核源码分析之文件系统(1) -- 三思而后行