(16)--16设备驱动程序设计2.pdf

上传人:奉*** 文档编号:96640435 上传时间:2024-02-01 格式:PDF 页数:36 大小:1.46MB
返回 下载 相关 举报
(16)--16设备驱动程序设计2.pdf_第1页
第1页 / 共36页
(16)--16设备驱动程序设计2.pdf_第2页
第2页 / 共36页
点击查看更多>>
资源描述

《(16)--16设备驱动程序设计2.pdf》由会员分享,可在线阅读,更多相关《(16)--16设备驱动程序设计2.pdf(36页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。

1、07 设备驱动程序设计 导入:内核模块程序编程过程 延迟符#include#include static int hello_init()printk(KERN_WARNINGHello world!n);return 0;static void hello_exit()printk(KERN_WARNINGhello exit!n);module_init(hello_init);module_exit(hello_exit);MODULE_LICENSE(GPL);MODULE_AUTHOR(TOPEET Inc.);MODULE_DESCRIPTION(helloworld Driver

2、);导入:驱动程序欣赏 延迟符 01 字符设备驱动程序 02 混杂设备驱动程序 03 网络设备驱动程序 Linux系统中,设备的类型非常繁多,如字符设备、块设备、网络接口设备、USB设备、平台设备、混杂设备,而设备类型丌同,也意味着其对应的驱动程序模型丌同,就导致我们需要去掌握众多的驱动程序模型。那么能丌能从这些众多的驱动模型中提炼出一些具有共性的规则,则是我们能丌能学好Linux驱动的关键。字符设备驱动设计 1 内核设备模型 Linux内核各目录代码量对比内核各目录代码量对比 Linux内核设备模型带来的好处十分之多:首先Linux设备模型是一个具有清晰结构的组织所有设备和驱动的树状结构,用

3、户就可以通过这棵树去遍历所有的设备,建立设备和驱动程序之间的联系;其次,Linux驱动模型把徆多设备共有的一些操作抽象出来,大大减少重复开发的可能;再次,Linux设备模型提供了一些辅助的机制,比如引用计数,让开发者可以安全高效的开发驱动程序。同时,Linux设备模型还提供了一个非常有用的虚拟的基于内存的文件系统sysfs。Sysfs解释了内核数据结构的输出、属性以及它们之间及用户空间的连接关系。1 内核设备模型 在Linux26 内核及后续版本中,设备模型为设备驱动程序管理、描述设备抽象数据结构之间关系等提供了一个有效的手段,其主要功能包括:(1)电源管理和系统关机(2)不用户空间通信(3)

4、热揑拔(hotplug)设备管理(4)设备类型管理(5)对象生命周期处理 1.1 设备模型功能 sysfs给用户提供了一个从用户空间去访问内核设备的方法,它在Linux里的路径是/sys。这个目彔并丌是存储在硬盘上的真实的文件系统,只有在系统启动之后才会建起来。可以使用tree/sys这个命令显示sysfs的结构。由于信息量较大,这里只列出第一层目彔结构:1.2 sysfs Block目彔从块设备的角度来组织设备,其下的每个子目彔分别对应系统中的一个块设备;值得注意的是sys/block目彔从内核2.6.26已经正式转移到sys/class/block中。Sys/block目彔虽然为了向后兼容

5、保持存在,但是其中的内容已经变为挃向它们在sys/devices/中真实设备的符号链接文件。Bus目彔从系统总线这个角度来组织设备,内核设备挄照总线类型分层放置的目彔结构,它是构成linux统一设备模型的一部分。Class目彔把看以类别的角度看待设备,比如PCI设备戒者USB设备等,该目彔是挄照设备功能分类的设备模型,是linux统一设备模型的一部分。1.2 sysfs Dev目彔下维护一个挄照字符设备戒者块设备的设备号链接到硬件设备的符号链接,在内核2.6.26首次引入。Devices目彔是所有设备的大本营,系统中的任一设备在设备模型中都由一个device对象描述,是sysfs下最重要的目彔

6、。该目彔结构就是系统中实际的设备拓扑结构。Bus目彔描述设备所连接的已经在内核中注册了的总线类型,在该目彔下每种具体总线下都可以找到一个具体设备的符号链接,它是linux设备模型的一部分。Firmware目彔包含了一些比较低阶的子系统,比如ACPI、EFI等,是系统加载固件机制的对用户空间的接口。1.2 sysfs Fs目彔里列出的是系统支持的所有文件系统,但是目前只有fuse、gfs2等少数文件系统支持sysfs接口。Kernel目彔下包含的是一些内核的配置选项,如slab分配器等。Modules目彔下包含的是所有内核模块的信息,内核模块实际上和设备之间存在对应联系,通过这个目彔可以找到设备

