1,HDF开发指南 HDF(HarmonyOS Driver Foundation)鸿蒙驱动框架,提供驱动框架能力,包括驱动加载,驱动服务管理,驱动消息机制和驱动电源管理。基于HDF框架的能力,驱动开发者可以更集中于驱动自身功能的开发,骑士提升驱动开发效率。
1.1驱动加载介绍 实现驱动的加载功能,包括按需加载和按序加载:
第一:按需加载
HDF框架支持驱动在系统启动过程中交替加载,同时支持驱动在系统启动之后动态加载。
第二:按序加载
HDF框架支持驱动在系统启动的过程中按照驱动的优先级进行加载。
1.2驱动服务管理 HDF框架会集中管理驱动服务,使用者可以直接通过HDF框架对外提供的能力接口获取驱动相关的服务。
HDF框架提供统一的驱动消息机制,支持用户态向内核态驱动发送消息,也支持内核态驱动向用户态应用发送消息。
HDF框架提供休眠和唤醒功能,驱动能力在首次被使用时,框架会通知驱动进行唤醒操作。在最后一次使用结束时,框架会通知驱动进行休眠操作。
1.3驱动加载开发指导 驱动必须基于HDF框架开发才能使用HDF框架相关功能。驱动聚焦于自身功能的实现,依赖HDF框架的机制将驱动驱动进来,不需要关注驱动加载的过程。HDF框架开放能力包含两个部分,配置文件和注册接口。
1.4编写驱动程序 这跟Linux的驱动框架不一样,在Linux中,APP打开设备中断后,APP调用的读取函数会直接进入内核状态调用驱动的读取函数。
在liteos-a中使用HDF时,APP需要先获得服务,然后调用服务的调度函数:它可以向驱动发送数据,获得返回结果。
所以写驱动时,我们要先“编写驱动”,在“驱动中实现服务”。
1.5编写驱动 编写hello_drv.c源文件,在HDF中,一个驱动被抽象为“ HdfDriverEntry”,代码如下:
上述代码中,使用HDF_INIT定义了某些段属性的结构体,内核启动后会注册这个HdfDriverEntry。
重要的是其中的Bind函数,Init和Release函数的作用暂时无了解,不写又不行,我直接写空函数,代码如下:
在哪里实现服务呢?在Bind函数中。
1.6在驱动中实现服务
这被称为“绑定”,给驱动程序提供一个IHelloDriverService结构体,代码如下:
重要的是:IHelloDriverService结构体中第一个成员必定是“ struct IRemoteService”,代码如下:
绑定时就是设置device-> service指向一个“ struct IRemoteService”,上面的代码第49行。
在“ struct IRemoteService”结构体中,设置“ Dispatch”函数,上面代码第47行。
您可以认为Dispatch函数相当于ioctl,在Linux中通过ioctl(fd,cmd,arg)来操作驱动。
在liteos-a中通过service->> dispatcher-> Dispatch(o***,cmd,数据,重播)来操作驱动(后面会看到)。
1.7实现调度函数
我现在只是实现了APP读取驱动的值,在驱动中设置reply即可,代码如下:
1.8把驱动放入内核中 这段代码可以,参考内核自带的gpio驱动。
1.9具体驱动加入内核的实现流程
第一步:把代码放入到vendor / Huawei / hdf / platform / hello目录中:
上面的Kconfig,Makefile是参考同级目录gpio中的文件,具体代码如下:
Hell0_drv.c具体代码为:
/ *
*版权所有(c)2020华为设备有限公司 *根据Apache许可2.0版(“许可”)获得许可; *未经许可,您不得使用此文件。 *您可以在以下位置获得许可证的副本: * * *除非适用法律要求或书面同意,否则软件 *根据许可协议分发的内容是按“原样”分发的, *不作任何明示或暗示的保证或条件。 *有关特定语言的管理权限,请参阅许可证 *许可中的限制。 * / #include“ hdf_device_desc.h” #include“ hdf_log.h” #include“ los_hwi.h” #include“ osal_io.h” #include“ osal_irq.h” #include“ osal_mem.h” #include“ osal_spinlock.h”
静态uint32_t g_hello_val = 0x12345678; struct IHelloDriverService { 构造IRemoteService remoteService; }; int32_t HelloDriverDispatch(struct HdfDeviceObject * device,int id,struct HdfSBuf * data,struct HdfSBuf * reply) { (void)设备; (无效)数据; HDF_LOGE(“%s:收到cmd%d,并设置回复”,__func__,id); 如果(!HdfSbufWriteInt32(reply,g_hello_val)){ HDF_LOGE(“%s:回复int32失败”,__func__); } 返回HDF_SUCCESS; // HdfDeviceSendEvent(device,id,data); } 静态int32_t HelleloDrvBind(结构HdfDeviceObject *设备) { HDF_LOGI(“ HelleloDrvBind:Enter n”); if(device == NULL){ 返回HDF_ERR_INVALID_OBJECT; } 静态结构IHelloDriverService helloDrv = { .remoteService.Dispatch = HelloDriverDispatch, }; device-> service =(struct IRemoteService *)(&helloDrv); 返回0; } 静态int32_t HelleloDrvInit(struct HdfDeviceObject * device) { (void)设备; 返回HDF_SUCCESS; } 静态void HelleloDrvRelease(struct HdfDeviceObject * device) { (void)设备; } struct HdfDriverEntry g_helloDriverEntry = { .moduleVersion = 1, .Bind = HelleloDrvBind, .Init = HelleloDrvInit, .Release = HelleloDrvRelease, .moduleName =“ PLATFORM_HELLO”, }; HDF_INIT(g_helloDriverEntry); |
第二步:Kconfig的具体代码如下:
第三步:添加Makefile的具体代码如下:
第四步:修改上一级目录的Kconfig,如下图增加最后一行:
第五步:修改hcs文件
1.vendor / huawei / hdf / config / hi3516dv300 / hdf_manager / manager_config.hcs:
2.vendor / huawei / hdf / config / hi3516dv300 / hello / hello_config.hcs:
第六步:修改mk文件
drivers / hdf / lite / hdf_tables_ldflags.mk:
drivers / hdf / lite / hdf_lite.mk:
注:文档和视频中所有的图片及代码截图皆为示意图,具体以HarmonyOS官网发布内容为准。