正点原子嵌入式linux驱动开发——Linux MISC驱动

news2024/11/22 9:10:16

misc的意思是混合、杂项的,因此MISC驱动也叫做杂项驱动,也就是当板子上的某些外设无法进行分类的时候就可以使用MISC驱动。MISC驱动其实就是最简单的字符设备驱动,通常嵌套在platform总线驱动中,实现复杂的驱动,本章就来学习一下MISC驱动的编写。

MISC设备驱动简介

所有的MISC设备驱动的主设备号都为10,不同的设备使用不同的从设备号。随着Linux字符设备驱动的不断增加,设备号变得越来越紧张,尤其是主设备号,MISC设备驱动就用于解决此问题。 MISC设备会自动创建cdev,不需要手动创建,因此采用MISC设备驱动可以简化字符设备驱动的编写需要向Linux注册一个miscdevice设备,miscdevice是一个结构体,定义在文件include/linux/miscdevice.h中,内容如下:
miscdevice结构体
定义一个MISC设备(miscdevice类型)以后需要设置minor、name和fops这三个成员变量。 minor表示子设备号,MISC设备的主设备号为10,这个是固定的,需要用户指定子设备号,Linux系统已经预定义了一些MISC设备的子设备号,这些预定义的子设备号定义在include/linux/miscdevice.h文件中,如下所示:
预定义的MISC设备子设备号
在使用的时候可以从这些预定义的子设备号中挑选一个,当然也可以自己定义,只要这个子设备号没有被其他设备使用接口。

name就是此MISC设备名字,当此设备注册成功以后就会在/dev目录下生成一个名为name的设备文件。fops就是字符设备的操作集合,MISC设备驱动最终是需要使用用户提供的fops操作集合

当设置好miscdevice以后就需要使用misc_register函数向系统中注册一个MISC设备,此函数原型如下:

int misc_register(struct miscdevice * misc)

函数参数和返回值含义如下:

  • misc:要注册的MISC设备。
  • 返回值:负数,失败;0,成功。

以前需要自己调用一堆的函数去创建设备,比如在以前的字符设备驱动中会使用如下几个函数完成设备创建过程:

示例代码37.1.3 传统的创建设备过程 
1 alloc_chrdev_region(); /* 申请设备号 */ 
2 cdev_init(); /* 初始化cdev */ 
3 cdev_add(); /* 添加cdev */ 
4 class_create(); /* 创建类 */ 
5 device_create(); /* 创建设备 */

现在可以直接使用misc_register一个函数来完成示例代码37.1.3中的这些步骤。当卸载设备驱动模块的时候需要调用misc_deregister函数来注销掉MISC设备,函数原型如下:

int misc_deregister(struct miscdevice *misc)

函数参数和返回值含义如下:

  • misc:要注销的MISC设备。
  • 返回值:负数,失败;0,成功。

以前注销设备驱动的时候,需要调用一堆的函数去删除此前创建的cdev、设备等等内容,如下所示:

示例代码37.1.4 传统的删除设备的过程 
1 cdev_del(); /* 删除cdev */ 
2 unregister_chrdev_region(); /* 注销设备号 */ 
3 device_destroy(); /* 删除设备 */ 
4 class_destroy(); /* 删除类 */

现在只需要一个misc_deregister函数即可完成示例代码37.1.4中的这些工作。关于MISC设备驱动就讲解到这里,接下来就使用platform加MISC驱动框架来编写beep蜂鸣器驱动

硬件原理图分析

就是之前的BEEP蜂鸣器的原理图。

实验程序编写

本章实验采用platform加misc的方式编写beep驱动,这也是实际的Linux驱动中很常用的方法。采用platform来实现总线、设备和驱动,misc主要负责完成字符设备的创建。

修改设备树

需要在stm32mp157d-atk.dts文件中创建蜂鸣器设备节点。

添加pinctrl节点

在STM32MP157开发板上的蜂鸣器使用了PC7这个引脚,打开stm32mp15-pinctrl.dtsi文
件,在pinctrl节点下添加一个‘beep_pins_a’子节点,这个节点就是蜂鸣器的pinctrl配置。

