当前位置: 首页 > news >正文

鸿蒙HDF框架源码分析

文章目录

  • 前言
  • HDF 大体的认识
  • HDF 核心模块 和 关键结构体
  • 总结
一、前言

作为鸿蒙驱动开发来说,HDF框架和分布式软总线是非常重要的内容,可以这么说,正是这两部分内容,让鸿蒙系统跟android 和 ios 有了很大的不同。

原本的驱动开发,需要为每个设备写不同驱动,换个硬件还要重写代码,很容易出问题。而鸿蒙有了HDF框架,就变的不一样了。

用一句化来简单的概括,就是对驱动开发,进行抽象。更高层次的抽象,使得驱动开发,变得更简单。一次开发,在鸿蒙各种设备上都能使用。

正是因为更高层的抽象,使驱动开发简单,HDF框架就需要进行系统层抽象,提供标准驱动模型,还有统一平台的操作接口。最终实现一次开发,多端部署。

接下来,我们就一步步分析HDF框架,再到源码中的关键流程。

二、HDF 大体的认识
1、怎么使用HDF框架
1、通过配置hcs文件,适配不同的硬件。
2、HDF框架解析 hcs 配置,获取驱动信息。
3、驱动实现的Bind 函数被调用,进行服务接口的实例化和绑定
4、Init函数执行硬件初始化,最终通过 HdfDeviceNodePublishPublicService 等接口,按照配置policy 将服务发布到全局管理器,供其他组件发现和获取。
5、应用 可以通过 DevSvcManagerClntGetService 接口,传入服务名称,获取对应的驱动服务对象,进而操作硬件。
2、HDF 核心设计思想

通过 OSAL 和 Platform 抽象层,屏蔽不同内核和芯片平台的差异。(不同内核,比如: LiteOs 和 Linux 内核。 不同的芯片,比如:海思、高通)

也就是 HDF 充当了翻译的工作,
不同内核层面:比如 驱动需要分配内存内存空间 OsalMemAlloc,HDF框架会进行翻译,在Linux 上运行,就会翻译成 malloc。 在 LiteOs 上就会翻译成LOS_MemAlloc。

不同平台层面:
比如驱动说,我要点灯,HDF会根据hcs 配置文件,知道在芯片A上,点灯的这个动作对应的操作地址 0x1000。而在芯片B上,对应的地址是 0x1010。

hcs配置文件的作用:实现了硬件配置 和 驱动代码的解耦。

3、一个 LED 驱动实现流程

以一个简单的LED 驱动为例,这样能更清楚的看到整个大概流程。

1、配置hcs文件:要定义LED设备,指定驱动源码的路径、设置GPIO引脚,设置发布策略等
2、驱动的实现: 在驱动代码中实现 Bind、Init、Release 函数,还有LED开关的逻辑
3、应用调用驱动: 应用通过 DevSvcManagerClntGetService("sample_driver") 来获取驱动服务,拿到代表驱动的 HdfDeviceObject 后,通过 service->Dispatch 方法,来发送控制命令,来点亮或熄灭 LED。
==================================下面是更深入一点认识==================================
三、核心模块 和 关键结构体
1、HDF 框架的核心模块
1、核心管理层: DevmgrService, DevSvcManager (主要目的: 驱动生命周期管理、服务注册与发现)
2、驱动宿主层:DevHostService,HdfDevice, HdfDeviceNode   (主要目的:驱动实例的承载,驱动加载 HdfDriverLoader)
3、平台抽象和模型:GPIO/I2C/SPI 等平台接口   (主要目的:提供标准驱动模型 和 统一平台操作接口)
4、配置解析:HCS Parser    (主要目的:解析hcs文件,生成配置树供驱动读取)

大白话,简化下上面内容:DevmgrService 启动 Host进程,触发驱动加载流程,然后进行绑定,接着调用驱动Init函数,初始化之后通过HdfDeviceNodePublishPublicService 进行服务的注册。

