• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# 驱动消息机制管理<a name="ZH-CN_TOPIC_0000001052657065"></a>
2
3-   [使用场景](#section33014541954)
4-   [接口说明](#section538852311616)
5-   [开发步骤](#section946912121153)
6
7## 使用场景<a name="section33014541954"></a>
8
9当用户态应用和内核态驱动需要交互时,可以使用HDF框架的消息机制来实现。
10
11## 接口说明<a name="section538852311616"></a>
12
13消息机制的功能主要有以下两种:
14
151.  用户态应用发送消息到驱动。
162.  用户态应用接收驱动主动上报事件。
17
18**表 1**  消息机制接口
19
20<a name="table208212674114"></a>
21<table><thead align="left"><tr id="row08282618416"><th class="cellrowborder" valign="top" width="46.379999999999995%" id="mcps1.2.3.1.1"><p id="p382132664112"><a name="p382132664112"></a><a name="p382132664112"></a>方法</p>
22</th>
23<th class="cellrowborder" valign="top" width="53.620000000000005%" id="mcps1.2.3.1.2"><p id="p4826264419"><a name="p4826264419"></a><a name="p4826264419"></a>描述</p>
24</th>
25</tr>
26</thead>
27<tbody><tr id="row1582426174114"><td class="cellrowborder" valign="top" width="46.379999999999995%" headers="mcps1.2.3.1.1 "><p id="p182341916144420"><a name="p182341916144420"></a><a name="p182341916144420"></a>struct HdfIoService *HdfIoServiceBind(const char *serviceName)</p>
28</td>
29<td class="cellrowborder" valign="top" width="53.620000000000005%" headers="mcps1.2.3.1.2 "><p id="p58272614113"><a name="p58272614113"></a><a name="p58272614113"></a>用户态获取驱动的服务,获取该服务之后通过服务中的Dispatch方法向驱动发送消息。</p>
30</td>
31</tr>
32<tr id="row578565084913"><td class="cellrowborder" valign="top" width="46.379999999999995%" headers="mcps1.2.3.1.1 "><p id="p15786185024918"><a name="p15786185024918"></a><a name="p15786185024918"></a>void HdfIoServiceRecycle(struct HdfIoService *service);</p>
33</td>
34<td class="cellrowborder" valign="top" width="53.620000000000005%" headers="mcps1.2.3.1.2 "><p id="p47861750154912"><a name="p47861750154912"></a><a name="p47861750154912"></a>释放驱动服务。</p>
35</td>
36</tr>
37<tr id="row1382112617413"><td class="cellrowborder" valign="top" width="46.379999999999995%" headers="mcps1.2.3.1.1 "><p id="p482182611415"><a name="p482182611415"></a><a name="p482182611415"></a>int HdfDeviceRegisterEventListener(struct HdfIoService *target, struct HdfDevEventlistener *listener);</p>
38</td>
39<td class="cellrowborder" valign="top" width="53.620000000000005%" headers="mcps1.2.3.1.2 "><p id="p18825261412"><a name="p18825261412"></a><a name="p18825261412"></a>用户态程序注册接收驱动上报事件的操作方法。</p>
40</td>
41</tr>
42<tr id="row498956124019"><td class="cellrowborder" valign="top" width="46.379999999999995%" headers="mcps1.2.3.1.1 "><p id="p6412911184019"><a name="p6412911184019"></a><a name="p6412911184019"></a>int HdfDeviceSendEvent(struct HdfDeviceObject *deviceObject, uint32_t id, struct HdfSBuf *data);</p>
43</td>
44<td class="cellrowborder" valign="top" width="53.620000000000005%" headers="mcps1.2.3.1.2 "><p id="p1698915634018"><a name="p1698915634018"></a><a name="p1698915634018"></a>驱动主动上报事件接口。</p>
45</td>
46</tr>
47</tbody>
48</table>
49
50## 开发步骤<a name="section946912121153"></a>
51
521.  将驱动配置信息中服务策略policy字段设置为2(SERVICE\_POLICY\_CAPACITY,参考[policy定义](driver-hdf-servicemanage.md))。
53
54    ```
55    device_sample :: Device {
56        policy = 2;
57        ...
58    }
59    ```
60
612.  配置驱动信息中的服务设备节点权限(permission字段)是框架给驱动创建设备节点的权限,默认是0666,驱动开发者根据驱动的实际使用场景配置驱动设备节点的权限。
623.  在服务实现过程中,实现服务基类成员IDeviceIoService中的Dispatch方法。
63
64    ```
65    // Dispatch是用来处理用户态发下来的消息
66    int32_t SampleDriverDispatch(struct HdfDeviceObject *device, int cmdCode, struct HdfSBuf *data, struct HdfSBuf *reply)
67    {
68        HDF_LOGE("sample driver lite A dispatch");
69        return 0;
70    }
71    int32_t SampleDriverBind(struct HdfDeviceObject *device)
72    {
73        HDF_LOGE("test for lite os sample driver A Open!");
74        if (device == NULL) {
75            HDF_LOGE("test for lite os sample driver A Open failed!");
76            return -1;
77        }
78        static struct ISampleDriverService sampleDriverA = {
79            .ioService.Dispatch = SampleDriverDispatch,
80            .ServiceA = SampleDriverServiceA,
81            .ServiceB = SampleDriverServiceB,
82        };
83        device->service = (struct IDeviceIoService *)(&sampleDriverA);
84        return 0;
85    }
86    ```
87
884.  驱动定义消息处理函数中的cmd类型。
89
90    ```
91    #define SAMPLE_WRITE_READ 1    // 读写操作码1
92    ```
93
945.  用户态获取服务接口并发送消息到驱动。
95
96    ```
97    int SendMsg(const char *testMsg)
98    {
99        if (testMsg == NULL) {
100            HDF_LOGE("test msg is null");
101            return -1;
102        }
103        struct HdfIoService *serv = HdfIoServiceBind("sample_driver");
104        if (serv == NULL) {
105            HDF_LOGE("fail to get service");
106            return -1;
107        }
108        struct HdfSBuf *data = HdfSBufObtainDefaultSize();
109        if (data == NULL) {
110            HDF_LOGE("fail to obtain sbuf data");
111            return -1;
112        }
113        struct HdfSBuf *reply = HdfSBufObtainDefaultSize();
114        if (reply == NULL) {
115            HDF_LOGE("fail to obtain sbuf reply");
116            ret = HDF_DEV_ERR_NO_MEMORY;
117            goto out;
118        }
119        if (!HdfSbufWriteString(data, testMsg)) {
120            HDF_LOGE("fail to write sbuf");
121            ret = HDF_FAILURE;
122            goto out;
123        }
124        int ret = serv->dispatcher->Dispatch(&serv->object, SAMPLE_WRITE_READ, data, reply);
125        if (ret != HDF_SUCCESS) {
126            HDF_LOGE("fail to send service call");
127            goto out;
128        }
129    out:
130        HdfSBufRecycle(data);
131        HdfSBufRecycle(reply);
132        HdfIoServiceRecycle(serv);
133        return ret;
134    }
135    ```
136
1376.  用户态接收该驱动上报的消息。
138    1.  用户态编写驱动上报消息的处理函数。
139
140        ```
141        static int OnDevEventReceived(void *priv,  uint32_t id, struct HdfSBuf *data)
142        {
143            OsalTimespec time;
144            OsalGetTime(&time);
145            HDF_LOGE("%s received event at %llu.%llu", (char *)priv, time.sec, time.usec);
146
147            const char *string = HdfSbufReadString(data);
148            if (string == NULL) {
149                HDF_LOGE("fail to read string in event data");
150                return -1;
151            }
152            HDF_LOGE("%s: dev event received: %d %s",  (char *)priv, id, string);
153            return 0;
154        }
155        ```
156
157    2.  用户态注册接收驱动上报消息的操作方法。
158
159        ```
160        int RegisterListen()
161        {
162            struct HdfIoService *serv = HdfIoServiceBind("sample_driver");
163            if (serv == NULL) {
164                HDF_LOGE("fail to get service");
165                return -1;
166            }
167            static struct HdfDevEventlistener listener = {
168                .callBack = OnDevEventReceived,
169                .priv ="Service0"
170            };
171            if (HdfDeviceRegisterEventListener(serv, &listener) != 0) {
172                HDF_LOGE("fail to register event listener");
173                return -1;
174            }
175            ......
176            HdfDeviceUnregisterEventListener(serv, &listener);
177            HdfIoServiceRecycle(serv);
178            return 0;
179        }
180        ```
181
182    3.  驱动上报事件。
183
184        ```
185        int32_t SampleDriverDispatch(struct HdfDeviceObject *device, int cmdCode, struct HdfSBuf *data, struct HdfSBuf *reply)
186        {
187            ... // process api call here
188            return HdfDeviceSendEvent(deviceObject, cmdCode, data);
189        }
190        ```
191
192
193
194