示例代码37.3.1.1 蜂鸣器的pinctrl节点 
1 beep_pins_a: beep_pins {
2     pins { 
3         pinmux = <STM32_PINMUX('C', 7, GPIO)>; /* BEEP */ 
4         drive-push-pull; 
5         bias-pull-up; 
6         output-high; 
7         slew-rate = <0>; 
8     }; 
9 };

添加beep设备节点

之前已经添加过了,稍作修改即可:

示例代码37.3.1.2 蜂鸣器节点 
1 beep { 
2     compatible = "alientek,beep"; 
3     status = "okay"; 
4     pinctrl-names = "default"; 
5     pinctrl-0 = <&beep_pins_a>; 
6     beep-gpio = <&gpioc 7 GPIO_ACTIVE_HIGH>; 
7 };

beep驱动程序编写

设备结构体miscbeep_dev中,只需要dev_t设备号,cdev结构体的cdev,class结构体的类,device结构体的设备,以及beep_gpio这个int类型的变量存储GPIO编号。

具象化beep设备,struct miscbeep_dev miscbeep。

通过beep_gpio_init初始化beep相关,通过of_get_named_gpio获取GPIO存入miscbeep.beep_gpio;然后gpio_request申请使用GPIO;最后通过gpio_direction_output设置初始化电平以及设置为输出。

msicbeep_write函数,要记一下是static ssize_t的,里面一样通过copy_to_user把数据输入进来然后存到databuf里面,databuf再传给beepstat,从而获取状态值,根据状态变量来gpio_set_value控制蜂鸣器状态。

还需要定义miscdevice结构体的MISC设备结构体beep_miscdev,里面要初始化.minor,.name和.fops。

然后就是platform驱动的probe函数static int miscbeep_probe,里面要通过beep_gpio_init初始化BEEP,然后通过misc_register注册MISC设备。

platform的remove函数里面,需要gpio_set_value关闭BEEP,然后gpio_free释放BEEP的IO,最后misc_deregister注销MISC设备。

还需要写一个匹配列表of_device_id结构体变量的beep_of_match,里面需要有匹配的.compatible属性的设备名(与设备树中节点的匹配)。

然后写一下platform的驱动结构体,.driver中的.name需要与设备匹配,再.of_match_table填入刚刚的匹配列表;还需要些.probe和.remove函数。

最后写一下驱动的入口和出口函数,就是platform的驱动注册和驱动注销函数。

编写测试APP

这里就是argc是3个,然后filename把argv[1]传入,open打开beep驱动,然后把要执行的操作通过atoi(argv[2])传入databuf里面,之后调用write来操作,最后close关闭文件。

运行测试

编译驱动程序

老样子,修改Makefile的obj-m为miscbeep.o,然后“make”以下就可以了。

编译测试APP

可以通过如下命令编译:

arm-none-linux-gnueabihf-gcc miscbeepApp.c -o miscbeepApp

运行测试

将上一小节编译出来miscbeep.ko和miscbeepApp这两个文件拷贝到rootfs/lib/modules/5.4.31目录中,重启开发板,进入到目录lib/modules/5.4.31中,输入如下命令加载miscbeep.ko这个驱动模 块:

depmod //第一次加载驱动的时候需要运行此命令
modprobe miscbeep.ko //加载设备模块

当驱动模块加载成功以后可以在/sys/class/misc这个目录下看到一个名为“miscbeep"的子目录。所有的misc设备都属于同一个类,/sys/class/misc目录下就是misc这个类的所有设备,每个设备对应一个子目录。

驱动与设备匹配成功以后就会生成/dev/miscbeep这个设备驱动文件,输入如下命令查看这个文件的主次设备号:

ls /dev/miscbeep -l

可以通过如下命令控制BEEP:

./miscbeepApp /dev/miscbeep 1 //打开BEEP
./miscbeepApp /dev/miscbeep 0 //关闭BEEP

如果要卸载驱动的话输入如下命令即可:

