0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

嵌入式Linux驱动程序的开发要点有哪些

Wildesbeast 来源:21IC 作者:21IC 2020-08-15 10:51 次阅读
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

学习过linux的都知道,Linux操作系统下有3类主要的设备文件类型:块设备、字符设备和网络设备。这种分类方法可以将控制输入/输出设备的驱动程序与其他操作系统软件分离开来。

字符设备与块设备的主要区别是:在对字符设备发出读/写请求时,实际的硬件I/O一般紧接着发生。块设备则不然,它利用一块系统内存作为缓冲区,若用户进程对设备的请求能满足用户的要求,就返回请求的数据;否则,就调用请求函数来进行实际的I/O操作。块设备主要是针对磁盘等慢速设备设计的,以免耗费过多的CPU时间用来等待。网络设备可以通过BSD接口访问数据。

每个设备文件都有其文件属性(c/b),表示是字符设备还是块设备。另外每个文件都有2个设备号,第一个是主设备号,标识驱动程序;第二个是从设备号,标识使用同一个设备驱动程序的、不同的硬件设备。设备文件的主设备号必须与设备驱动程序在登记时申请的主设备号一致,否则用户进程将无法访问驱动程序。

系统调用时操作系统内核与应用程序之间的接口,设备驱动程序是操作系统内核与机器硬件之间的接口。设备驱动程序是内核的一部分,它完成以下功能:

*对设备初始化和释放

*把数据从内核传送到硬件和从硬件读取数据

*读取应用程序传送给设备文件的数据和回送应用程序请求的数据

*检测和处理设备出现的错误

MTD(Memory Technology Device)设备是闪存芯片、小型闪存卡、记忆棒之类的设备,它们在嵌入式设备中的使用正在不断增加。MTD驱动程序是在Linux下专门为嵌入式环境开发的新的一类驱动程序。相对于常规块设备驱动程序,使用MTD驱动程序的优点在于他们能更好的支持、管理给予闪存设备,有基于扇区的擦除和读/写操作的更好的接口。

驱动程序结构

Linux的设备驱动程序可以分为3个主要组成部分:

1. 自动配置和初始化子程序,负责监测所要驱动的硬件设备是否存在和能否正常工作。如果该设备正常,则对这个设备及其相关的设备驱动程序需要的软件状态进行初始化。这部分驱动程序仅在初始化时被调用一次。

2. 服务于I/O请求的子程序,又称为驱动程序的上半部分。调用这部分程序是由于系统调用的结果。这部分程序在执行时,系统仍认为是与进行调用的进程属于同一个进程,只是由用户态变成了核心态,具有进行此系统调用的用户程序的运行环境,因而可以在其中调用sleep()等与进行运行环境有关的函数。

3. 中断服务子程序,又称为驱动程序的下半部分。在Linux系统中,并不是直接从中断向量表中调用设备驱动程序的中断服务子程序,而是由Linux系统来接收硬件中断,再由系统调用中断服务子程序。中断可以在任何一个进程运行时产生,因而在中断服务程序被调用时,不能依赖于任何进程的状态,也就不能调用任何与进程运行环境有关的函数。因为设备驱动程序一般支持同一类型的若干设备,所以一般在系统调用中断服务子程序时,都带有一个或多个参数,以唯一标识请求服务的设备。

在系统内部,I/O设备的存/取通过一组固定的入口点来进行,这组入口点是由每个设备的驱动程序提供的。具体到Linux系统,设备驱动程序所提供的这组入口点由一个文件操作结构来向系统进行说明。file_operation结构定义于linux/fs.h文件中。

struct file_operaTIon{

int (*lseek)(struct inode *inode, struct file *filp, off_t off, int pos);

int (*read)(struct inode *inode, struct file *filp, char *buf, int count);

int (*write)(struct inode *inode, struct file *filp, const char *buf, int count);

int (*readdir)(struct inode *inode, struct file *filp, struct dirent *dirent, int count);

int (*select)(struct inode *inode, struct file *filp, int sel_type, select_table *wait);

int (*ioctl)(struct inode *inode, struct file *filp, unsigned int cmd, unsigned int arg);

int (*mmap)(void);

int (*open)(struct inode *inode, struct file *filp);

int (*release)(struct inode *inode, struct file *filp);

int (*fasync)(struct inode *inode, struct file *filp);

};

