字符设备驱动基础篇3——字符设备驱动工作原理
以下内容源于朱有鹏嵌入式课程的学习,如有侵权,请告知删除。
参考资料:http://www.cnblogs.com/biaohc/p/6575074.html。
1、系统整体工作原理
(1)应用层-》API-》设备驱动-》硬件;
(2)API:open、read、write、close等操作逻辑(“吃饭”这个宏观操作);
(3)驱动源码中提供真正的open、read、write、close等函数实体(右手,用筷子等具体操作);
2、file_operations结构体
结构体成员的解释,见博文:http://blog.****.net/oqqhutu12345678/article/details/78508273
(1)该结构体的元素主要是函数指针,用来挂接实体函数地址;
(2)每个设备驱动都需要一个该结构体类型的变量;
(3)设备驱动向内核注册时,提供该结构体类型的变量。
(4)该结构体的成员函数是字符设备驱动程序设计的主体内容,这些函数实际会在应用程序进行linux的open()、read()等系统调用时最终被内核调用。
3、注册字符设备
- 在没有框架模型前,这里注册驱动、注册设备混为一谈(设备号和file_opertion紧结合,一个驱动的信息包含两者)。
(1)为何要注册驱动?如果不注册,内核查无此人。
(2)谁去负责注册?驱动去注册自己。
(3)向谁注册?向内核注册。
(4)注册函数从哪里来?内核提供了注册函数,驱动需要调用此函数来注册自己。
(5)注册前怎样?注册后怎样?注册产生什么结果?查有此人,内核可以调用此驱动去驱动硬件。
4、register_chrdev函数详解(#include <linux/fs.h>)
(1)作用是驱动向内核注册某设备的file_operations
- 成功返回值为0,失败返回负数。
(2)参数
- major,可以自己指定,也可以让内核帮忙分配。表征当前设备的编号,范围是1~254;犹如身份证号。
- name,表示当前设备驱动的名字;犹如具体名字。
- fops,file_operations结构体指针。
- cat /proc/devices,可以查看哪些设备号可用。
(3)inline和static
- inline修饰:因为此函数定义在头文件里面,如果被两个文件包含,就会被重复定义,使用inline后,就只剩函数体了,而不是函数定义。本质原因是此函数太短了。
5、内核如何管理字符设备驱动
(1)内核中用一个数组,来存储注册的字符设备驱动;
- 数组的缺陷,因此只有1-254?
(2)register_chrdev函数将(要注册的)驱动的信息(包括设备号和file_operations)存储在数组中相应的位置;
(3)使用cat /proc/devices,查看内核中已经注册过的字符设备驱动和块设备驱动;
- 有些编号默认分配给某些设备。
- 理解主设备号(major)的概念。