rmmod miscbeep.ko

总结

这一章就是通过MISC的方法来结合platform写一个驱动。

设备结构体就得到了简化,gpio的初始化是一样的;write函数也是一样的;需要自行写一个MISC设备结构体,以及platform驱动的probe和remove函数,这两者中的注册和注销就可以直接用misc_register和misc_deregister

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1126401.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Web APIS——第一天(下)

一、随机轮播图案例 <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8" /><meta http-equiv"X-UA-Compatible" content"IEedge" /><meta name"viewport" content"widthde…

JAVA多线程基础篇--守护线程(Daemon Thread)

1.概述 JAVA中的线程主要分为两类&#xff1a;用户线程&#xff08;User Thread&#xff09;和守护线程(Daemon Thread)。JAVA语言中无论是线程还是线程池&#xff0c;默认都是用户线程&#xff0c;因此用户线程也被称为普通线程。守护线程也被称之为后台线程、服务线程或精灵…

LeetCode977——有序数组的平方

LeetCode977——有序数组的平方 给你一个按 非递减顺序 排序的整数数组 nums&#xff0c;返回 每个数字的平方 组成的新数组&#xff0c;要求新数组也按 非递减顺序 排序。 输入&#xff1a;nums [-4,-1,0,3,10] 输出&#xff1a;[0,1,9,16,100] 解释&#xff1a;平方后&…

【ECS游戏架构】逻辑帧驱动带来的性能和即时性问题分析

1024水一篇~ 个人拙见&#xff0c;如有错误希望大佬拔刀纠正。 根据守望先锋在GDC会议上对ECS架构的描述&#xff0c;所有的系统(system)都是由逻辑帧驱动的&#xff1a;每帧遍历所有的system&#xff0c;并调用system的update()更新游戏世界的状态。 在实际应用中这可能会存…

缓存分片中的哈希算法与一致性哈希算法

什么是缓存分片 在高并发场景下&#xff0c;缓存往往成为了瓶颈。这时候&#xff0c;我们可以通过缓存数据分片的方式来解决问题。所谓缓存数据分片&#xff0c;就是将缓存数据按照一定的规则分成多个片段&#xff0c;每个片段由不同的缓存节点负责。这样做有两个好处&#xf…

广告掘金全自动挂机项目,单设备30+【软件脚本+技术教程】

广告掘金项目是一种越来越受欢迎的赚钱方式&#xff0c;它通过观看广告视频来获取收益。然而&#xff0c;手动观看每个广告视频可能会耗费大量时间和精力。为了简化操作并提升效率&#xff0c;我们可以利用全自动挂机脚本来完成这一任务。接下来&#xff0c;将为您介绍如何使用…

proxmox pve /dev/mapper/pve-root扩容

vgs3 pvs4 vgs5 lvs6 lvremove /dev/pve/data8 lvresize -l 100%FREE /dev/pve/root9 resize2fs /dev/mapper/pve-root 10 history

爆肝整理,Pytest+Allure+Jenkins自动化测试集成实战(图文详细步骤)

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 1、简介 pytesta…

宝塔FTP提示:553 Can‘t open that file: Permission denied的解决方案

[2023-10-18 15:16] 无法传输文件 ‘D:\phpstudy_pro\WWW\lockgis\static\js\coordtransform.js’。Cant open output connection for file “ftp://iot.test.net/lockgis/static/js/coordtransform.js”. Reason: “553 Can’t open that file: Permission denied”. 原因分析…

美国国防部网络战略如何改变国家网络防御

十年前&#xff0c;时任国防部长莱昂帕内塔说了一句后来臭名昭著的短语&#xff1a;“网络珍珠港”。帕内塔利用他作为该国主要国家安全官员的平台来警告美国未来将遭受可怕的数字攻击。 他警告说&#xff0c;能源基础设施、交通系统、金融平台等都容易受到剥削。媒体、专家和…

基于C语言 --- 自己写一个通讯录

