【OneOS学习笔记】设备驱动模型中的I2C
- 简介
- OneOS 在各类外设的基础上抽象出了设备驱动模型,本文将围绕驱动模型来分析I2C驱动的实现过程。
- I2C驱动以STM32为例,主要分析驱动模型中各层之间的调用关系。
- OneOS设备驱动模型见OneOS 官网(https://os.iot.10086.cn)文档驱动部分。
- I2C驱动总概
- I2C驱动框架如下图所示:
- 从图中可以看出用户可以直接访问设备统一接口和I2C设备框架层的API。
- 驱动为I2C设备提供的API见下表:
API
层
os_device_find
管理层
os_i2c_transfer
框架层
os_i2c_client_write
框架层
os_i2c_client_read
框架层
os_i2c_client_write_byte
框架层
os_i2c_client_read_byte
框架层
os_i2c_master_send
框架层
os_i2c_master_recv
框架层
- 对于不同芯片,管理层提供设备操作接口,框架层提供I2C这类设备通用的接口,驱动层提供具体芯片的I2C设备驱动程序。
- STM32系列芯片I2C驱动实现过程:
- 设备注册:
OneOS启动之后会进入到_driver_stm32_i2c_driver_init(),当执行初始化函数时,会调用到driver_match_devices()完成驱动和设备的匹配,匹配成功就会执行设备驱动层的stm32_i2c_probe()函数,在probe()函数中调用os_i2c_bus_device_register()函数,实现st的i2c设备注册到i2c总线设备中。在框架层的os_i2c_bus_device_register()函数,通过调用os_device_register()函数实现i2c总线设备挂载到内核设备链表上。
- 设备访问:
应用层通过find函数查找到设备,设备ops函数在框架层和驱动层实现,同一功能函数层层调用,调用关系如下:
os_device_read_nonblock→i2c_bus_device_read(os_i2c_master_recv)→os_i2c_transfer→stm32_i2c_transfer(调用ST系列HAL库函数)
os_device_write_block→i2c_bus_device_write(os_i2c_master_send)→os_i2c_transfer→ stm32_i2c_transfer(调用ST系列HAL库函数)
os_device_control→i2c_bus_device_control→os_i2c_transfer()→stm32_i2c_transfer(调 用ST系列HAL库函数)
- 设备管理层
设备管理层实现了对设备驱动程序的封装,是所有设备通用的函数接口,I2C设备在管理层实现设备查找和注册。
- 查找设备:os_device_find()
函数原型:os_device_t *os_device_find(const char *name)
位置:drivers\device.c
参数:name(设备名称)
返回值类型:os_device_t(返回设备指针)
注:通过os_device_find()访问设备时,只在设备管理层实现。
- os_device_find()根据传入设备的名称 "i2c1",通过定义os_list_for_each_entry遍历设备链表os_device_list查找设备;若查找到设备,返回相应的设备指针,否则返回空指针OS_NULL。
- os_device_list的值来源于设备注册函数os_device_register()。
- 注册设备:os_device_register()
位置:drivers\device.c
参数:dev(设备指针),name(设备名称)
返回值类型:os_err_t
- 首先用os_device_find查找设备名是否已被注册过,如果已注册过,则返回无效参数的错误类型。
- 初始化基类对象,纳入对象容器实现设备的初始化,并通过os_list_add将设备结点添加到系统的设备链表里。
4、设备框架层
设备框架层对同类硬件设备驱动的抽象,将不同厂家的同类硬件设备驱动中相同的部分抽取出来,将不同部分留出接口,由驱动程序实现。
- 函数接口(API):
函数
功能
os_i2c_bus_device_find
根据I2C总线名称查找I2C总线设备
i2c_bus_device_control
控制I2C总线设备的特性
i2c_bus_device_write
将发送数据写入I2C总线设备
i2c_bus_device_read
读I2C总线设备接收的数据
os_i2c_master_recv
I2C总线设备数据接收
os_i2c_master_send
I2C总线设备数据发送
os_i2c_client_write
I2C 主设备数据发送
os_i2c_client_read
I2C 主设备数据接收
os_i2c_client_write_byte
使用cmd向I2C 主设备写入单字节数据
os_i2c_client_read_byte
根据cmd读取I2C主设备单字节数据
os_i2c_transfer
使用I2C设备传输消息
os_i2c_bus_device_register
注册I2C设备总线
- 主要作用:
- 这一层主要起到承上启下的作用,为上层应用提供统一的API,为下层驱动,提供注册函数。
- 实现设备ops函数:i2c_ops
- const static struct os_device_ops i2c_ops = {
- .read = i2c_bus_device_read,
- .write = i2c_bus_device_write,
- .control = i2c_bus_device_control
- };
- 调用os_device_register函数将I2C设备注册到设备管理层。
5、设备驱动层
1、 实现设备ops功能函数stm32_i2c_transfer,对接底层硬件,调用STM32的HAL库。
2、 probe函数实现设备初始化,调用os_i2c_bus_device_register向框架层注册设备。
3、 调用probe函数的方法。
- 调用OS_DRIVER_INFO,将st_i2c的probe和name赋值给os_driver_info_t。
- OS_DRIVER_INFO stm32_i2c_driver = {
- .name = "I2C_HandleTypeDef",
- .probe = stm32_i2c_probe,
- };
- #define OS_DRIVER_INFO static OS_USED OS_SECTION("driver_table") const os_driver_info_t
- os_driver_info_t结构体定义如下:
- typedef struct os_driver_info
- {
- char *name;
- int (*probe)(const struct os_driver_info *drv, const struct os_device_info *dev);
- } os_driver_info_t;
- 在设备进行初始化时会将stm32_i2c_driver作为OS_DRIVER_DEFINE的参数,调用驱动和设备匹配函数,让driver逐一与device_table中的device对应的driver进行比较,直到找到相同的driver即匹配完成,之后将device和driver传递给probe完成设备注册。

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。
持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。
转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。
- 上一篇
稳,从数据库连接池 testOnBorrow 看架构设计 | 京东云技术团队
本文从 Commons DBCP testOnBorrow 的作用机制着手,管中窥豹,从一点去分析数据库连接池获取的过程以及架构分层设计。 以下内容会按照每层的作用,贯穿分析整个调用流程。 1️⃣框架层 commons-pool The indication of whether objects will bevalidated before being borrowedfrom the pool. If the object fails to validate, it will be dropped from the pool, and we will attempt to borrow another. testOnBorrow 不是 dbcp 定义的,是commons-pool 定义的。commons-pool 详细的定义了资源池使用的一套规范和运行流程。 /** * Borrow an object from the pool. get object from 资源池 * @see org.apache.commons.pool2.impl.GenericObjectPoo...
- 下一篇
【SIGMOD 2023】深度学习弹性数据流水线系统GoldMiner,大幅提升任务和集群效率
第一板块:开篇 近日,阿里云机器学习平台PAI和北京大学杨智老师团队合作的论文《GoldMiner: Elastic Scaling of Training Data Pre-Processing Pipelines for Deep Learning》被数据库领域顶会SIGMOD 2023接收。 GoldMiner观察到深度学习任务中的数据预处理流水线具有无状态的特点,具有内在的资源弹性。基于此,GoldMiner将数据预处理流水线和模型训练部分分离执行,通过自动计算图分析来识别无状态的数据预处理计算,并对其实现高效的并行加速和弹性伸缩,从而缓解数据预处理瓶颈,提升训练性能。通过与集群调度器的协同设计,GoldMiner进一步发挥了数据预处理计算的资源弹性,大幅提升集群调度效率。实验显示GoldMiner可提升训练性能达12.1倍,提升GPU集群利用率达2.5倍。 第二板块:背景 近年来,随着GPU加速器的不断进化,以及各类软件优化技术的层出不穷,深度学习训练的计算效率正不断被提升到新的层次。但与此同时,深度学习本质上仍是一种多阶段、多资源的任务类型:不仅需要在GPU上进行大量的训练...
相关文章
文章评论
共有0条评论来说两句吧...
文章二维码
点击排行
推荐阅读
最新文章
- Docker使用Oracle官方镜像安装(12C,18C,19C)
- Docker安装Oracle12C,快速搭建Oracle学习环境
- Docker快速安装Oracle11G,搭建oracle11g学习环境
- CentOS7安装Docker,走上虚拟化容器引擎之路
- SpringBoot2全家桶,快速入门学习开发网站教程
- CentOS7设置SWAP分区,小内存服务器的救世主
- CentOS7,CentOS8安装Elasticsearch6.8.6
- Hadoop3单机部署,实现最简伪集群
- SpringBoot2更换Tomcat为Jetty,小型站点的福音
- SpringBoot2配置默认Tomcat设置,开启更多高级功能