Linux驱动入门系列
Linux驱动入门(三)Led驱动
文章目录
目的:实现一个led驱动,应用层写入1led亮,写0led灭
一、注册字符设备驱动
led驱动是一个字符设备驱动,编写led驱动首先要注册字符设备,生成设备节点,然后再是完善文件操作集合
关于如何注册字符设备和生成设备字节,在Linux驱动入门(一)字符设备驱动基础中讲得比较详细了,这里给出代码
#include <linux/module.h>
#include <linux/init.h>
#include <linux/fs.h>
#include <linux/cdev.h>
#include <linux/slab.h>
#include <linux/device.h>
#include <asm/io.h>
#include <asm/uaccess.h>
static dev_t dev_id;
static struct cdev *led_dev;
static struct class *led_class;
int led_open(struct inode *inode, struct file *file)
{
/* 设置gpio */
return 0;
}
ssize_t led_write(struct file *file, const char __user *data, size_t size, loff_t *loff)
{
int val, ret;
/* 从用户空间拷贝数据 */
ret = copy_from_user(&val, data, sizeof(val));
if(val == 0)
{
/* 熄灭led */
}
else if(val == 1)
{
/* 点亮 */
}
return 0;
}
static struct file_operations led_fops = {
.owner = THIS_MODULE,
.open = led_open,
.write = led_write,
};
static __init int led_init(void)
{
/* 申请设备号 */
alloc_chrdev_region(&dev_id, 1, 1, "led");
/* 分配字符设备 */
led_dev = cdev_alloc();
/* 设置字符设备 */
cdev_init(led_dev, &led_fops);
/* 注册字符设备 */
cdev_add(led_dev, dev_id, 1);
/* 创建设备节点 */
led_class = class_create(THIS_MODULE, "led"); //创建类
device_create(led_class, NULL, dev_id, NULL, "led"); //创建设备节点
return 0;
}
static __exit void led_exit(void)
{
/* 注销设备节点 */
device_destroy(led_class, dev_id);
class_destroy(led_class);
/* 注销字符设备 */
cdev_del(led_dev);
kfree(led_dev);
/* 注销注册的设备号 */
unregister_chrdev_region(dev_id, 1);
}
module_init(led_init);
module_exit(led_exit);
MODULE_LICENSE("GPL");
编译上面的驱动程序,加载模块,就会生成/dev/led
设备节点,这是我们led驱动的基本框架,我们还要在led_open
、led_write
中操作硬件
从上面代码中可以看到,在led_