ldd3已经读了4章了。在这里思考一下,为何dev file 和 proc file的创建方式有些不同。
1 dev file的书写流程:
需求:需要写一个driver,在/dev目录下创建4个文件scull0, scull1, scull2, scull3.
按照从整体到细节的过程如下:
- 1 使用alloc_chrdev_region 告诉kernel我是一个驱动,需要一个设备号,kernel就会动态分配一个设备号。(参数不细说)
- 2 为不同的设备文件申请struct scull_dev的数据结构空间,struct scull_dev中包含struct cdev元素,[看注释2]
- 3 初始化struct scull_dev,包括申请空间,组织好结构神马的。
- 4 对四个dev文件,使用cdev_add + 不同的设备号进行注册(关键注册数据结构:struct cdev)。
- over
在注册玩了之后,文件系统还没有生成node,需要使用mknod命令针对设备号来生成这4个设备文件。注意生成文件的设备号要与代码中的一致(不论是major还是minor)。major可去/proc/drivers查看。
注释2:
- struct scull_dev中包含struct cdev元素。这是与文件系统的一个重要接口。struct cdev中包含struct file_operations元素。是filesystem用来操作设备的函数指针。struct cdev将来在filesystem中是被放在inode中的。(b2 == belongs to)
- 这里不得不说的:struct file_operations ----b2-----struct cdev----b2------inode----b2----filesystem
inode中包含大量文件的信息,顺带着要提一下 struct file。代表一个 open file。
2 proc file文件的生成过程
这里利用了两种方法生成了2个不同的proc file。
old method:
实现<linux/proc_fs.h>的read_proc函数,将要显示的内容写到buf中,并使用create_proc_read_entry进行生成结点并注册【注:关键参数:要将实现的函数的指针传递过去】。
new method:
- 原来的方法太过于集中,不够灵活。新方法实现<linux/seq_file.h>的iterator接口start,next,stop,show方法。至于一个item是多少,根据实际情况实现者自己去定。
- 使用<linux/seq_file.h>去构造struct seq_operations scull_seq_ops, 然后构造struct file_operations scull_proc_ops.但是也是使用seq_file中的函数去构造结构里的元素。
- 使用create_proc_entry函数生成一个文件,果断scull_proc_ops该在这个时候传给filesystem。
new method的小结:
seq_file感觉就是一个函数库啊,它向上实现了针对filesystem的函数接口(比如seq_read, seq_lseek, seq_release),同时给使用的人提供了接口(start, next, stop, show)。
使用的人还要完成组装的功能。
为啥proc 和 dev的生成方法不一样呢?
就拿proc的old method 和 dev的生成方法做对比。
- 1 dev需要有设备号,需要管理4个文件。proc只需要管理一个文件。
- 2 dev是设备文件,proc只是在模拟一个普通文件。
其他的倒是没什么了,主要是 文件类型不同,drivers管理的dev文件多一些。