iTOP-STM32MP157开发板编写驱动程序和应用程序

news2025/6/17 12:58:15

通过 40.1 章节的学习,我们已经把内核层和用户层实现数据交互的基本概念搞懂了,在上一章节的基础上我们编写驱动程序实现在内核层与应用层传数据。

新建 file_operation.c 文件在 Ubuntu 的/home/driver/04_file_operation 目录下,可以在上次实验 misc.c的基础上进行修改。

填充 file_operation 结构体

//文件操作集

struct file_operations misc_fops={

.owner = THIS_MODULE, .open = misc_open, .release = misc_release, .read = misc_read, .write = misc_write, };

填充接口函数

ssize_t misc_read (struct file *file, char __user *ubuf, size_t size, loff_t *loff_t)

{

printk("misc_read\n ");

return 0;

}

ssize_t misc_write (struct file *file, const char __user *ubuf, size_t size, loff_t *loff_t)

{

printk("misc_write\n ");

return 0;

}

int misc_release(struct inode *inode,struct file *file){

printk("hello misc_relaease bye bye \n ");

return 0;

}

int misc_open(struct inode *inode,struct file *file){

printk("hello misc_open\n ");

return 0;

}

完整驱动代码如下:

/*

* @Descripttion: 在上一章节实现了最简单杂项设备的编写,本代码再其基础上验证内核层与应用层数

据交互

*/

#include <linux/init.h> //初始化头文件

#include <linux/module.h> //最基本的文件,支持动态添加和卸载模块。

#include <linux/miscdevice.h>/*注册杂项设备头文件*/

#include <linux/uaccess.h>

#include <linux/fs.h>

/**

* @name: misc_read

* @test: 从设备中读取数据,当用户层调用函数 read 时,对应的,内核驱动就会调用这个函数。

* @msg: * @param {structfile} *file file 结构体

* @param {char__user} *ubuf 这是对应用户层的 read 函数的第二个参数 void *buf * @param {size_t} size 对应应用层的 read 函数的第三个参数

* @param {loff_t} *loff_t 这是用于存放文件的偏移量的,回想一下系统编程时,读写文件的操作都会使

偏移量往后移。

* @return {*} 当返回正数时,内核会把值传给应用程序的返回值。一般的,调用成功会返回成功读取

的字节数。

如果返回负数,内核就会认为这是错误,应用程序返回-1

*/

ssize_t misc_read(struct file *file, char __user *ubuf, size_t size, loff_t *loff_t)

{

printk("misc_read\n ");

return 0;

}

/**

* @name: misc_write * @test: 往设备写入数据,当用户层调用函数 write 时,对应的,内核驱动就会调用这个函数。

* @msg: * @param {structfile} * filefile 结构体

* @param {constchar__user} *ubuf 这是对应用户层的 write 函数的第二个参数 const void *buf * @param {size_t} size 对应用户层的 write 函数的第三个参数 count。

* @param {loff_t} *loff_t 这是用于存放文件的偏移量的,回想一下系统编程时,读写文件的操作都会使

偏移量往后移。

* @return {*} 当返回正数时,内核会把值传给应用程序的返回值。一般的,调用成功会返回成功读取

的字节数。

如果返回负数,内核就会认为这是错误,应用程序返回-1。

*/

ssize_t misc_write(struct file *file, const char __user *ubuf, size_t size, loff_t *loff_t)

{

printk("misc_write\n ");

return 0;

}

/**

* @name: misc_release * @test: 当设备文件被关闭时内核会调用这个操作,当然这也可以不实现,函数默认为 NULL。关闭设

备永远成功。

* @msg: * @param {structinode} *inode 设备节点

* @param {structfile} *file filefile 结构体

* @return {0} */

int misc_release(struct inode *inode,struct file *file){

printk("hello misc_release bye bye \n");

return 0;

}

/**

* @name: misc_open

* @test: 在操作设备前必须先调用 open 函数打开文件,可以干一些需要的初始化操作。

* @msg: * @param {structinode} *inode 设备节点

* @param {structfile} *file filefile 结构体

* @return {0} */

int misc_open(struct inode *inode, struct file *file)

{

printk("hello misc_open\n ");

return 0;

}

//文件操作集

struct file_operations misc_fops =

{

.owner = THIS_MODULE, .open = misc_open, .release = misc_release, .read = misc_read, .write = misc_write, };

//miscdevice 结构体

struct miscdevice misc_dev =

