最简单的驱动程序
一、驱动的硬件操作函数
- copy_to_user():完成内核空间到用户空间的复制
第一个参数 to:目标用户空间的地址
第二个参数 from: 源内核空间地址。保存了要拷贝到用户空间的内容的地址
第三个参数 n:要拷贝的字节数
copy_from_user 完成用户空间到内核空间的复制
第一个参数 to:目标内核空间的地址
第二个参数 from: 源用户空间地址。保存了用户要发送的数据,或者要拷贝到内核空间的内容的地址
第三个参数 n:要拷贝的字节数
返回值:成功返回 0
static char readbuf[100]; /* 读缓冲区 */
/*
* 该函数一般用于内核中的 read 函数的定义中,将内核接收到的内容拷贝到用户缓冲区
*/
static ssize_t xxx_read(struct file *filp, char __user *buf,
size_t cnt, loff_t *offt)
{
int ret = copy_to_user(buf, readbuf, cnt); // 将readbuf中的内容拷贝到buf
// 拷贝的字节数大小为cnt
if(ret == 0)
{
printk("kernel send data ok!\n");
}
else
{
printk("kernel send data failed!\n");
}
return 0;
}
static char writebuf[100];
/*
* 该函数一般用于内核中的 write 函数的定义中,将用户要发送的内容拷贝到内核缓冲区
*/
static ssize_t xxx_write(struct file *pfile, const char __user *buf,
size_t cnt, loff_t *offset)
{
/* 用户实现具体功能 */
int ret = copy_from_user(writebuf, buf, cnt); // 将buf中的内容拷贝到writebuf
if(ret == 0)
{
printk("kernel read data ok!\n");
}
else
{
printk("kernel read data failed!\n");
}
return 0;
}
二、file_operation结构体管理硬件操作函数
三、入口函数,
1、注册file_opeation到内核数组中去
设备号分成主设备号与从设备号,主设备号相同的注册到一条链表上,共有一个驱动程序。
从设备号就是表示多个相同设备
2、将物理地址转换虚拟地址
3、设备节点自动创建函数
四、出口函数
1、撤销地址转换
2、销毁设备节点
代码分析:
分层思想
一、leddrv.c
硬件操作函数以及它的上司file_operation结构体
入口函数,
1、注册file_opeation到内核数组中去
2、设备节点自动创建函数
出口函数
1、销毁设备节点
二、LED资源分配
led_resource
1、定义引脚选择结构体
2、创建一个函数获得引脚选择结构体的指针
board_A_led.c
1、创建引脚选择结构体的实例,并且赋值
2、完善引脚结构体指针函数,返回指向实例的指针
三、LED硬件相关操作
led_opr.h
定义led操作结构体、定义一个函数获得led操作结构体的指针
chip_demo_gpio
1、创建led控制结构体的实例并且立于函数赋值,
2、创建led控制函数、led初始化函数
3、完善函数,获得led控制函数结构体的指针
总线设计思想
一、公共部分
leddrv.h
定义三个函数封装了底层的设备节点创建、设备节点销毁、注册led_operations结构体(就是换一个指针指向led_operation结构体
设备节点的创建是我们自己创建,因为有多个,后面自己会调用
#ifndef _LEDDRV_H
#define _LEDDRV_H
#include "led_opr.h"
void led_class_create_device(int minor);
void led_class_destroy_device(int minor);
void register_led_operations(struct led_operations *opr);
#endif /* _LEDDRV_H */
leddrv.c
完善设备节点创建、设备节点销毁、注册led_operation封装函数
构建file_operation结构体,并且将对应函数进行赋值
入口函数
注册file_operations,
出口函数
撤销注册的file_operations结构体
撤销设备节点的前置
二、LED资源分配
注册platform_device 函数
创建驱动资源结构体platform_device结构体
创建资源分配结构体数组
三、LED硬件相关操作
chip_demo_gpio
入口函数
1、注册硬件驱动结构体
匹配成功函数
probe记录引脚信息
创建设备节点
匹配失败
销毁设备节点
2、注册硬件操作结构体
led引脚初始化
控制led引脚
设备树
将led资源分配写成设备树的形式简化了代码
Printctrl 子系统和GPIO子系统
将对硬件的具体操作完全封装了,我们只需要调用指定的函数就可以完成