当前位置: 首页 > news >正文

驱动DAY9

驱动文件

#include <linux/init.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/of_gpio.h>
#include <linux/gpio.h>
#include <linux/fs.h>
#include <linux/io.h>
#include <linux/device.h>
#include <linux/cdev.h>
#include <linux/uaccess.h>
#include <linux/slab.h>
#include <linux/platform_device.h>
#include <linux/mod_devicetable.h>
#include <linux/of_irq.h>
#include <linux/interrupt.h>//获取资源结构体
struct resource *res;
//中断号
unsigned int irqno;
//gpio信息结构体
struct gpio_desc *gpiono;
//字符设备驱动对象空间首地址
struct cdev *cdev;
char kbuf[128] = {0};
//主设备号
unsigned int major = 0;
//次设备号
unsigned int minor = 0;
//设备号
dev_t devno;
module_param(major,uint,0664);  //方便在命令行传递major的值
//用于保存目录信息
struct class *cls;
//用于保存设备节点信息
struct device *dev;
int number = 0;
unsigned int condition = 0;
wait_queue_head_t wq_head;//中断处理函数
irqreturn_t key_handler(int irq,void *dev)
{gpiod_set_value(gpiono,!(gpiod_get_value(gpiono)));number = !number;condition = 1;wake_up_interruptible(&wq_head);return IRQ_HANDLED;
}int mycdev_open(struct inode *inode, struct file *file)
{printk("%s:%s:%d\n",__FILE__,__func__,__LINE__);return 0;
}
ssize_t mycdev_read(struct file *file, char  *ubuf, size_t size, loff_t *lof)
{printk("%s:%s:%d\n",__FILE__,__func__,__LINE__);int ret;//向用户空间读取拷贝if(size>sizeof(number))//用户空间期待读取的大小内核满足不了,那就给内核支持的最大大小size=sizeof(number);//切换进程为休眠态wait_event_interruptible(wq_head,condition);ret=copy_to_user(ubuf,&number,size);if(ret)//拷贝失败{printk("copy_to_user filed\n");return ret;}condition = 0;return 0;
}int mycdev_close(struct inode *inode, struct file *file)
{printk("%s:%s:%d\n",__FILE__,__func__,__LINE__);return 0;
}//定义操作方法结构体变量并赋值
struct file_operations fops={.open=mycdev_open,.read=mycdev_read,.release=mycdev_close,
};
//封装probe函数
int pdrv_probe(struct platform_device *pdev)
{int ret;// 为字符设备驱动对象申请空间cdev = cdev_alloc();if (cdev == NULL){printk("字符设备驱动对象申请空间失败\n");ret = -EFAULT;goto out1;}printk("申请对象空间成功\n");// 初始化字符设备驱动对象cdev_init(cdev, &fops);// 申请设备号if (major > 0) // 静态指定设备号{ret = register_chrdev_region(MKDEV(major, minor), 3, "myplatform");if (ret){printk("静态申请设备号失败\n");goto out2;}}else if (major == 0) // 动态申请设备号{ret = alloc_chrdev_region(&devno, minor, 3, "myplatform");if (ret){printk("动态申请设备号失败\n");goto out2;}major = MAJOR(devno); // 获取主设备号minor = MINOR(devno); // 获取次设备号}printk("申请设备号成功\n");// 注册字符设备驱动对象ret = cdev_add(cdev, MKDEV(major, minor), 3);if (ret){printk("注册字符设备驱动对象失败\n");goto out3;}printk("注册字符设备驱动对象成功\n");// 向上提交目录信息cls = class_create(THIS_MODULE, "myplatform");if (IS_ERR(cls)){printk("向上提交目录失败\n");ret = -PTR_ERR(cls);goto out4;}printk("向上提交目录成功\n");// 向上提交设备节点信息int i;for (i = 0; i < 3; i++){dev = device_create(cls, NULL, MKDEV(major, i), NULL, "myplatform%d", i);if (IS_ERR(dev)){printk("向上提交设备节点信息失败\n");ret = -PTR_ERR(dev);goto out5;}}printk("向上提交设备信息成功\n");//初始化等待队列头init_waitqueue_head(&wq_head);//获取MEM类型的资源res = platform_get_resource(pdev,IORESOURCE_MEM,0);if(res == NULL){printk("获取MEM类型资源失败\n");return -ENXIO;}//获取中断类型的资源irqno = platform_get_irq(pdev,0);if(irqno < 0){printk("获取中断类型资源失败\n");return -ENXIO;}//注册中断int ret1 = request_irq(irqno,key_handler,IRQF_TRIGGER_FALLING,"key_int",NULL);if(ret1<0){printk("注册按键1中断失败\n");return ret1;}printk("注册按键1中断成功\n");printk("mem资源%llx\n",res->start);printk("irq资源%d\n",irqno);printk("%s;%s:%d\n",__FILE__,__func__,__LINE__);//设备树匹配成功后,设备树节点指针可以通过pdev->dev.of_node获取//基于设备树节点信息获取gpio_desc对象指针gpiono = gpiod_get_from_of_node(pdev->dev.of_node,"led1-gpio",0,GPIOD_OUT_LOW,NULL);if(IS_ERR(gpiono)){printk("解析GPIO管脚信息失败\n");return -ENXIO;}printk("解析GPIO管脚信息成功\n");return 0;
out5:// 释放前一次提交成功的设备信息for (--i; i >= 0; i--){device_destroy(cls, MKDEV(major, i));}class_destroy(cls); // 释放目录
out4:cdev_del(cdev);
out3:unregister_chrdev_region(MKDEV(major, minor), 3);
out2:kfree(cdev);
out1:return ret;
}
//封装remove函数
int pdrv_remove(struct platform_device *pdev)
{//关灯gpiod_set_value(gpiono,0);//释放GPIO信息gpiod_put(gpiono);//注销中断free_irq(irqno,NULL);// 释放节点信息int i;for (i = 0; i < 3; i++){device_destroy(cls, MKDEV(major, i));}// 销毁目录class_destroy(cls);// 注销驱动对象cdev_del(cdev);// 释放设备号unregister_chrdev_region(MKDEV(major, minor), 3);// 释放对象空间kfree(cdev);printk("%s;%s:%d\n",__FILE__,__func__,__LINE__);return 0;
}
//构建设备树匹配表
struct of_device_id oftable[] = {{ .compatible = "hqyj,myplatform"},{ /* end node */ },//防止数组越界
};
//定义驱动信息对象并初始化
struct platform_driver pdrv = {.probe = pdrv_probe,.remove = pdrv_remove,.driver = {.name = "bbbbb",.of_match_table=oftable,//用于设备树匹配 },
};//一键注册宏
module_platform_driver(pdrv);MODULE_LICENSE("GPL");

应用程序

#include<stdlib.h>
#include<stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include<unistd.h>
#include<string.h>int main(int argc, char const *argv[])
{int num;int fd=open("/dev/myplatform0",O_RDWR);if(fd<0){printf("打开设备文件失败\n");exit(-1);}while(1){read(fd,&num,sizeof(num));printf("num = %d\n",num);}close(fd);return 0;
}

相关文章:

驱动DAY9

驱动文件 #include <linux/init.h> #include <linux/module.h> #include <linux/of.h> #include <linux/of_gpio.h> #include <linux/gpio.h> #include <linux/fs.h> #include <linux/io.h> #include <linux/device.h> #incl…...

03贪心:摆动序列

03贪心&#xff1a;摆动序列 376. 摆动序列 局部最优&#xff1a;删除单调坡度上的节点&#xff08;不包括单调坡度两端的节点&#xff09;&#xff0c;那么这个坡度就可以有两个局部峰值。 整体最优&#xff1a;整个序列有最多的局部峰值&#xff0c;从而达到最长摆动序列。…...

javascript获取元素在浏览器中工作区域的左、右、上、下距离,或带滚动条的元素在页面中的大小

//获取元素在包含元素框中的大小 //第1个函数为获取元素在包含元素中左内边框的距离 function getELementLeft(element){//获取元素在包含元素左边距离var actualeftelement.offsetLeft;//获取元素的上级包含元素var currentelement.offsetParent;//循环到一直没有包含元素whil…...

VSCode 安装使用教程 环境安装配置 保姆级教程

一个好用的 IDE 不仅能提升我们的开发效率&#xff0c;还能让我们保持愉悦的心情&#xff0c;这样才是非常 Nice 的状态 ^_^ 那么&#xff0c;什么是 IDE 呢 &#xff1f; what IDE&#xff08;Integrated Development Environment&#xff0c;集成开发环境&#xff09;是含代码…...

c盘中temp可以删除吗?appdata\local\temp可以删除吗?

http://www.win10d.com/jiaocheng/22594.html C盘AppData文件夹是一个系统文件夹&#xff0c;里面存储着临时文件&#xff0c;各种应用的自定义设置&#xff0c;快速启动文件等。近期有用户发现appdata\local\temp占用了大量的空间&#xff0c;那么该文件可以删除吗&#xff1f…...

Java手写聚类算法

Java手写聚类算法 1. 算法思维导图 以下是聚类算法的实现原理的思维导图&#xff0c;使用Mermanid代码表示&#xff1a; #mermaid-svg-AK9EgYRS38PkRJI4 {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-AK9EgYRS38…...

解密Java多线程中的锁机制:CAS与Synchronized的工作原理及优化策略

目录 CAS什么是CASCAS的应用ABA问题异常举例 Synchronized 原理基本特征加锁过程偏向锁轻量级锁重量级锁 其他优化操作锁消除锁粗化 CAS 什么是CAS CAS: 全称Compare and swap&#xff0c;字面意思:”比较并交换“&#xff0c;CAS涉及如下操作&#xff1a; 假设内存中的原数据…...

solid works草图绘制与设置零件特征的使用说明

&#xff08;1&#xff09;草图绘制 • 草图块 在 FeatureManager 设计树中&#xff0c;您可以隐藏和显示草图的单个块。您还可以查看块是欠定义 (-)、过定义 () 还是完全定义。 要隐藏和显示草图的单个块&#xff0c;请在 FeatureManager 设计树中右键单击草图块&#xff0c;…...

vue3使用router.push()页面跳转后,该页面不刷新问题

文章目录 原因分析最优解决 原因分析 这是一个常见问题&#xff0c;当使用push的时候&#xff0c;会向history栈添加一个新记录&#xff0c;这个时候&#xff0c;再添加一个完全相同的路由时&#xff0c;就不会再次刷新了 最优解决 在页面跳转时加上params参数时间 router.…...

如何理解数字工厂管理系统的本质

随着科技的飞速发展和数字化转型的推动&#xff0c;数字工厂管理系统逐渐成为工业4.0时代的重要工具。数字工厂系统旨在整合和优化工厂运营的各个环节&#xff0c;通过实时数据分析和处理&#xff0c;提升生产效率&#xff0c;降低成本&#xff0c;并增强企业的整体竞争力。为了…...

笔记1.3 数据交换

如何实现数据通过网络核心从源主机到达目的主机&#xff1f; 数据交换 交换网络&#xff1a; 动态转接动态分配传输资源 数据交换类型&#xff1a; &#xff08;1&#xff09;电路交换 &#xff08;2&#xff09;报文交换 &#xff08;3&#xff09;分组交换 电路交换的特…...

实时车辆行人多目标检测与跟踪系统(含UI界面,Python代码)

算法架构&#xff1a; 目标检测&#xff1a;yolov5 目标跟踪&#xff1a;OCSort其中&#xff0c; Yolov5 带有详细的训练步骤&#xff0c;可以根据训练文档&#xff0c;训练自己的数据集&#xff0c;及其方便。 另外后续 目标检测会添加 yolov7 、yolox&#xff0c;目标跟踪会…...

谷歌AI机器人Bard发布强大更新,支持插件功能并增强事实核查;全面整理高质量的人工智能、机器学习、大数据等技术资料

&#x1f989; AI新闻 &#x1f680; 谷歌AI机器人Bard发布强大更新&#xff0c;支持插件功能并增强事实核查 摘要&#xff1a;谷歌的人工智能聊天机器人Bard发布了一项重大更新&#xff0c;增加了对谷歌应用的插件支持&#xff0c;包括 Gmail、Docs、Drive 等&#xff0c;并…...

NI SCXI-1125 数字量控制模块

NI SCXI-1125 是 NI&#xff08;National Instruments&#xff09;生产的数字量控制模块&#xff0c;通常用于工业自动化和控制系统中&#xff0c;以进行数字输入和输出控制。以下是该模块的一些主要产品特点&#xff1a; 数字量输入&#xff1a;SCXI-1125 模块通常具有多个数字…...

链表oj题1(Leetcode)——移除链表元素,反转链表,链表的中间节点,

链表OJ 一&#xff0c;移除链表元素1.1分析1.2代码 二&#xff0c;找到链表的中间节点2.1分析2.2代码 三&#xff0c;反转链表3.1分析3.2代码 四&#xff0c;找到链表中倒数第k个节点4.1分析4.2代码 一&#xff0c;移除链表元素 移除链表元素 1.1分析 这里的删除要分成两种…...

【libuv】与uvgrtrp的_SSIZE_T_定义不同

libuv的 #if !defined(_SSIZE_T_) && !defined(_SSIZE_T_DEFINED) typedef intptr_t ssize_t;...

安卓ROM定制 修改必备常识-----初步了解system系统分区文件夹的基本含义 【二】

安卓修改rom 固件 修改GSI 移植rom 必备常识 lib--**so文件基本解析 一起来了解system目录相应文件的用途吧。&#xff08;rom版本不同里面的app也会不一样&#xff09; 简单打开img格式后缀文件 给大家说下最简单的方法提取img里面的文件&#xff0c;对于后缀img格式的文件可…...

GPT会统治人类吗

一 前言 花了大概两天时间看完《这就是ChatGPT》&#xff0c;触动还是挺大的&#xff0c;让我静下来&#xff0c;认真地想一想&#xff0c;是否真正理解了ChatGPT&#xff0c;又能给我们以什么样的启发。 二 思考 在工作和生活中&#xff0c;使用ChatGPT或文心一言&#xff0c;…...

win系统环境搭建(六)——Windows安装nginx

windows环境搭建专栏&#x1f517;点击跳转 win系统环境搭建&#xff08;六&#xff09;——Windows安装nginx 本系列windows环境搭建开始讲解如何给win系统搭建环境&#xff0c;本人所用系统是腾讯云服务器的Windows Server 2022&#xff0c;你可以理解成就是你用的windows10…...

Java中使用BigDecimal类相除保留两位小数

问题 遇到2个数相除&#xff0c;需要保留2位小数的结果。 解决 BigDecimal sum ...; BigDecimal yearValue ...;MathContext mathContext new MathContext(2, RoundingMode.DOWN); yearValue.divide(sum, mathContext);...

激光雷达在ADAS测试中的应用与方案

在科技高速发展的今天&#xff0c;汽车智能化已是必然的趋势&#xff0c;且自动驾驶汽车的研究也在世界范围内进行得如火如荼。而在ADAS测试与开发中&#xff0c;激光雷达以其高性能和高精度占据着非常重要的地位&#xff0c;它是ADAS测试与开发中不可缺少的组成。 一 激光雷达…...

malloc与free

目录 前提须知&#xff1a; malloc&#xff1a; 大意&#xff1a; 头文件&#xff1a; 申请空间&#xff1a; 判断是否申请成功&#xff1a; 使用空间&#xff1a; 结果&#xff1a; 整体代码&#xff1a; malloc申请的空间怎么回收呢? 注意事项&#xff1a; free:…...

计算周包材,日包材用来发送给外围系统

文章目录 1 Introduction2 code 1 Introduction In this example We get data from BOM and RESB . and calculate it . 2 code TYPES: BEGIN OF TY_ZPPT_0015_W,AUFNR TYPE ZPPT_0015-AUFNR,ZXH TYPE ZPPT_0015-ZXH,ZZJHID TYPE ZPPT_0015-ZZJHID,ZRJHID TYPE Z…...

R语言柱状图直方图 histogram

柱状图简介 柱状图也叫直方图&#xff0c;是展示连续性数值的分布状况。在x轴上将连续型数值分为一定数量的组&#xff0c;y轴显示对应值的频数。 R基本的柱状图 hist 我们用R自带的Orange数据来画图。 > head(Orange)Tree age circumference(圆周长) 1 1 118 …...

Linux磁盘管理:最佳实践

&#x1f337;&#x1f341; 博主猫头虎&#xff08;&#x1f405;&#x1f43e;&#xff09;带您 Go to New World✨&#x1f341; &#x1f984; 博客首页——&#x1f405;&#x1f43e;猫头虎的博客&#x1f390; &#x1f433; 《面试题大全专栏》 &#x1f995; 文章图文…...

uni-app:通过三目运算动态增加样式效果(class)

效果 代码 第一条&#xff1a;当变量line的值等于abc时&#xff0c;class就等于yes,反之class等于no&#xff08;显然等于abc&#xff0c;执行yes,前景色为红色&#xff09; 第一条&#xff1a;当变量line1的值等于abc时&#xff0c;class就等于yes,反之class等于no&#xff…...

API安全

1 API的简介 API代表应用程序编程接口,它由一组允许软件组件进行通信的定义和协议组成。作为软件系统之间的中介,API使软件应用程序或服务能够共享数据和功能。但是API不仅仅提供连接基础,它还管理软件应用程序如何被允许进行通信和交互。API控制程序之间交换请求的类型、请…...

手写一个翻页功能

最近在对接海康摄像头&#xff0c;需要写一个翻页得功能&#xff0c;于是乎就想到了手写&#xff0c;然后就记录一下。在vue项目里写的 <img:src"require()"alt""click"onNext(delete)"/><img:src"require()"alt""…...

element show-overflow-tooltip 复制

el-table-column的show-overflow-tooltip弹出的提示无法复制&#xff0c;官方也暂时不准备解决&#xff0c;可以自己模拟一个 <el-table-column label"支付单号" width"100"><template #default"{ row }"><el-tooltip :content&…...

【C语言】指针的进阶(三)—— 模拟实现qsort函数以及指针和数组的笔试题解析

目录 1、模拟实现qsort函数 1.1、qsort函数的回顾 1.2、模拟实现qsort函数 2、指针和数组笔试题解析 2.1、一维数组 2.2、字符数组 1、模拟实现qsort函数 1.1、qsort函数的回顾 要模拟实现qsort函数&#xff0c;就要了解清楚qsort函数的参数以及使用方式。 我们先回顾一…...

有哪些做批发的网站/域名查询 站长查询

以织梦官方站为例&#xff0c;我们采集站长学院下的PHP教程栏目&#xff0c;打开列表地址http://www.dedecms.com/web-art/PHP_jiaocheng。 登录后台&#xff0c;进入“采集节点管理”&#xff0c;新建一个节点&#xff0c;选择内容模型为“普通文章”。1.设置节点基本信息先填…...

门户网站开发是什么/google登录入口

基于Matlab的湘江水质重金属污染预测模型研究 安徽农业科学 。 J o arn a l o f A n h u i A g fi &#xff0e;S c i &#xff0e; 2 0 1 2。 4 0 ( 9) &#xff1a; 5 4 9 6— 5 4 9 8 责任编辑杨莹莹责任校对况玲玲 基于 Ma t l a b的湘江水质重金属污染预测模型研究 宁 可 …...

58同城宿迁二手房/太原百度网站快速优化

Redis五大基本Value数据结构类型: String&#xff0c;List&#xff0c;Hash&#xff0c;Set&#xff0c;ZSet1:String String 是Redis 里面最简单的一种数据结构。在Redis中&#xff0c;所有的Key都是字符串&#xff0c;存储对象时也是需要进行序列化操作&#xff0c;但是不同…...

天津综合网站建设商店/360优化大师下载安装

0、写在前面的话关于索引的内容本来是想写的&#xff0c;大概收集了下资料&#xff0c;发现并没有想象中的简单&#xff0c;又不想总结了&#xff0c;纠结了一下&#xff0c;决定就大概写点浅显的&#xff0c;好吧&#xff0c;就是懒&#xff0c;先挖个浅坑&#xff0c;以后再挖…...

手机网站开发计划/seo推广是什么意思

#define&#xff0c;typedef&#xff0c;struct&#xff0c;enmu是我们阅读单片机底层代码时最经常碰到几个概念。 首先分开解释一下 宏定义#define与定义别名typedef&#xff0c;它俩一起说&#xff0c;因为它俩的功能十分相似&#xff0c;具体的的用法不说了&#xff0c;注…...

商丘做网站优化/分销渠道

https://blog.csdn.net/sidely/article/details/43059795 xrandr --output VGA --auto --output LVDS --off 打开外接显示器&#xff0c;同时关闭笔记本液晶屏幕&#xff08;只用外接显示器工作&#xff09; xrandr --output VGA --off --output LVDS --auto 关闭外接显示器…...