file_operaTIon结构中的成员几乎全部是函数指针,所以实质上就是函数跳转表。每个进程对设备的操作都会根据major、minor设备号,转换成对file_operaTIon结构的访问。

常用的操作包括以下几种:

*lseek, 移动文件指针的位置,只能用于可以随机存取的设备。

*read, 进行读操作,参数buf为存放读取结果的缓冲区,count为所要读取的数据长度。返回值为负表示读取操作发生错误;否则,返回实际读取的字节数。对于字符型,要求读取的字节数和返回的实际读取字节数都必须是inode-i_blksize的倍数。

*write, 进行写操作,与read类似

*readdir, 取得下一个目录入口点,只有与文件系统相关的设备程序才使用。

*select, 进行选择操作。如果驱动程序没有提供select入口,select操作会认为设备已经准备好进行任何I/O操作。

*ioctl, 进行读、写以外的其他操作,参数cmd为自定义的命令

*mmap, 用于把设备的内容映射到地址空间,一般只有块设备驱动程序使用

*open, 打开设备准备进行I/O操作。返回0表示打开成功,返回负数表示失败。如果驱动程序没有提供open入口,则只要/dev/driver文件存在就认为打开成功。

*release, 即close操作。

在用户自己的驱动程序中,首先要根据驱动程序的功能,完成file_operaTIon结构中函数实现。不需要的函数接口可以直接在file_operation结构中初始化为NULL。file_operation变量会在驱动程序初始化时注册到系统内部。当操作系统对设备操作时,会调用驱动程序注册的file_operation结构中的函数指针。

Linux对中断的处理

在Linux系统里,对中断的处理是属于系统核心部分,因而如果设别与系统之间以中断方式进行数据交换,就必须把该设备的驱动程序作为系统核心的一部分。设备驱动程序通过调用request_irq函数来申请中断,通过free_irq来释放中断。它们被定义为:

#include

int request_irq(unsigned int irq,

void (*handler)(int irq, void dev_id, struct pt_regs *regs),

unsigned long flags,

const char *device,

void *dev_id);

void free_irq(unsigned int irq, void *dev_id);

参数irq表示所要申请的硬件中断号;handler为向系统登记的中断处理子程序,中断产生时由系统来调用,调用时所带参数irq为中断号;dev_id为申请时告诉系统的设备标识;regs为中断发生时的寄存器内容;device为设备名,将会出现在/proc/interrupts文件里;flag是申请时的选项,它决定中断处理程序的一些特性,其中最重要的是中断处理程序是快速处理程序还是慢速处理程序。快速处理程序运行时,所有中断都被屏蔽,而慢速处理程序运行时,除了正在处理的中断外,其他中断都没有被屏蔽。在Linux系统中,中断可以被不同的中断处理程序共享。

作为系统核心的一部分,设备驱动程序在申请和释放内存时不是调用malloc和free,而代之以调用kmalloc和kfree,它们被定义为:

#include

void *kmalloc(unsigned int len, int priority);

void kfree(void *obj);

参数len为希望申请的字节数;obj为要释放的内存指针;priority为分配内存操作的优先级,即在没有足够空闲内存时如何操作,一般用GFP_KERNEL。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • cpu
    cpu
    +关注

    关注

    68

    文章

    11337

    浏览量

    226009
  • Linux
    +关注

    关注

    88

    文章

    11825

    浏览量

    219616
  • 驱动程序
    +关注

    关注

    19

    文章

    872

    浏览量

    50812