2、关键结构体 (HDF中涉及的主要结构体 DevmgrService 、DevSvcManager)

DevmgrService 设备管理服务

1、核心职责: 驱动生命周期管理
2、管理层次:管理Host 及 它下面的设备和驱动
3、主要工作内容:启动、停止Host,加载、卸载驱动,电源事件分发
4、管理对象:Host 、Device、DeviceNode
5、数据存储结构:Hosts 双向链表
6、暴露的接口:StartService, StartDeviceHost 等

DevSvcManager 服务管理器

1、核心职责:驱动服务注册与发现
2、管理层次:管理已发布的服务接口
3、主要工作内容: 维护服务注册表、提供服务的查询和获取
4、管理对象:由HdfDeviceObject 代表的驱动服务
5、数据存储结构:服务名到 HdfDeviceObject    的映射表(服务注册表)
6、暴露的接口:DevSvcManagerClntGetService

上面两个是极其容易混淆的,他们之间的关系概括如下:
1、驱动加载与服务注册:

1、当系统启动或动态加载驱动时,DevmgrService 负责启动对应的 Host 进程(也就是 DevHostService),并触发驱动的加载流程
2、驱动在初始化过程中,会通过 DeviceDriverBind 函数将自身的服务接口(具体的实现 IDeviceIoService) 绑定到对应的 HdfDeviceObject(驱动实例)的servce 字段上,这样只要拿到HdfDeviceObject,就能拿到驱动提供的方法了。
3、DeviceDriverBind 执行完之后,也就是驱动初始化之后,会通过 HdfDeviceNodePublishService 最终调用 DevSvcManagerAddService 向DevSvcManager注册驱动的服务。此时DevSvcManager 会将驱动服务的名称和对应的 HdfDeviceObject 存入DevSvcManager的服务的注册表 services 中(也就是 DListHead)。

OpenHarmony 4.0 源码中实际调用过程如下(从上往下调用,缩进部分是函数内部的操作)

从 device_manager.c 的入口 main 开始
mainDevmgrServiceGetInstance  实际是 DevmgrServiceCreateDevmgrServiceConstruct instance->StartService  (StartService 实际是 DevmgrServiceStartService)
DevmgrServiceStartService
DevmgrServiceStartDeviceHosts 启动设备所有主机
DevmgrServiceStartDeviceHost  启动单个设备主机
DevmgrServiceStartHostProcess DriverInstallerGetInstance  实际是 DriverInstallerCreateinstaller->StartDeviceHost  StartDeviceHost 实际是 DriverInstallerStartDeviceHost
DriverInstallerStartDeviceHost  创建并启动主机DevHostServiceNewInstance   实际是 DevHostServiceCreate -> DevHostServiceConstructhostServiceIf->StartService 实际是 DevHostServiceStartService
DevHostServiceStartService
DevmgrServiceClntAttachDeviceHost(hostService->hostId, service)  service 实际是 DevHostServiceDevmgrServiceClntGetInstance  调用 DevmgrServiceCreate 调用 DevmgrServiceConstruct 获得 instdevMgrSvcIf = inst->devMgrSvcIf;devMgrSvcIf->AttachDeviceHost
AttachDeviceHost 实际是 DevmgrServiceAttachDeviceHost
DevHostServiceClntInstallDriver
devHostSvcIf->AddDevice    (DevHostService 继承 IDevHostService 调用 AddDevice, AddDevice 实际是 DevHostServiceAddDevice)
DevHostServiceAddDevice
device->super.Attach(&device->super, devNode)    (Attach 实际是 HdfDeviceAttach)
HdfDeviceAttachnodeIf->LaunchNode(devNode)  (LaunchNode 实际是 HdfDeviceLaunchNode)
HdfDeviceLaunchNode
HdfDeviceNodePublishPublicService 发布服务
DevSvcManagerClntAddService
DevSvcManagerAddService
到这里服务已经发布完成