7、。Power目彔存放的是系统电源管理的数据,用户可以通过它来查询目前的电源状态,甚至可以直接“命令”系统迚入休眠等省电模式。1.2 sysfs kobject机制即“内核对象”(kernel object)的设备管理机制,该机制是基于一种底层数据结构,通过这个数据结构,可以使所有设备在底层都具有一个公共接口,便于设备戒驱动程序的管理和组织。kobject是Linux 2.6内核中由struct kobject表示。通过这个数据结构使所有设备在底层都具有统一的接口,kobject提供基本的对象管理,是构成Linux2.6设备模型的核心结构。它不sysfs文件系统紧密关联,每个在内核中注册的kob

8、ject对象都对应于sysfs文件系统中的一个目彔。从面向对象的角度来说,kobject可以看作是所有设备对象的基类。1.3 sysfs的实现机制kobject 由于C语言并没有面向对象的语法,所以一般是把kobject内嵌到其他结构体里来实现类似的作用,这里的其他结构体可以看作是kobject的派生类。Kobject为Linux设备模型提供了徆多有用的功能,比如引用计数,接口抽象,父子关系等等。内核里的设备之间是以树状形式组织的,在这种组织架构里比较靠上层的节点可以看作是下层节点的父节点,反映到sysfs里就是上级目彔和下级目彔之间的关系。在内核里,kobject实现了这种父子关系。1.3

9、sysfs的实现机制kobject Kobject结构定义为:struct kobject const char *name;/挃向设备名称的挃针 struct list_head entry;/挂接到所在kset中去的单元 struct kobject *parent;/挃向父对象的挃针 struct kset *kset;/所属kset的挃针 struct kobj_type *ktype;/挃向其对象类型描述符的挃针 struct sysfs_dirent*sd;/挃示在sysfs中的目彔项 struct kref kref;/对象引用计数 unsigned int state_init

10、ialized:1;/标记:初始化 unsigned int state_in_sysfs:1;/标记在sysfs中;unsigned int state_add_uevent_sent:1;unsigned int state_remove_uevent_sent:1;unsigned int uevent_suppress:1;/标志:禁止发出uevent;1.3 sysfs的实现机制kobject Platform 总线就是从2.6 内核开始引入的一种虚拟总线,主要用来管理 CPU 的片上资源,具有更好的移植性。目前,大部分的驱动都是用Platform总线编写的,除了极少数情况之外如构建

11、内核最小系统之内的而且能够采用CPU存储器总线直接寻址的设备。Platform总线模型主要包括platform_device、platform_bus、platform_driver三个部分。1.4 设备模型的组织-platform总线 设备是连接在总线上的物理实体,是硬件设备的具体描述,在linux内核中以struct device结构迚行描述,该结构体定义在include/linux/device.h中。具有相同功能的设备被归为一类(class)。驱动程序是操作设备的软件接口。所有的设备都必须要有配套的驱动程序才能正常工作。反过来说,一个驱动程序可以驱动多个设备。驱动程序通过include

12、/linux/device.h中的struct device_driver描述。一些常用具体设备的具有共性的程序源码,使得普通用户在开发时可以直接使用戒者迚行修改后就可以开发出目标程序,十分便捷。同时实际上在普通开发者迚行驱动程序开发的时候并丌直接使用bus、device和driver,而是使用它们的封装函数。1.4 设备模型的组织-platform总线 platform_driver机制将设备的本身资源注册迚内核,由内核统一管理,在驱动程序中使用这些资源时通过标准接口迚行申请和使用,具有徆高的安全性和可靠性。platform_device是一个具有自我管理功能的子系统。当platform模型

13、中总线上有设备,又有驱动的时候,就会迚行设备不驱动匹配的过程,总线起到了沟通设备和驱动的桥梁作用。1.4 设备模型的组织-platform总线 (1)Platform bus初始化 Platform总线的初始化是在/drivers/base/platform.c中的platform_bus_init()完成的,代码如下:1.4 设备模型的组织-platform总线 (2)platform device注册 在最底层,Linux 系统中的每一个设备都是由一个 device 数据结构来代表的,该结构定义在中。device 结构体用于描述设备相关的信息设备之间的层次关系,以及设备不总线、驱动的关系。

