• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2020-2021 Huawei Device Co., Ltd.
3  *
4  * HDF is dual licensed: you can use it either under the terms of
5  * the GPL, or the BSD license, at your option.
6  * See the LICENSE file in the root of this repository for complete details.
7  */
8 
9 #include "hdf_device_desc.h"
10 #include "platform_core.h"
11 #include "gpio_if.h"
12 #include "gpio/gpio_core.h"
13 #include "gpio/gpio_service.h"
14 
15 #define HDF_LOG_TAG gpio_service
16 
GpioServiceIoRead(struct HdfSBuf * data,struct HdfSBuf * reply)17 static int32_t GpioServiceIoRead(struct HdfSBuf *data, struct HdfSBuf *reply)
18 {
19     int32_t ret;
20     uint16_t gpio;
21     uint16_t value;
22 
23     if (data == NULL || reply == NULL) {
24         HDF_LOGE("%s: data or reply is NULL", __func__);
25         return HDF_ERR_INVALID_PARAM;
26     }
27 
28     if (!HdfSbufReadUint16(data, &gpio)) {
29         HDF_LOGE("%s: read gpio number fail", __func__);
30         return HDF_ERR_IO;
31     }
32 
33     ret = GpioRead(gpio, &value);
34     if (ret != HDF_SUCCESS) {
35         HDF_LOGE("%s: read gpio fail:%d", __func__, ret);
36         return ret;
37     }
38 
39     if (!HdfSbufWriteUint16(reply, value)) {
40         HDF_LOGE("%s: write subf fail:%d", __func__, ret);
41         return ret;
42     }
43 
44     return ret;
45 }
46 
GpioServiceIoWrite(struct HdfSBuf * data,struct HdfSBuf * reply)47 static int32_t GpioServiceIoWrite(struct HdfSBuf *data, struct HdfSBuf *reply)
48 {
49     int32_t ret;
50     uint16_t gpio;
51     uint16_t value;
52 
53     if (data == NULL || reply == NULL) {
54         HDF_LOGE("%s: data or reply is NULL", __func__);
55     }
56 
57     if (!HdfSbufReadUint16(data, &gpio)) {
58         HDF_LOGE("%s: read gpio number fail", __func__);
59         return HDF_ERR_IO;
60     }
61 
62     if (!HdfSbufReadUint16(data, &value)) {
63         HDF_LOGE("%s: read gpio value fail", __func__);
64         return HDF_ERR_IO;
65     }
66 
67     ret = GpioWrite(gpio, value);
68     if (ret != HDF_SUCCESS) {
69         HDF_LOGE("%s: write gpio fail:%d", __func__, ret);
70         return ret;
71     }
72 
73     return ret;
74 }
75 
GpioServiceIoGetDir(struct HdfSBuf * data,struct HdfSBuf * reply)76 static int32_t GpioServiceIoGetDir(struct HdfSBuf *data, struct HdfSBuf *reply)
77 {
78     int32_t ret;
79     uint16_t gpio;
80     uint16_t dir;
81 
82     if (data == NULL || reply == NULL) {
83         HDF_LOGE("%s: data or reply is NULL", __func__);
84         return HDF_ERR_INVALID_PARAM;
85     }
86 
87     if (!HdfSbufReadUint16(data, &gpio)) {
88         HDF_LOGE("%s: read gpio number fail", __func__);
89         return HDF_ERR_IO;
90     }
91 
92     ret = GpioGetDir(gpio, &dir);
93     if (ret != HDF_SUCCESS) {
94         HDF_LOGE("%s: get gpio dir fail:%d", __func__, ret);
95         return ret;
96     }
97 
98     if (!HdfSbufWriteUint16(reply, dir)) {
99         HDF_LOGE("%s: write subf fail:%d", __func__, ret);
100         return ret;
101     }
102 
103     return ret;
104 }
105 
GpioServiceIoSetDir(struct HdfSBuf * data,struct HdfSBuf * reply)106 static int32_t GpioServiceIoSetDir(struct HdfSBuf *data, struct HdfSBuf *reply)
107 {
108     int32_t ret;
109     uint16_t gpio;
110     uint16_t dir;
111 
112     if (data == NULL || reply == NULL) {
113         HDF_LOGE("%s: data or reply is NULL", __func__);
114         return HDF_ERR_INVALID_PARAM;
115     }
116 
117     if (!HdfSbufReadUint16(data, &gpio)) {
118         HDF_LOGE("%s: read gpio number fail", __func__);
119         return HDF_ERR_IO;
120     }
121 
122     if (!HdfSbufReadUint16(data, &dir)) {
123         HDF_LOGE("%s: read gpio dir fail", __func__);
124         return HDF_ERR_IO;
125     }
126 
127     ret = GpioSetDir(gpio, dir);
128     if (ret != HDF_SUCCESS) {
129         HDF_LOGE("%s: set gpio dir fail:%d", __func__, ret);
130         return ret;
131     }
132 
133     return ret;
134 }
135 
GpioServiceIoSetIrq(struct HdfSBuf * data,struct HdfSBuf * reply)136 static int32_t GpioServiceIoSetIrq(struct HdfSBuf *data, struct HdfSBuf *reply)
137 {
138     uint16_t gpio;
139     uint16_t mode;
140 
141     if (data == NULL || reply == NULL) {
142         HDF_LOGE("%s: data or reply is NULL", __func__);
143         return HDF_ERR_INVALID_PARAM;
144     }
145 
146     if (!HdfSbufReadUint16(data, &gpio)) {
147         HDF_LOGE("%s: read gpio fail", __func__);
148         return HDF_ERR_IO;
149     }
150 
151     if (!HdfSbufReadUint16(data, &mode)) {
152         HDF_LOGE("%s: read gpio mode fail", __func__);
153         return HDF_ERR_IO;
154     }
155 
156     return HDF_SUCCESS;
157 }
158 
GpioServiceIoUnsetIrq(struct HdfSBuf * data,struct HdfSBuf * reply)159 static int32_t GpioServiceIoUnsetIrq(struct HdfSBuf *data, struct HdfSBuf *reply)
160 {
161     uint16_t gpio;
162     (void)reply;
163 
164     if (data == NULL) {
165         HDF_LOGE("%s: data is NULL", __func__);
166         return HDF_ERR_INVALID_PARAM;
167     }
168 
169     if (!HdfSbufReadUint16(data, &gpio)) {
170         HDF_LOGE("%s: read gpio number fail", __func__);
171         return HDF_ERR_IO;
172     }
173 
174     return HDF_SUCCESS;
175 }
176 
GpioServiceIoEnableIrq(struct HdfSBuf * data,struct HdfSBuf * reply)177 static int32_t GpioServiceIoEnableIrq(struct HdfSBuf *data, struct HdfSBuf *reply)
178 {
179     int32_t ret;
180     uint16_t gpio;
181     (void)reply;
182 
183     if (data == NULL) {
184         HDF_LOGE("%s: data is NULL", __func__);
185         return HDF_ERR_INVALID_PARAM;
186     }
187 
188     if (!HdfSbufReadUint16(data, &gpio)) {
189         HDF_LOGE("%s: read gpio number fail", __func__);
190         return HDF_ERR_IO;
191     }
192 
193     ret = GpioEnableIrq(gpio);
194     if (ret != HDF_SUCCESS) {
195         HDF_LOGE("%s: enable gpio irq fail:%d", __func__, ret);
196         return ret;
197     }
198 
199     return ret;
200 }
201 
GpioServiceIoDisableIrq(struct HdfSBuf * data,struct HdfSBuf * reply)202 static int32_t GpioServiceIoDisableIrq(struct HdfSBuf *data, struct HdfSBuf *reply)
203 {
204     int32_t ret;
205     uint16_t gpio;
206     (void)reply;
207 
208     if (data == NULL) {
209         HDF_LOGE("%s: data is NULL", __func__);
210         return HDF_ERR_INVALID_PARAM;
211     }
212 
213     if (!HdfSbufReadUint16(data, &gpio)) {
214         HDF_LOGE("%s: read gpio number fail", __func__);
215         return HDF_ERR_IO;
216     }
217 
218     ret = GpioDisableIrq(gpio);
219     if (ret != HDF_SUCCESS) {
220         HDF_LOGE("%s: disable gpio irq fail:%d", __func__, ret);
221         return ret;
222     }
223 
224     return ret;
225 }
226 
227 
GpioServiceDispatch(struct HdfDeviceIoClient * client,int cmd,struct HdfSBuf * data,struct HdfSBuf * reply)228 static int32_t GpioServiceDispatch(struct HdfDeviceIoClient *client, int cmd,
229     struct HdfSBuf *data, struct HdfSBuf *reply)
230 {
231     int32_t ret;
232 
233     switch (cmd) {
234         case GPIO_IO_READ:
235             return GpioServiceIoRead(data, reply);
236         case GPIO_IO_WRITE:
237             return GpioServiceIoWrite(data, reply);
238         case GPIO_IO_GETDIR:
239             return GpioServiceIoGetDir(data, reply);
240         case GPIO_IO_SETDIR:
241             return GpioServiceIoSetDir(data, reply);
242         case GPIO_IO_SETIRQ:
243             return GpioServiceIoSetIrq(data, reply);
244         case GPIO_IO_UNSETIRQ:
245             return GpioServiceIoUnsetIrq(data, reply);
246         case GPIO_IO_ENABLEIRQ:
247             return GpioServiceIoEnableIrq(data, reply);
248         case GPIO_IO_DISABLEIRQ:
249             return GpioServiceIoDisableIrq(data, reply);
250         default:
251             ret = HDF_ERR_NOT_SUPPORT;
252             break;
253     }
254     return ret;
255 }
256 
GpioServiceBind(struct HdfDeviceObject * device)257 static int32_t GpioServiceBind(struct HdfDeviceObject *device)
258 {
259     int32_t ret;
260     struct PlatformManager *gpioMgr = NULL;
261 
262     PLAT_LOGI("GpioServiceBind: enter");
263     if (device == NULL) {
264         HDF_LOGE("GpioServiceBind: device is NULL");
265         return HDF_ERR_INVALID_OBJECT;
266     }
267 
268     gpioMgr = GpioManagerGet();
269     if (gpioMgr == NULL) {
270         HDF_LOGE("GpioServiceBind: get gpio manager fail");
271         return HDF_PLT_ERR_DEV_GET;
272     }
273 
274     ret = PlatformDeviceCreateService(&gpioMgr->device, GpioServiceDispatch);
275     if (ret != HDF_SUCCESS) {
276         HDF_LOGE("GpioServiceBind: create gpio service fail:%d", ret);
277         return ret;
278     }
279 
280     ret = PlatformDeviceBind(&gpioMgr->device, device);
281     if (ret != HDF_SUCCESS) {
282         HDF_LOGE("GpioServiceBind: bind gpio device fail:%d", ret);
283         (void)PlatformDeviceDestroyService(&gpioMgr->device);
284         return ret;
285     }
286 
287     PLAT_LOGI("GpioServiceBind: success");
288     return HDF_SUCCESS;
289 }
290 
GpioServiceInit(struct HdfDeviceObject * device)291 static int32_t GpioServiceInit(struct HdfDeviceObject *device)
292 {
293     (void)device;
294     return HDF_SUCCESS;
295 }
296 
GpioServiceRelease(struct HdfDeviceObject * device)297 static void GpioServiceRelease(struct HdfDeviceObject *device)
298 {
299     struct PlatformManager *gpioMgr = NULL;
300 
301     PLAT_LOGI("GpioServiceRelease: enter");
302     if (device == NULL) {
303         PLAT_LOGI("GpioServiceRelease: device is null");
304         return;
305     }
306 
307     gpioMgr = GpioManagerGet();
308     if (gpioMgr == NULL) {
309         HDF_LOGE("GpioServiceBind: get gpio manager fail");
310         return;
311     }
312 
313     (void)PlatformDeviceUnbind(&gpioMgr->device, device);
314     (void)PlatformDeviceDestroyService(&gpioMgr->device);
315     PLAT_LOGI("GpioServiceRelease: done");
316 }
317 
318 struct HdfDriverEntry g_gpioServiceEntry = {
319     .moduleVersion = 1,
320     .Bind = GpioServiceBind,
321     .Init = GpioServiceInit,
322     .Release = GpioServiceRelease,
323     .moduleName = "HDF_PLATFORM_GPIO_MANAGER",
324 };
325 HDF_INIT(g_gpioServiceEntry);
326