前言
上一篇,我们在鸿蒙上运行了第一个程序,这一篇我们来编写一个驱动开启摄像头的红外补光灯,顺便熟悉一下鸿蒙上的 HDF 驱动开发。
硬件准备
先查一下原理图(具体可参考第一篇的硬件资料),找到红外灯的 IO 口编号,GPIO5_1。

HDF 驱动开发
1. 简介
HDF(OpenHarmony Driver Foundation)驱动框架,为驱动开发者提供驱动框架能力,包括驱动加载、驱动服务管理和驱动消息机制。旨在构建统一的驱动架构平台,为驱动开发者提供更精准、更高效的开发环境,力求做到一次开发,多系统部署。
HDF框架以组件化的驱动模型作为核心设计思路,为开发者提供更精细化的驱动管理,让驱动开发和部署更加规范。HDF框架将一类设备驱动放在同一个host里面,驱动内部实现开发者也可以将驱动功能分层独立开发和部署,支持一个驱动多个node,HDF框架管理驱动模型如下图所示:

2. 驱动框架
2.1 驱动框架实现
在 huawei/hdf
目录下新建一个文件夹 led
, 然后在其中新建一个源文件 led.c
。
#include "hdf_device_desc.h" // HDF框架对驱动开放相关能力接口的头文件
#include "hdf_log.h" // HDF 框架提供的日志接口头文件
#define HDF_LOG_TAG led_driver // 打印日志所包含的标签,如果不定义则用默认定义的HDF_TAG标签
//驱动对外提供的服务能力,将相关的服务接口绑定到HDF框架
int32_t HdfLedDriverBind(struct HdfDeviceObject *deviceObject)
{
HDF_LOGD("Led driver bind success");
return 0;
}
// 驱动自身业务初始的接口
int32_t HdfLedDriverInit(struct HdfDeviceObject *deviceObject)
{
if (deviceObject == NULL) {
HDF_LOGE("Led driver Init failed!");
return HDF_ERR_INVALID_OBJECT;
}
HDF_LOGD("Led driver Init success");
return HDF_SUCCESS;
}
// 驱动资源释放的接口
void HdfLedDriverRelease(struct HdfDeviceObject *deviceObject)
{
if (deviceObject == NULL) {
HDF_LOGE("Led driver release failed!");
return;
}
HDF_LOGD("Led driver release success");
return;
}
2.2 驱动入口注册到HDF框架
// 定义驱动入口的对象,必须为HdfDriverEntry(在hdf_device_desc.h中定义)类型的全局变量
struct HdfDriverEntry g_ledDriverEntry = {
.moduleVersion = 1,
.moduleName = "led_driver",
.Bind = HdfLedDriverBind,
.Init = HdfLedDriverInit,
.Release = HdfLedDriverRelease,
};
// 调用HDF_INIT将驱动入口注册到HDF框架中,在加载驱动时HDF框架会先调用Bind函数,再调用Init函数加载该驱动,当Init调用异常时,HDF框架会调用Release释放驱动资源并退出。
HDF_INIT(g_ledDriverEntry);
3. 驱动编译
在 huawei/hdf/led
目录下新建编译文件 Makefile
include $(LITEOSTOPDIR)/../../drivers/hdf/lite/lite.mk #导入hdf预定义内容,必需
MODULE_NAME := hdf_led_driver #生成的结果文件
LOCAL_SRCS += led.c #本驱动的源代码文件
LOCAL_INCLUDE := ./include #本驱动的头文件目录
LOCAL_CFLAGS += -fstack-protector-strong -Wextra -Wall -Werror #自定义的编译选项
include $(HDF_DRIVER) #导入模板makefile完成编译
这里的hdf_led_driver
为驱动文件名,注意对应关系。
4. 编译结果链接到内核镜像
修改 huawei/hdf/hdf_vendor.mk
文件,添加以下代码
LITEOS_BASELIB += -lhdf_led_driver #链接生成的静态库
LIB_SUBDIRS += $(VENDOR_HDF_DRIVERS_ROOT)/led #驱动代码Makefile的目录
填入驱动文件名和源码路径。
5. 驱动配置
驱动配置包含两部分,HDF框架定义的驱动设备描述和驱动的私有配置信息。
5.1 驱动设备描述(必选)
HDF框架加载驱动所需要的信息来源于HDF框架定义的驱动设备描述。
修改 vendor/hisi/hi35xx/hi3516dv300/config/device_info/device_info.hcs
配置文件,添加驱动的设备描述。
platform :: host {
hostName = "platform_host"; // host名称,host节点是用来存放某一类驱动的容器
priorit