电子商务网站建设 实验分析,wordpress 网站访问量,wordpress做人事网站,网站建设工具哪个好一. 简介
前面一篇文章简单学习了 Linux内核中platform驱动代码。文章地址如下#xff1a;
Linux下platform驱动简介-CSDN博客
本文学习编写 platform驱动框架代码。 二. Linux下platform驱动框架编写
1. 编写platform驱动代码的思路
#xff08;1#xff09; 定义结…一. 简介
前面一篇文章简单学习了 Linux内核中platform驱动代码。文章地址如下
Linux下platform驱动简介-CSDN博客
本文学习编写 platform驱动框架代码。 二. Linux下platform驱动框架编写
1. 编写platform驱动代码的思路
1 定义结构体以及实现匹配方法以及 probe 函数 在编写 platform 驱动的时候首先定义一个 platform_driver 结构体变量。 然后实现结构体中的各个成员变量重点是实现匹配方法以及 probe 函数。 当驱动和设备匹配成功以后 probe 函数就会执行具体的驱动程序在 probe 函数里面编写比如字符设备驱动等等。 2 向Linux内核注册一个platform驱动 当我们定义并初始化好 platform_driver 结构体变量以后需要在驱动入口函数里面调用 platform_driver_register 函数向 Linux 内核注册一个 platform 驱动。 platform_driver_register 函数 原型如下所示 int platform_driver_register (struct platform_driver *driver) 函数参数和返回值含义如下 driver 要注册的 platform 驱动。 返回值 负数失败 0 成功。 3卸载platform驱动 还需要在驱动卸载函数中通过 platform_driver_unregister 函数卸载 platform 驱动 platform_driver_unregister 函数原型如下 void platform_driver_unregister(struct platform_driver *drv) 函数参数和返回值含义如下 drv 要卸载的 platform 驱动。 返回值 无。 二. platform 驱动框架 platform 驱动框架如下所示 /* 设备结构体 */
struct xxx_dev{
struct cdev cdev;
/* 设备结构体其他具体内容 */
};struct xxx_dev xxxdev; /* 定义个设备结构体变量 */static int xxx_open(struct inode *inode, struct file *filp)
{ /* 函数具体内容 */return 0;
}static ssize_t xxx_write(struct file *filp, const char __user *buf,
size_t cnt, loff_t *offt)
{/* 函数具体内容 */return 0;
}/*
* 字符设备驱动操作集
*/
static struct file_operations xxx_fops {.owner THIS_MODULE,.open xxx_open,.write xxx_write,
};/*
* platform 驱动的 probe 函数
* 驱动与设备匹配成功以后此函数就会执行
*/
static int xxx_probe(struct platform_device *dev)
{ ......cdev_init(xxxdev.cdev, xxx_fops); /* 注册字符设备驱动 *//* 函数具体内容 */return 0;
}static int xxx_remove(struct platform_device *dev)
{......cdev_del(xxxdev.cdev);/* 删除 cdev *//* 函数具体内容 */return 0;
}/* 匹配列表 */
static const struct of_device_id xxx_of_match[] {
{ .compatible xxx-gpio },
{ /* Sentinel */ }
};/*
* platform 平台驱动结构体
*/
static struct platform_driver xxx_driver {.driver {.name xxx,.of_match_table xxx_of_match,},.probe xxx_probe,.remove xxx_remove,
};/* 驱动模块加载 */
static int __init xxxdriver_init(void)
{return platform_driver_register(xxx_driver);
}/* 驱动模块卸载 */
static void __exit xxxdriver_exit(void)
{platform_driver_unregister(xxx_driver);
}module_init(xxxdriver_init);
module_exit(xxxdriver_exit);
MODULE_LICENSE(GPL);
MODULE_AUTHOR(WeiWuXian); 驱动代码说明如下 第 1~27 行传统的字符设备驱动所谓的 platform 驱动并不是独立于字符设备驱动、块设备驱动和网络设备驱动之外的其他种类的驱动。 platform 只是为了驱动的分离与分层而提出来的一种框架其驱动的具体实现还是需要字符设备驱动、块设备驱动或网络设备驱动。 第 33~39 行 xxx_probe 函数当驱动和设备匹配成功以后此函数就会执行以前在驱动入口 init 函数里面编写的字符设备驱动程序就全部放到此 probe 函数里面。比如注册字符设备 驱动、添加 cdev 、创建类等等。 第 41~47 行 xxx_remove 函数 platform_driver 结构体中的 remove 成员变量当关闭 platform 备驱动时此函数就会执行以前在驱动卸载 exit 函数里面要做的事情就放到此函数中来。 比如使用 iounmap 释放内存、删除 cdev 注销设备号等等。 第 50~53 行 xxx_of_match 匹配表如果使用设备树的话将通过此匹配表进行驱动和设备 的匹配。 第 51 行设置了一个匹配项此匹配项的 compatible 值为“ xxx-gpio ”因此当设备树中 设备节点的 compatible 属性值为“ xxx-gpio ”的时候此设备就会与此驱动匹配。 第 52 行是一个标记of_device_id 表最后一个匹配项必须是空的。 第 58~65 行定义一个 platform_driver 结构体变量 xxx_driver 表示 platform 驱动。 第 59~62 行设置 paltform_driver 中的 device_driver 成员变量的 name 和 of_match_table 这两个属性。 其中 name 属性用于传统的驱动与设备匹配也就是检查驱动和设备的 name 字段是不是相同。 of_match_table 属性就是用于设备树下的驱动与设备检查。 对于一个完整的驱动程序必须提供 有设备树和无设备树两种匹配方法。 最后 63 和 64 这两行设置 probe 和 remove 这两成员变量。 第 68~71 行驱动入口函数调用 platform_driver_register 函数向 Linux 内核注册一个 platform 驱动也就是上面定义的 xxx_driver 结构体变量。 第 74~77 行驱动出口函数调用 platform_driver_unregister 函数卸载前面注册的 platform 驱动。 三. 总结 总体来说 platform 驱动还是传统的字符设备驱动、块设备驱动或网络设备驱动只是套上了一张“ platform ”的皮目的是为了使用总线、驱动和设备这个驱动模型来实现驱动的分 离与分层。