{

.minor = MISC_DYNAMIC_MINOR, .name = "hello_misc", .fops = &misc_fops, };

static int misc_init(void)

{

int ret;

ret = misc_register(&misc_dev); //注册杂项设备

if (ret < 0)

{

printk("misc registe is error \n");

期:2022-1-18

332 www.top

}

printk("misc registe is succeed \n");

return 0;

}

static void misc_exit(void)

{

misc_deregister(&misc_dev); //卸载杂项设备

printk(" misc gooodbye! \n");

}

module_init(misc_init);

module_exit(misc_exit);

MODULE_LICENSE("GPL");

我们编写应用程序 app.c,在 ubuntu 的/home/driver/04_file_operation 目录下,完整代码如下图所示:

#include <stdio.h>

#include <sys/types.h>

#include <sys/stat.h>

#include <fcntl.h>

#include <unistd.h>

int main(int argc,char *argv[])

{

int fd; //定义一个句柄

char buf[64] = {0};

fd = open("/dev/hello_misc",O_RDWR);//打开设备节点

if(fd < 0)

{

perror("open error \n");

return fd;

}

write(fd,buf,sizeof(buf));

close(fd);

return 0;

}

输入以下命令编译 app.c,如下所示:

arm-none-linux-gnueabihf-gcc app.c -o app -static

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

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

相关文章

基于Javaweb的摄影作品网站/摄影网站

摘 要 随着信息化时代的到来&#xff0c;系统管理都趋向于智能化、系统化&#xff0c;摄影作品网站也不例外&#xff0c;但目前国内的有些网站仍然都使用人工管理&#xff0c;浏览网站人数越来越多&#xff0c;同时信息量也越来越庞大&#xff0c;人工管理显然已无法应对时代的…

智慧二维码门牌管理系统:便捷、高效、智能的服务体验

文章目录 前言一、便捷的获取信息和服务二、提升管理和服务效率三、地区定制化应用四、展望未来 前言 随着信息技术的飞速发展&#xff0c;人们的生活方式正在发生翻天覆地的变化。为了更好地适应这种变化&#xff0c;智慧城市建设项目应运而生&#xff0c;而其中智慧二维码门…

LRU算法源码实现

算法介绍&#xff1a; 最近最久未使用&#xff08;Least Recently Used LRU&#xff09;算法是⼀种缓存淘汰策略。该算法的思路是&#xff0c;将最近一段时间内最久未使用的页面置换出去。 升级版LRUK算法见 基于LRU-K算法设计本地缓存实现流量削峰https://blog.csdn.net/l…

如何通过时间跟踪改进项目管理?

领导一家成功企业难免面临一系列挑战&#xff1a;如未能制定清晰明确的目标、管理不善的团队成员、将错误的任务分配给错误的人……如果没有适当的项目管理&#xff0c;企业管理可能会举步维艰。 虽然提高项目管理技能的方法有很多&#xff0c;但最有效、最快捷的方法之一就是…

如何正确地设置Outlook SMTP发送电子邮件(wordpress配置)

如何正确地设置Outlook SMTP发送电子邮件&#xff08;wordpress配置&#xff09; 作者&#xff1a;虚坏叔叔 博客&#xff1a;https://pay.xuhss.com 早餐店不会开到晚上&#xff0c;想吃的人早就来了&#xff01;&#x1f604; 正在寻找正确的Outlook SMTP设置&#xff1f…

leetcode414. 第三大的数

题目&#xff1a; 给你一个非空数组&#xff0c;返回此数组中 第三大的数 。如果不存在&#xff0c;则返回数组中最大的数。 示例 1&#xff1a; 输入&#xff1a;[3, 2, 1] 输出&#xff1a;1 解释&#xff1a;第三大的数是 1 。 示例 2&#xff1a; 输入&#xff1a;[1, …

SAP 开启录制与回放功能(RZ11 : sapgui/user_scripting)<转载>

原文链接&#xff1a;https://www.pianshen.com/post/683635733189/#google_vignette 问题现象&#xff1a; 1、如下图&#xff0c;在SAP界面的定制本地布局菜单中&#xff0c;脚本录制和回放功能为灰色&#xff0c;无法进行点击操作&#xff0c;因此也无法进行本地脚本录制。 …

【前端】深入理解CSS定位

目录 一、前言二、定位组成1、定位模式1.1、静态定位static①、语法定义②、特点 1.2、相对定位relative①、语法定义②、特点③、代码示例 1.3、绝对定位absolute①、语法定义②、特点③、代码示例1&#xff09;、没有祖先元素或者祖先元素没有定位2&#xff09;、祖先元素有定…

