|
HarmonyOS HDF驅(qū)動框架---驅(qū)動消息機制管理,
使用場景
當(dāng)用戶態(tài)應(yīng)用和內(nèi)核態(tài)驅(qū)動需要交互時,可以使用HDF框架的消息機制來實現(xiàn)。
接口說明 消息機制的功能主要有以下兩種:
- 用戶態(tài)應(yīng)用發(fā)送消息到驅(qū)動。
- 用戶態(tài)應(yīng)用接收驅(qū)動主動上報事件。
表1 消息機制接口[td]
方法 | 描述 | struct HdfIoService *HdfIoServiceBind(const char *serviceName, mode_t permission) | 用戶態(tài)獲取驅(qū)動的服務(wù),獲取該服務(wù)之后通過服務(wù)中的Dispatch方法向驅(qū)動發(fā)送消息。 | void HdfIoServiceRecycle(struct HdfIoService *service); | 釋放驅(qū)動服務(wù)。 | int HdfDeviceRegisterEventListener(struct HdfIoService *target, struct HdfDevEventlistener *listener); | 用戶態(tài)程序注冊接收驅(qū)動上報事件的操作方法。 | int HdfDeviceSendEvent(struct HdfDeviceObject *deviceObject, uint32_t id, struct HdfSBuf *data); | 驅(qū)動主動上報事件接口。 |
開發(fā)步驟
- 將驅(qū)動配置信息中服務(wù)策略policy字段設(shè)置為2(SERVICE_POLICY_CAPACITY,參考policy定義)。
- device_sample :: Device {
- policy = 2;
- ...
- }
- 配置驅(qū)動信息中的服務(wù)設(shè)備節(jié)點權(quán)限(permission字段)是框架給驅(qū)動創(chuàng)建設(shè)備節(jié)點的權(quán)限,默認(rèn)是0666,驅(qū)動開發(fā)者根據(jù)驅(qū)動的實際使用場景配置驅(qū)動設(shè)備節(jié)點的權(quán)限。
- 在服務(wù)實現(xiàn)過程中,實現(xiàn)服務(wù)基類成員IDeviceIoService中的Dispatch方法。
- // Dispatch是用來處理用戶態(tài)發(fā)下來的消息
- int32_t SampLEDriverDispatch(struct HdfDeviceObject *device, int cmdCode, struct HdfSBuf *data, struct HdfSBuf *reply)
- {
- HDF_LOGE(“sample driver lite A dispatch“);
- return 0;
- }
- int32_t SampleDriverBind(struct HdfDeviceObject *device)
- {
- HDF_LOGE(“test for lite os sample driver A Open!“);
- IF (device == NULL) {
- HDF_LOGE(“test for lite os sample driver A Open failed!“);
- return -1;
- }
- static struct ISampleDriverService sampleDriverA = {
- .ioService.Dispatch = SampleDriverDispatch,
- .ServiceA = SampleDriverServiceA,
- .ServiceB = SampleDriverServiceB,
- };
- device->service = (struct IDeviceIoService *)(&sampleDriverA);
- return 0;
- }
- 驅(qū)動定義消息處理函數(shù)中的cmd類型。
- #define SAMPLE_WRITE_READ 1 // 讀寫操作碼1
- 用戶態(tài)獲取服務(wù)接口并發(fā)送消息到驅(qū)動。
- int SendMsg(const char *testMsg)
- {
- if (testMsg == NULL) {
- HDF_LOGE(“test msg is null“);
- return -1;
- }
- struct HdfIoService *serv = HdfIoServiceBind(“sample_driver“, 0);
- if (serv == NULL) {
- HDF_LOGE(“fail to get service“);
- return -1;
- }
- struct HdfSBuf *data = HdfSBufObtainDefaultSize();
- if (data == NULL) {
- HDF_LOGE(“fail to obtain sbuf data“);
- return -1;
- }
- struct HdfSBuf *reply = HdfSBufObtainDefaultSize();
- if (reply == NULL) {
- HDF_LOGE(“fail to obtain sbuf reply“);
- ret = HDF_DEV_ERR_NO_MEMORY;
- goto out;
- }
- if (!HdfSbufWriteString(data, testMsg)) {
- HDF_LOGE(“fail to write sbuf“);
- ret = HDF_FAILURE;
- goto out;
- }
- int ret = serv->dispatcher->Dispatch(&serv->object, SAMPLE_WRITE_READ, data, reply);
- if (ret != HDF_SUCCESS) {
- HDF_LOGE(“fail to send service call“);
- goto out;
- }
- out:
- HdfSBufRecycle(data);
- HdfSBufRecycle(reply);
- HdfIoServiceRecycle(serv);
- return ret;
- }
- 用戶態(tài)接收該驅(qū)動上報的消息。
- 用戶態(tài)編寫驅(qū)動上報消息的處理函數(shù)。
- static int OnDevEventReceived(void *priv, uint32_t id, struct HdfSBuf *data)
- {
- OsalTimespec time;
- OsalGetTime(&time);
- HDF_LOGE(“%s received event at %llu.%llu“, (char *)priv, time.sec, time.usec);
-
- const char *string = HdfSbufReadString(data);
- if (string == NULL) {
- HDF_LOGE(“fail to read string in event data“);
- return -1;
- }
- HDF_LOGE(“%s: dev event received: %d %s“, (char *)priv, id, string);
- return 0;
- }
- 用戶態(tài)注冊接收驅(qū)動上報消息的操作方法。
- int RegisterListen()
- {
- struct HdfIoService *serv = HdfIoServiceBind(“sample_driver“, 0);
- if (serv == NULL) {
- HDF_LOGE(“fail to get service“);
- return -1;
- }
- static struct HdfDevEventlistener listener = {
- .callBack = OnDevEventReceived,
- .priv =“Service0“
- };
- if (HdfDeviceRegisterEventListener(serv, &listener) != 0) {
- HDF_LOGE(“fail to register event listener“);
- return -1;
- }
- ......
- HdfDeviceUnregisterEventListener(serv, &listener);
- HdfIoServiceRecycle(serv);
- return 0;
- }
- 驅(qū)動上報事件。
- int32_t SampleDriverDispatch(struct HdfDeviceObject *device, int cmdCode, struct HdfSBuf *data, struct HdfSBuf *reply)
- {
- ... // process api call here
- return HdfDeviceSendEvent(deviceObject, cmdCode, data);
- }
|
|