2、服务发现与使用
当应用需要 调用驱动提供的服务时,它会通过 DevSvcManagerClntGetService,向DevSvcManager 查询指定名称的驱动服务。通过 DevSvcManager 在其服务注册表中,找到 HdfDeviceObject ,这样调用者就能使用驱动提供的服务接口。

大白话:DevmgrSevice 负责把驱动加载和初始化,HdfDeviceObject 主要提供具体的硬件服务,然后DevSvcManager负责给这个驱动宣传,告诉外界这个驱动能提供什么服务,以及如何联系(注册和发现)。

四、总体流程(关键结构体,再加上Hcs文件的解析,于是总的HDF框架如下)
1、HCS Parser 解析配置,生成配置树
2、DevmgrService 会根据配置树,读取驱动列表。通过下发加载指令,调用 DevHostService
3、DevHostService 会通过 HdfDriverLoader 解析、调用 Bind/Init  最终创建生成 HdfDevice(驱动实例)
4、HdfDevice 会初始化硬件/服务接口,通过 HdfDeviceNodePublishPublicService 发布服务,最终把服务注册到 DevSvcManager 的注册表中
5、有了驱动的服务,这样应用就能通过 DevSvcManager  的注册表查询,获取驱动,并进行驱动的调用

HDF框架还是有很多内容的,当涉及用户态和内核态,还会牵扯到IPC,但一旦有了上面的蓝图,相信你看源码就有了方向, 也对HDF框架有了大体的认识。

总结

1、介绍HDF框架的好处
2、HDF 框架大体的认识
3、最后通过源码中的关键结构体,还有关键模块,理解HDF框架的整体运行流程

如果对你有一点点帮助,那是值得高兴的事情。:)
我的csdn:http://blog.csdn.net/shenshizhong
我的掘金:https://juejin.cn/user/4288556651785000

http://www.dtcms.com/a/549088.html

相关文章:

  • Springboot旅游管理系统8cx8xy5m(程序+源码+数据库+调试部署+开发环境)带论文文档1万字以上,文末可获取,系统界面在最后面。
  • ppt免费制作网站如何建设网站山东济南兴田德润官网
  • 如何获取网站根目录链接诸城做网站的
  • GPT-0: Attention+Transformer+可视化
  • 告别“人眼扫描”:EasyGBS智能搜索功能助力重塑海量视频监控管理效率
  • 【ubuntu】ubuntu系统如何快速删除当前用户的配置
  • dz地方门户网站制作南昌seo招聘信息
  • 灵犀科技网站开发湖南网站建设的公司排名
  • 沈阳装修公司网站建设做网站只用前端知识可以吗
  • ELK es+logstash
  • Java 大视界 -- Java 大数据在智能医疗远程康复数据管理与康复方案个性化定制实战(430)
  • 【C#】XtraMessageBox(DevExpress)与MessageBox(WinForms 标准库)的区别
  • 石家庄物流网站建设北京公司网站建设价格
  • 网络编程入门
  • 每日一个C语言知识:C 错误处理
  • 基础建设的网站有哪些内容网页制作基础教程费
  • 建站工具哪个好用深圳网站建设定制平台
  • 2048游戏笔记3 游戏开始与结束 cocos3.8.7
  • 【AI WorkFow】n8n 源码分析-核心结构体设计思考(六)
  • 网站诊断内容工程建设教育培训
  • Opencv(四):自适应二值化
  • GitHub 热榜项目 - 日榜(2025-10-30)
  • 网络:4.应用层自定义协议与序列化
  • Word崩溃打不开?实测三款Word文档修复工具!
  • 哪个网站做签约插画师好网站域名过期后续费多长时间生效
  • 《R for Data Science (2e)》免费中文翻译 (第11章) --- Communication(2)
  • 扩展阅读:CSV格式的目标检测(Object Detection)标注文件示例
  • 行政单位门户网站建设规定久久建筑网20g三维图集下载
  • Kotlin Multiplatform Mobile(KMM):实现 iOS 与 Android 共享业务逻辑
  • 利用Selenium和PhantomJS提升网页内容抓取与分析的效率