收藏 人收藏
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

    评论

    相关推荐
    热点推荐

    从架构到驱动:这三本经典书,承包了我的嵌入式Linux入门与进阶

    作为一个深耕嵌入式领域的开发者,书架上总有几本“压箱底” 的书 —— 它们既是新手入门的灯塔,也是老手复盘的手册。今天想和大家聊聊几本经典的书,《ARM64 体系结构编程与实践》《鸟哥的 Linux
    的头像 发表于 02-09 17:02 1392次阅读

    嵌入式驱动开发,需要掌握哪些技能?

    嵌入式驱动开发中,方便设备管理、驱动移植等,所以,需要掌握一定的数据结构。 3、 操作系统知识如果基于Linux、RTOS等操作系统设
    发表于 01-20 16:46

    Linux开发嵌入式必备命令速查表

    嵌入式开发中,Linux系统几乎成为必备的开发环境。不管你是在做STM32、RaspberryPi、还是基于ARM的板子,熟练掌握Linux命令不仅能加快
    的头像 发表于 01-19 09:06 1058次阅读
    <b class='flag-5'>Linux</b> 下<b class='flag-5'>开发</b><b class='flag-5'>嵌入式</b>必备命令速查表

    什么是嵌入式应用开发

    概述 所谓的嵌入式应用开发就是在嵌入式操作系统下进行开发、软硬件综合开发嵌入式应用
    发表于 01-12 16:13

    迅为Hi3403开发驱动教程全面上线,开启嵌入式Linux开发新篇章!

    迅为iTOP-Hi3403开发linux驱动教程全面上线,开启嵌入式Linux开发新篇章!
    的头像 发表于 12-18 14:23 932次阅读
    迅为Hi3403<b class='flag-5'>开发</b>板<b class='flag-5'>驱动</b>教程全面上线,开启<b class='flag-5'>嵌入式</b><b class='flag-5'>Linux</b><b class='flag-5'>开发</b>新篇章!

    从小白到大牛:Linux嵌入式系统开发的完整指南

    编写简单的 Shell 脚本(如自动备份文件、批量编译程序)巩固技能。​ 二、能力进阶:攻克核心技术模块​ 入门后需聚焦嵌入式 Linux 的核心技术栈,分模块突破,形成系统化能力:​ 内核与
    发表于 12-16 10:42

    一个面向单片机、事件驱动嵌入式开发平台介绍

    EventOS,是一个面向单片机、事件驱动嵌入式开发平台。它主要有两大技术特色:一是事件驱动,二是超轻量。EventOS以及其母项目EventOS,目标是开发一个企业级的
    发表于 12-05 06:26

    CW32嵌入式软件开发的必备知识

    嵌入式系统中最常用的编程语言,因为它们提供了直接访问硬件的能力,并且代码执行效率高。 了解汇编语言,用于编写底层驱动、中断处理程序以及性能要求极高的代码段。 对其他编程语言如Python、Java等
    发表于 11-28 07:48

    C语言在嵌入式开发中的应用

    C 语言在汽车电子控制系统开发中的主导地位。 2、设备驱动程序 设备驱动程序嵌入式系统中连接硬件和软件的桥梁,它负责实现嵌入式系统与
    发表于 11-21 08:09

    【书籍评测活动NO.67】成为硬核Linux开发者:《Linux 设备驱动开发(第 2 版)》

    工程师、Linux系统管理员及开发人员学习,助力其从零开始掌握嵌入式设备驱动编写。吃透《Linux 设备
    发表于 11-17 17:52

    为什么嵌入式驱动开发工程师可以拿高薪

    嵌入式驱动开发工程师能拿到高薪,核心在于这个岗位刚好踩中了行业刚需、技术壁垒高、人才缺口大这三个关键节点,而且这种需求还在随着智能硬件的普及持续扩大。首先得明确,嵌入式
    的头像 发表于 10-30 16:37 1029次阅读
    为什么<b class='flag-5'>嵌入式</b><b class='flag-5'>驱动</b><b class='flag-5'>开发</b>工程师可以拿高薪

    嵌入式需要掌握哪些核心技能?

    嵌入式需要掌握哪些核心技能? 若想通过学习嵌入式技术提升就业竞争力,需重点掌握C语言、嵌入式硬件架构、RTOS/Linux开发、通信协议四
    发表于 10-21 16:25

    为FreeRTOS增加新的设备驱动程序

    如果你正在使用FreeRTOS构建嵌入式系统,并且考虑添加新的设备驱动程序,那么这篇文章很适合你。高效的设备集成不仅仅是让设备功能正常运行——更关乎模块化、可靠性和安全性。
    的头像 发表于 08-06 15:44 1136次阅读
    为FreeRTOS增加新的设备<b class='flag-5'>驱动程序</b>

    Linux嵌入式和单片机嵌入式的区别?

    新的应用程序驱动程序来扩展功能。 6. 开发难度 : 单片机嵌入式开发难度相对较低,适合初学者入门。
    发表于 06-20 09:46

    嵌入式开发入门指南:从零开始学习嵌入式

    基础 3. 学习路径推荐第一阶段:熟悉开发环境(如Keil、IAR、STM32)第二阶段:掌握裸机编程与驱动开发第三阶段:学习RTOS(实时操作系统)如FreeRTOS第四阶段:深入理解Lin
    发表于 05-15 09:29