1 /*
2 * Copyright (c) 2022 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 "platform_listener_u.h"
10 #include "hdf_log.h"
11 #include "osal_mem.h"
12 #include "platform_listener_common.h"
13
RtcOnDevEventReceive(void * priv,uint32_t id,struct HdfSBuf * data)14 int RtcOnDevEventReceive(void *priv, uint32_t id, struct HdfSBuf *data)
15 {
16 struct PlatformUserListenerRtcParam *rtc = NULL;
17 struct PlatformUserListener *userListener = NULL;
18 uint8_t index;
19 if (priv == NULL || data == NULL) {
20 HDF_LOGE("RtcOnDevEventReceive id %d param error", id);
21 return HDF_FAILURE;
22 }
23
24 userListener = (struct PlatformUserListener *)priv;
25 rtc = (struct PlatformUserListenerRtcParam *)userListener->data;
26 if (rtc == NULL || rtc->func == NULL) {
27 HDF_LOGE("RtcOnDevEventReceive rtc id %d error", id);
28 return HDF_FAILURE;
29 }
30
31 if (!HdfSbufReadUint8(data, &index)) {
32 HDF_LOGE("RtcOnDevEventReceive id %d read sbuf fail", id);
33 return HDF_ERR_IO;
34 }
35
36 HDF_LOGD("RtcOnDevEventReceive event %d index:%d == index:%d", id, index, rtc->index);
37 if ((id == PLATFORM_LISTENER_EVENT_RTC_ALARM_NOTIFY) && (index == rtc->index)) {
38 rtc->func(index);
39 }
40 return HDF_SUCCESS;
41 }
42
TimerOnDevEventReceive(void * priv,uint32_t id,struct HdfSBuf * data)43 int TimerOnDevEventReceive(void *priv, uint32_t id, struct HdfSBuf *data)
44 {
45 struct PlatformUserListenerTimerParam *timer = NULL;
46 struct PlatformUserListener *userListener = NULL;
47 uint32_t handle;
48 if (priv == NULL || data == NULL) {
49 HDF_LOGE("TimerOnDevEventReceive id %d param error", id);
50 return HDF_FAILURE;
51 }
52
53 userListener = (struct PlatformUserListener *)priv;
54 timer = (struct PlatformUserListenerTimerParam *)userListener->data;
55 if (timer == NULL || timer->func == NULL) {
56 HDF_LOGE("TimerOnDevEventReceive timer id %d error", id);
57 return HDF_FAILURE;
58 }
59
60 if (!HdfSbufReadUint32(data, &handle)) {
61 HDF_LOGE("TimerOnDevEventReceive id %d read sbuf fail", id);
62 return HDF_ERR_IO;
63 }
64
65 HDF_LOGD("TimerOnDevEventReceive event %d handle:%d == handle:%d", id, handle, timer->handle);
66 if ((id == PLATFORM_LISTENER_EVENT_TIMER_NOTIFY) && (handle == timer->handle)) {
67 timer->func(handle);
68 }
69 return HDF_SUCCESS;
70 }
71
GpioOnDevEventReceive(void * priv,uint32_t id,struct HdfSBuf * data)72 int GpioOnDevEventReceive(void *priv, uint32_t id, struct HdfSBuf *data)
73 {
74 struct PlatformUserListenerGpioParam *gpio = NULL;
75 struct PlatformUserListener *userListener = NULL;
76 uint16_t gpioId;
77 if (priv == NULL || data == NULL) {
78 HDF_LOGE("GpioOnDevEventReceive id %d param error", id);
79 return HDF_FAILURE;
80 }
81
82 userListener = (struct PlatformUserListener *)priv;
83 gpio = (struct PlatformUserListenerGpioParam *)userListener->data;
84 if (gpio == NULL || gpio->data == NULL || gpio->func == NULL) {
85 HDF_LOGE("GpioOnDevEventReceive id %d gpio error", id);
86 return HDF_FAILURE;
87 }
88
89 if (!HdfSbufReadUint16(data, &gpioId)) {
90 HDF_LOGE("GpioOnDevEventReceive id %d read sbuf fail", id);
91 return HDF_ERR_IO;
92 }
93
94 HDF_LOGD("GpioOnDevEventReceive event %d gpioId:%d == gpio:%d", id, gpioId, gpio->gpio);
95 if ((id == PLATFORM_LISTENER_EVENT_GPIO_INT_NOTIFY) && (gpioId == gpio->gpio)) {
96 gpio->func(gpioId, gpio->data);
97 }
98 return HDF_SUCCESS;
99 }
100
PlatformUserListenerInit(const struct PlatformUserListenerManager * manager,uint32_t num,void * data,OnEventReceived callback)101 static struct PlatformUserListener *PlatformUserListenerInit(
102 const struct PlatformUserListenerManager *manager, uint32_t num, void *data, OnEventReceived callback)
103 {
104 struct PlatformUserListener *userListener = NULL;
105 struct HdfDevEventlistener *listener = NULL;
106
107 userListener = OsalMemCalloc(sizeof(struct PlatformUserListener));
108 if (userListener == NULL) {
109 HDF_LOGE("PlatformUserListenerInit userListener get failed");
110 return NULL;
111 }
112
113 listener = OsalMemCalloc(sizeof(struct HdfDevEventlistener));
114 if (listener == NULL) {
115 HDF_LOGE("PlatformUserListenerInit hdf listener get failed");
116 OsalMemFree(userListener);
117 return NULL;
118 }
119
120 userListener->listener = listener;
121 userListener->moudle = manager->moudle;
122 userListener->num = num;
123 userListener->data = data;
124
125 listener->callBack = callback;
126 listener->priv = userListener;
127 if (HdfDeviceRegisterEventListener(manager->service, listener) != HDF_SUCCESS) {
128 HDF_LOGE("PlatformUserListenerInit HdfDeviceRegisterEventListener failed");
129 OsalMemFree(userListener);
130 OsalMemFree(listener);
131 return NULL;
132 }
133
134 HDF_LOGD("PlatformUserListenerInit get listener for %d %d success", manager->moudle, num);
135 return userListener;
136 }
137
PlatformUserListenerReg(struct PlatformUserListenerManager * manager,uint32_t num,void * data,OnEventReceived callback)138 int32_t PlatformUserListenerReg(
139 struct PlatformUserListenerManager *manager, uint32_t num, void *data, OnEventReceived callback)
140 {
141 struct PlatformUserListener *pos = NULL;
142 struct PlatformUserListener *node = NULL;
143 if (manager == NULL || callback == NULL) {
144 HDF_LOGE("PlatformUserListenerReg param null");
145 return HDF_FAILURE;
146 }
147
148 if (OsalMutexLock(&manager->lock) != HDF_SUCCESS) {
149 HDF_LOGE("PlatformUserListenerReg: OsalMutexLock failed");
150 return HDF_FAILURE;
151 };
152 DLIST_FOR_EACH_ENTRY(pos, &manager->listeners, struct PlatformUserListener, node) {
153 if (pos->num == num) {
154 (void)OsalMutexUnlock(&manager->lock);
155 return HDF_SUCCESS;
156 }
157 }
158
159 node = PlatformUserListenerInit(manager, num, data, callback);
160 if (node == NULL) {
161 HDF_LOGE("PlatformUserListenerReg PlatformUserListenerInit fail");
162 (void)OsalMutexUnlock(&manager->lock);
163 return HDF_FAILURE;
164 }
165
166 DListInsertTail(&node->node, &manager->listeners);
167 (void)OsalMutexUnlock(&manager->lock);
168 return HDF_SUCCESS;
169 }
170
PlatformUserListenerDestory(struct PlatformUserListenerManager * manager,uint32_t num)171 void PlatformUserListenerDestory(struct PlatformUserListenerManager *manager, uint32_t num)
172 {
173 struct PlatformUserListener *pos = NULL;
174 struct PlatformUserListener *tmp = NULL;
175 if (manager == NULL) {
176 HDF_LOGE("PlatformUserListenerDestory manager null");
177 return;
178 }
179 if (OsalMutexLock(&manager->lock) != HDF_SUCCESS) {
180 HDF_LOGE("%s: OsalMutexLock failed", __func__);
181 return;
182 }
183 DLIST_FOR_EACH_ENTRY_SAFE(pos, tmp, &manager->listeners, struct PlatformUserListener, node) {
184 if (pos->num == num) {
185 HDF_LOGD("PlatformUserListenerDestory: node [%d][%d] find, then del", manager->moudle, num);
186 if (HdfDeviceUnregisterEventListener(manager->service, pos->listener) != HDF_SUCCESS) {
187 HDF_LOGE("PlatformUserListenerDestory unregister fail");
188 (void)OsalMutexUnlock(&manager->lock);
189 return;
190 }
191 OsalMemFree(pos->listener);
192 OsalMemFree(pos->data);
193 DListRemove(&pos->node);
194 OsalMemFree(pos);
195 (void)OsalMutexUnlock(&manager->lock);
196 return;
197 }
198 }
199 (void)OsalMutexUnlock(&manager->lock);
200 }
201
PlatformUserListenerManagerGet(enum PlatformModuleType moudle)202 struct PlatformUserListenerManager *PlatformUserListenerManagerGet(enum PlatformModuleType moudle)
203 {
204 struct PlatformUserListenerManager *manager = OsalMemCalloc(sizeof(struct PlatformUserListenerManager));
205 if (manager == NULL) {
206 HDF_LOGE("PlatformUserListenerManagerGet manager get failed");
207 return NULL;
208 }
209
210 manager->moudle = moudle;
211 DListHeadInit(&manager->listeners);
212 if (OsalMutexInit(&manager->lock) != HDF_SUCCESS) {
213 HDF_LOGE("PlatformUserListenerManagerGet moudle %d OsalSpinInit fail", moudle);
214 OsalMemFree(manager);
215 return NULL;
216 }
217
218 HDF_LOGD("PlatformUserListenerManagerGet moudle %d success", moudle);
219 return manager;
220 }
221