C语言程序设计笔记---039 C语言之实现通讯录1、介绍C/C程序的内存开辟2、C语言实现通讯录2.1、ContactMain.c程序大纲2.2、Contact2.h2.3、Contact2.c2.3.1 InitContact( )初始化通讯录函数2.3.2 AddContact( )添加联系人和CheckCapaticy( )检查容量函数2.3.3、ShowContact( )显…

重大技术问题,iPhone 15 Pro Max面临“烧屏门”风波 | 百能云芯

近期&#xff0c;社交媒体平台上陆续涌现大量用户和数码博主就iPhone 15 Pro Max出现烧屏问题的投诉与评论。 烧屏问题是OLED屏幕常见的一个缺陷&#xff0c;这是由OLED屏幕发光机制引发的&#xff0c;OLED屏幕可视为由无数微小的灯泡-像素点构成&#xff0c;这些像素点可以独立…

redis场用命令及其Java操作

目录 1. Redis入门 1.1 Redis简介 1.2 Redis下载与安装 1.2.1 Redis下载 1.2.2 Redis安装 1.3 Redis服务启动与停止 1.3.1 服务启动命令 1.3.2 客户端连接命令 1.3.3 修改Redis配置文件 1.3.4 Redis客户端图形工具 2. Redis数据类型 2.1 五种常用数据类型介绍 2.2 …

【单片机基础】按键状态机实现短按、长按、双击、三击和N击

下载地址&#xff1a; 【CSDNNaiva】源码&#xff1a;HK32F030M-按键扫描-短按长按检测 参考资料 [1] 【CSDNPillarPeng】【按键】[独立按键] - 1&#xff1a; 单击&#xff0c;双击&#xff0c;三击以及N击 [2] 【CSDNPillarPeng】【按键】[独立按键] - 2&#xff1a;双击 …

git简介和指令

git是一个开源的的分布式版本控制系统&#xff0c;用于高效的管理各种大小项目和文件 用途&#xff1a;防止代码丢失&#xff0c;做备份 项目的版本管理和控制&#xff0c;可以通过设置节点进行跳转 建立各自的开发环境分支&#xff0c;互不影响&#xff0c;方便合并 在多终端开…

git pull 和 git fetch 有什么区别?

一、是什么 先回顾两个命令的定义 git fetch 命令用于从另一个存储库下载对象和引用git pull 命令用于从另一个存储库或本地分支获取并集成(整合) 再来看一次git的工作流程图&#xff0c;如下所示&#xff1a; 可以看到&#xff0c;git fetch是将远程主机的最新内容拉到本地…

md5算法实现

前言 md5算法是我们经常会用到的一个hash函数, 虽然已经被证明是不安全的了, 但其应用依然十分广泛. 哈希函数具有如下特点: 将任意长度的字符串映射为固定长度源数据微小的改动会导致结果差异巨大不可逆暴力破解困难 你有没有好奇过, 哈希函数是如何做到这些的呢? 本文就…

LSTM 与 GRU

RNN无法处理长距离依赖问题&#xff0c;通俗点就是不能处理一些较长的序列数据&#xff0c;那么今天就来介绍一下两个能处理长距离依赖问题地RNN变种结构&#xff0c;LSTM和GRU。 1. LSTM&#xff08;Long short-term memory&#xff09; 1.1 LSTM结构 上左图是普通RNN结构图…

深入浅出排序算法之归并排序

目录 1. 归并排序的原理 1.1 二路归并排序执行流程 2. 代码分析 2.1 代码设计 3. 性能分析 4. 非递归版本 1. 归并排序的原理 “归并”一词的中文含义就是合并、并入的意思&#xff0c;而在数据结构中的定义是将两个或者两个以上的有序表组合成一个新的有序表。 归并排序…

前端性能优化 - 虚拟滚动

一 需求背景 需求&#xff1a;在一个表格里面一次性渲染全部数据&#xff0c;不采用分页形式&#xff0c;每行数据都有Echart图插入。 问题&#xff1a;图表渲染卡顿 技术栈&#xff1a;Element UI 卡顿原因&#xff1a;页面渲染时大量的元素参与到了重排的动作中&#xff0c;…