关于内点定义不同的讨论

根据和译者联系后&#xff0c;根据提供P660页的关于内点的定义与其他国内教材不同。 《离散数学及其应用&#xff08;原书第8版&#xff09;》ISBN:978-7-111-63687-8内点定义如下图所示 因此 《离散数学及其应用&#xff08;原书第8版&#xff09;》ISBN:978-7-111-63687-8 第…

为自己的 SSM项目设计评论功能

为自己的 SSM项目设计评论功能 设计思路增加评论显示评论评论总数 设计思路 首先需要设计评论信息的实体类&#xff08;对应评论表&#xff09; 主要分为以下2个功能&#xff1a; 显示所有评论 当我们进入文章详情页的时候&#xff0c;页面就会通过 ajax 发送请求给服务器&…

电厂人员定位方案可以使用多种技术来实现

电厂人员定位方案可以使用多种技术来实现。以下是一个常见的电厂人员定位方案的步骤&#xff1a; 1.选取合适的定位技术&#xff1a;根据电厂的需求和运行环境&#xff0c;选择适合的定位技术&#xff0c;例如基于UWB&#xff08;Ultra-Wideband&#xff09;、RFID&#xff08…

Linux 黑话解析:什么是 LUKS 加密?

导读LUKS 是 Linux 用户中流行的磁盘加密机制。在这篇术语解析文章中&#xff0c;可以了解更多关于 LUKS 的信息。 计算机安全旨在保护私密信息。有许多方法可以保护系统。一些用户使用简单的用户名/密码登录方案进行基本保护。其他用户可能会通过加密以不同的方式增加额外的保…

Leetcode 剑指 Offer II 040. 矩阵中最大的矩形

题目难度: 困难 原题链接 今天继续更新 Leetcode 的剑指 Offer&#xff08;专项突击版&#xff09;系列, 大家在公众号 算法精选 里回复 剑指offer2 就能看到该系列当前连载的所有文章了, 记得关注哦~ 题目描述 给定一个由 0 和 1 组成的矩阵 matrix &#xff0c;找出只包含 1…

c语言实现MD5算法

MD5加密 文章目录 MD5加密MD5介绍应用场景代码分析 &#xff08;基于qt5.14.2&#xff09;测试记录 MD5介绍 1。 一种单向加密算法&#xff0c;即对明文加密&#xff0c;而不能通过密文得到明文。对原数据的任何改动&#xff0c;哪怕是1字节&#xff0c;得到的MD5值都有很大的区…

C#系统锁屏事件例子 - 开源研究系列文章

今天有个网友问了个关于操作系统锁屏的问题。 我们知道&#xff0c;操作系统是基于消息和事件处理的&#xff0c;所以我们只要找到该操作系统锁屏和解屏的那个事件&#xff0c;然后在事件里进行处理即可。下面是例子介绍。 1、 项目目录&#xff1b; 下面是项目目录&#xff1a…

vue的scrollTop手机环境设置值失效,本地正常可以赋值

获取div盒子ref或者document获取都行 监听方法 一定要加this.$nexttick,在本地测试只用nexttick是没有问题的&#xff0c;但是到手机测试就不行了&#xff0c;原因是因为手机渲染比本地更快&#xff0c;所以结合setTimeout使用 如果有更好的处理方法&#xff0c;恳请大佬指点一…

C语言——通讯录详解(动态版)

通讯录详解 前言&#xff1a;一、定义一个通讯录二、初始化三、增加联系人3.1 给通讯录扩容3.2增加联系人 四、释放内存五、完整代码 前言&#xff1a; 我们已经学过了通讯录的静态版&#xff0c;但是它的缺点很明显&#xff0c;通讯录满了就添加不了联系人了啦。我再让通讯录升…

为什么要用i ,√(-1)不行吗?

首先讲一下&#xff0c;我不是拦着各位使用√(-1)&#xff0c;这只是一种记号&#xff0c;在这里只是探讨一下一些数的性质而已 我们首先需要探讨下根式的一个性质&#xff0c;下面将会讲一个关于小明的故事&#xff1a; 他的老师在黑板上写下这么一道题 一道很正常的题 他的同…

vue3 setup语法糖导入mixin

像这样直接导入&#xff0c;然后通过defineOptions声明mixin 然后就可以在这个组件使用mixin里的数据和方法了