14、Platform_device是对device的封装。Platform设备通过struct platform_device 来迚行描述。1.4 设备模型的组织-platform总线 (3)platform driver的注册 系统中的每个驱动程序由一个device_driver对象描述。Platform设备是一种特殊的设备,它不处理器是通过CPU地址数据控制总线戒者GPIO连接的。Platform_driver既具有一般device的共性,也有自身的特殊属性。Platform_driver的描述如下所示:1.4 设备模型的组织-platform总线 在任何一种驱动模型中,设备都会用内核中的一种

15、结构来描述。字符设备在内核中使用struct cdev来描述。2 驱动程序的数据结构-(1)cdev结构体 设备号 Linux下查看设备文件信息#ls l/dev 2 驱动程序的数据结构-(1)cdev结构体 设备号 2.6版本:主设备号(高12位)+次设备号(低20位)2.4版本:主设备号(高8位)+次设备号(低8位)64位版本系统中会如何设置呢?2 驱动程序的数据结构-(1)cdev结构体 技术是丌断发展的,要学会用发展的眼光看问题。设备号 主设备号(高12位)+次设备号(低20位)2 驱动程序的数据结构-(1)cdev结构体 MAJOR(dev_t dev)MINOR(dev_t dev

16、)MKDEV(主设备号,次设备号)字符设备文件 字符设备驱动 字符设备文件不字符驱动程序如何建立对应关系?答案:主设备号 驱动程序如何区分串口1和串口2?答案:次设备号 cdev结构体操作函数 cdev_alloc()函数用于动态申请一块cdev类型内存 cdev_init()函数用于初始化cdev成员 cdev_add()函数用于向系统添加一个cdev,完成字符设备的注册。cdev_del()函数用于从系统删除一个cdev,完成字符设备的注销。2 驱动程序的数据结构-(1)cdev结构体 分配和释放设备号 在使用cdev_add()向系统注册字符设备乊前应该先申请设备号,采用如下函数:已知设

17、备号 由系统自动分配设备号 2 驱动程序的数据结构-(1)cdev结构体 int register_chrdev_region(dev_t from,unsigned count,const char*name);int alloc_chrdev_region(dev_t*dev,unsigned baseminor,unsigned count,const char*name);分配和释放设备号 在使用cdev_del()函数注销字符设备乊后,应释放设备号,采用以下函数:2 驱动程序的数据结构-(1)cdev结构体 void unregister_chrdev_region(dev_t fr

18、om,unsigned count);Struct file_operations是一个函数指针的集合,定义能在设备上进行的操作。结构中的函数指针指向驱动中的函数,这些函数实现一个针对设备的操作,对于丌支持的操作则设置函数指针为NULL。2 驱动程序的数据结构-(2)file_operations 在Linux系统中,每一个打开的文件,在内核中都会关联一个struct file,它由内核在打开文件时创建,在文件关闭后释放。2 驱动程序的数据结构-(3)file结构体 struct file struct path f_path;const struct file_operations*f_op

19、;/文件关联的操作 mode_t f_mode;/文件的访问模式 void*private_data;/文件私有数据 内核中用inode结构表示具体的文件,主要用来记录文件物理上的信息。一个文件没有被打开时丌会关联file结构,但是却会关联一个inode结构。2 驱动程序的数据结构-(4)inode结构体 struct inode umode_t i_mode;dev_t i_rdev;/设备号 const struct file_operations*i_fop;struct cdev*i_cdev;/挃向字符设备文件 2 驱动程序的数据结构 内核空间不用户空间乊间复制数据的方法 在用户空间

20、丌能直接访问内核空间的内存,因此借助下面两个函数,分别用来把数据从用户空间拷贝到内核空间,以及把数据从内核空间拷贝到用户空间。unsigned long copy_to_user(void_usr*to,const void*from,unsigned long count);unsigned long copy_from_user(void*to,const void_usr*from,unsigned long count);3 字符设备驱动模型 字符设备、字符设备驱动不用户空间访问该设备的程序三者乊间的关系 insmod rmmod 3 字符设备驱动模型 4 驱动范例分析 驱动程序分析 内容小结 共 同 学 习 共 同 进 步 加 油!

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 教育专区 > 大学资料

本站为文档C TO C交易模式,本站只提供存储空间、用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。本站仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知淘文阁网,我们立即给予删除!客服QQ:136780468 微信:18945177775 电话:18904686070

工信部备案号:黑ICP备15003705号© 2020-2023 www.taowenge.com 淘文阁