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_input_device_manager.h"
10 #include <securec.h>
11 #include "event_hub.h"
12 #include "hdf_base.h"
13 #include "hdf_device_object.h"
14 #include "hdf_log.h"
15 #include "osal_mem.h"
16
17 #define NODE_MODE 0660
18 #define SERVICE_NAME_LEN 24
19 #define QUEUE_NAME_LEN 18
20 #define INPUT_DEV_EXIST 1
21 #define INPUT_DEV_NOT_EXIST 0
22 #define INPUTDEV_FIRST_ID 2
23 #define FILLER_FLAG 1
24 #define PLACEHOLDER_LENGTH 2
25 #define PLACEHOLDER_LIMIT 10
26
27 static InputManager *g_inputManager;
28
GetInputManager(void)29 InputManager* GetInputManager(void)
30 {
31 return g_inputManager;
32 }
33
IsHidDevice(InputDevice * inputDev)34 static bool IsHidDevice(InputDevice *inputDev)
35 {
36 if ((inputDev->devType > INDEV_TYPE_HID_BEGIN_POS) && (inputDev->devType < INDEV_TYPE_UNKNOWN)) {
37 return true;
38 #ifdef CONFIG_ARCH_ROCKCHIP
39 } else if (strncmp(inputDev->devName, "hid-powerkey", strlen("hid-powerkey")) == 0) {
40 return true;
41 #endif
42 }
43 return false;
44 }
45
HidRegisterHdfDevice(InputDevice * inputDev)46 static struct HdfDeviceObject *HidRegisterHdfDevice(InputDevice *inputDev)
47 {
48 char svcName[SERVICE_NAME_LEN] = {0};
49 const char *moduleName = "HDF_HID";
50 struct HdfDeviceObject *hdfDev = NULL;
51
52 int32_t len = (inputDev->devId < PLACEHOLDER_LIMIT) ? 1 : PLACEHOLDER_LENGTH;
53 int32_t ret = snprintf_s(svcName, SERVICE_NAME_LEN, strlen("hdf_input_event") + len, "%s%u",
54 "hdf_input_event", inputDev->devId);
55 if (ret < 0) {
56 HDF_LOGE("%s: snprintf_s failed", __func__);
57 return NULL;
58 }
59
60 hdfDev = HdfDeviceObjectAlloc(g_inputManager->hdfDevObj, moduleName);
61 if (hdfDev == NULL) {
62 HDF_LOGE("%s: failed to alloc device object", __func__);
63 return NULL;
64 }
65 ret = HdfDeviceObjectRegister(hdfDev);
66 if (ret != HDF_SUCCESS) {
67 HDF_LOGE("%s: failed to register device %s", __func__, moduleName);
68 HdfDeviceObjectRelease(hdfDev);
69 return NULL;
70 }
71 ret = HdfDeviceObjectPublishService(hdfDev, svcName, SERVICE_POLICY_CAPACITY, 0664); // 0664:permission setting
72 if (ret != HDF_SUCCESS) {
73 HDF_LOGE("%s: failed to register device %s", __func__, moduleName);
74 HdfDeviceObjectRelease(hdfDev);
75 return NULL;
76 }
77 inputDev->hdfDevObj = hdfDev;
78 HDF_LOGI("%s: svcName is %s, devName = %s", __func__, svcName, inputDev->devName);
79 return hdfDev;
80 }
81
HotPlugNotify(const InputDevice * inputDev,uint32_t status)82 static void HotPlugNotify(const InputDevice *inputDev, uint32_t status)
83 {
84 HotPlugEvent event = {0};
85 int32_t ret;
86
87 if (inputDev->eventBuf == NULL) {
88 HDF_LOGE("%s: event buffer is null", __func__);
89 return;
90 }
91
92 event.devId = inputDev->devId;
93 event.devType = inputDev->devType;
94 event.status = status;
95
96 if (!HdfSbufWriteBuffer(inputDev->eventBuf, &event, sizeof(HotPlugEvent))) {
97 HDF_LOGE("%s: write buffer failed", __func__);
98 HdfSbufFlush(inputDev->eventBuf);
99 return;
100 }
101 ret = HdfDeviceSendEvent(g_inputManager->hdfDevObj, 0, inputDev->eventBuf);
102 if (ret != HDF_SUCCESS) {
103 HDF_LOGE("%s: send event failed", __func__);
104 }
105 HdfSbufFlush(inputDev->eventBuf);
106 }
107
CreateDeviceNode(InputDevice * inputDev)108 static int32_t CreateDeviceNode(InputDevice *inputDev)
109 {
110 if (IsHidDevice(inputDev)) {
111 HDF_LOGI("%s: prepare to register hdf device", __func__);
112 inputDev->hdfDevObj = HidRegisterHdfDevice(inputDev);
113 if (inputDev->hdfDevObj == NULL) {
114 return HDF_DEV_ERR_NO_DEVICE;
115 }
116 inputDev->hdfDevObj->priv = (void *)inputDev;
117 }
118
119 HDF_LOGI("%s: create node succ, devId is %d ", __func__, inputDev->devId);
120 return HDF_SUCCESS;
121 }
122
DeleteDeviceNode(InputDevice * inputDev)123 static void DeleteDeviceNode(InputDevice *inputDev)
124 {
125 if (IsHidDevice(inputDev)) {
126 HDF_LOGI("remove input device: hdf_input_event%u", inputDev->devId);
127 HdfDeviceObjectRelease(inputDev->hdfDevObj);
128 }
129
130 HDF_LOGI("%s: delete node succ, devId is %d", __func__, inputDev->devId);
131 }
132
AddInputDevice(InputDevice * inputDev)133 static void AddInputDevice(InputDevice *inputDev)
134 {
135 InputDevice *tmpDev = NULL;
136 if (g_inputManager->inputDevList == NULL) {
137 g_inputManager->inputDevList = inputDev;
138 (g_inputManager->inputDevList)->next = NULL;
139 } else {
140 tmpDev = g_inputManager->inputDevList;
141 while (tmpDev != NULL) {
142 if (tmpDev->next == NULL) {
143 tmpDev->next = inputDev;
144 inputDev->next = NULL;
145 break;
146 }
147 tmpDev = tmpDev->next;
148 }
149 }
150 g_inputManager->devCount++;
151 HotPlugNotify(inputDev, ONLINE);
152 }
153
CheckInputDevice(InputDevice * inputDev)154 static int32_t CheckInputDevice(InputDevice *inputDev)
155 {
156 InputDevice *tmpDev = NULL;
157 if (g_inputManager->inputDevList == NULL) {
158 return HDF_SUCCESS;
159 } else {
160 tmpDev = g_inputManager->inputDevList;
161 while (tmpDev != NULL) {
162 if (tmpDev->devId == inputDev->devId) {
163 HDF_LOGE("%s: device%d registered", __func__, inputDev->devId);
164 return INPUT_DEV_EXIST;
165 }
166 tmpDev = tmpDev->next;
167 }
168 }
169 return INPUT_DEV_NOT_EXIST;
170 }
171
DeleteInputDevice(InputDevice * inputDev)172 static int32_t DeleteInputDevice(InputDevice *inputDev)
173 {
174 if (g_inputManager->inputDevList == NULL) {
175 return HDF_FAILURE;
176 } else {
177 if ((g_inputManager->inputDevList)->devId == inputDev->devId) {
178 g_inputManager->inputDevList = g_inputManager->inputDevList->next;
179 goto EXIT;
180 }
181
182 InputDevice *preNode = g_inputManager->inputDevList;
183 InputDevice *tmpDev = preNode->next;
184 while (tmpDev != NULL) {
185 if (tmpDev->devId == inputDev->devId) {
186 preNode->next = tmpDev->next;
187 goto EXIT;
188 }
189 preNode = tmpDev;
190 tmpDev = tmpDev->next;
191 }
192 HDF_LOGE("%s: device%d not exist", __func__, inputDev->devId);
193 return HDF_FAILURE;
194 }
195
196 EXIT:
197 g_inputManager->devCount--;
198 HotPlugNotify(inputDev, OFFLINE);
199 return HDF_SUCCESS;
200 }
201
202 #define DEFAULT_TOUCH_BUF_PKG_NUM 50
203 #define DEFAULT_KEY_BUF_PKG_NUM 10
204 #define DEFAULT_MOUSE_BUF_PKG_NUM 30
205 #define DEFAULT_KEYBOARD_BUF_PKG_NUM 20
206 #define DEFAULT_CROWN_BUF_PKG_NUM 20
207 #define DEFAULT_ENCODER_BUF_PKG_NUM 20
208 #define DEFAULT_ROCKER_BUF_PKG_NUM 40
209 #define DEFAULT_TRACKBALL_BUF_PKG_NUM 30
210
AllocPackageBuffer(InputDevice * inputDev)211 static int32_t AllocPackageBuffer(InputDevice *inputDev)
212 {
213 uint16_t pkgNum;
214 switch (inputDev->devType) {
215 case INDEV_TYPE_TOUCH:
216 pkgNum = DEFAULT_TOUCH_BUF_PKG_NUM;
217 break;
218 case INDEV_TYPE_KEY:
219 pkgNum = DEFAULT_KEY_BUF_PKG_NUM;
220 break;
221 case INDEV_TYPE_MOUSE:
222 pkgNum = DEFAULT_MOUSE_BUF_PKG_NUM;
223 break;
224 case INDEV_TYPE_KEYBOARD:
225 pkgNum = DEFAULT_KEYBOARD_BUF_PKG_NUM;
226 break;
227 case INDEV_TYPE_CROWN:
228 pkgNum = DEFAULT_CROWN_BUF_PKG_NUM;
229 break;
230 case INDEV_TYPE_ENCODER:
231 pkgNum = DEFAULT_ENCODER_BUF_PKG_NUM;
232 break;
233 case INDEV_TYPE_ROCKER:
234 pkgNum = DEFAULT_ROCKER_BUF_PKG_NUM;
235 break;
236 case INDEV_TYPE_TRACKBALL:
237 pkgNum = DEFAULT_TRACKBALL_BUF_PKG_NUM;
238 break;
239 default:
240 HDF_LOGE("%s: devType not exist", __func__);
241 return HDF_FAILURE;
242 }
243 inputDev->pkgBuf = HdfSbufObtain(sizeof(EventPackage) * pkgNum);
244 if (inputDev->pkgBuf == NULL) {
245 HDF_LOGE("%s: malloc sbuf failed", __func__);
246 return HDF_ERR_MALLOC_FAIL;
247 }
248 inputDev->eventBuf = HdfSbufObtain(sizeof(HotPlugEvent));
249 if (inputDev->eventBuf == NULL) {
250 HDF_LOGE("%s: malloc sbuf failed", __func__);
251 return HDF_ERR_MALLOC_FAIL;
252 }
253 inputDev->pkgNum = pkgNum;
254 return HDF_SUCCESS;
255 }
256
AllocDeviceID(InputDevice * inputDev)257 static int32_t AllocDeviceID(InputDevice *inputDev)
258 {
259 InputDevice *tmpDev = g_inputManager->inputDevList;
260 uint32_t idList[MAX_INPUT_DEV_NUM + 1];
261 uint32_t id;
262 int32_t ret;
263 ret = memset_s(idList, (MAX_INPUT_DEV_NUM + 1) * sizeof(uint32_t), 0,
264 (MAX_INPUT_DEV_NUM + 1) * sizeof(uint32_t));
265 if (ret != 0) {
266 HDF_LOGE("%s: memset_s is failed", __func__);
267 return HDF_FAILURE;
268 }
269 while (tmpDev != NULL) {
270 if (idList[tmpDev->devId] == 0) {
271 idList[tmpDev->devId] = FILLER_FLAG;
272 }
273 tmpDev = tmpDev->next;
274 }
275
276 if (inputDev->devType == INDEV_TYPE_TOUCH) {
277 inputDev->devId = 1;
278 return HDF_SUCCESS;
279 }
280 for (id = INPUTDEV_FIRST_ID; id < MAX_INPUT_DEV_NUM + 1; id++) {
281 if (idList[id] == 0) {
282 inputDev->devId = id;
283 return HDF_SUCCESS;
284 }
285 }
286 HDF_LOGE("%s: alloc device id failed", __func__);
287 return HDF_FAILURE;
288 }
289
290 #ifndef __LITEOS_M__
InitEventWorkQueue(InputDevice * inputDev)291 static int32_t InitEventWorkQueue(InputDevice *inputDev)
292 {
293 char queueName[QUEUE_NAME_LEN] = {0};
294
295 int32_t len = (inputDev->devId < PLACEHOLDER_LIMIT) ? 1 : PLACEHOLDER_LENGTH;
296 int32_t ret = snprintf_s(queueName, QUEUE_NAME_LEN, strlen("hdf_event") + len + strlen("_queue"), "%s%u%s",
297 "hdf_event", inputDev->devId, "_queue");
298 if (ret < 0) {
299 HDF_LOGE("%s: snprintf_s failed", __func__);
300 return HDF_FAILURE;
301 }
302 if (HdfWorkQueueInit(&inputDev->eventWorkQueue, queueName) != HDF_SUCCESS) {
303 HDF_LOGE("%s: device %s init work queue failed", __func__, inputDev->devName);
304 return HDF_FAILURE;
305 }
306 if (HdfWorkInit(&inputDev->eventWork, EventQueueWorkEntry, inputDev) != HDF_SUCCESS) {
307 HDF_LOGE("%s: create event thread failed", __func__);
308 return HDF_FAILURE;
309 }
310 return HDF_SUCCESS;
311 }
312 #endif // __LITEOS_M__
313
RegisterInputDevice(InputDevice * inputDev)314 int32_t RegisterInputDevice(InputDevice *inputDev)
315 {
316 int32_t ret;
317
318 HDF_LOGI("%s: enter", __func__);
319 if (inputDev == NULL) {
320 HDF_LOGE("%s: inputdev is null", __func__);
321 return HDF_ERR_INVALID_PARAM;
322 }
323
324 if ((g_inputManager == NULL) || (g_inputManager->initialized == false)) {
325 HDF_LOGE("%s: dev manager is null or initialized failed", __func__);
326 return HDF_FAILURE;
327 }
328
329 OsalMutexLock(&g_inputManager->mutex);
330 ret = AllocDeviceID(inputDev);
331 if (ret != HDF_SUCCESS) {
332 goto EXIT;
333 }
334 ret = CreateDeviceNode(inputDev);
335 if (ret != HDF_SUCCESS) {
336 goto EXIT1;
337 }
338
339 ret = AllocPackageBuffer(inputDev);
340 if (ret != HDF_SUCCESS) {
341 goto EXIT1;
342 }
343 #ifndef __LITEOS_M__
344 ret = InitEventWorkQueue(inputDev);
345 if (ret != HDF_SUCCESS) {
346 goto EXIT1;
347 }
348 #endif // __LITEOS_M__
349 AddInputDevice(inputDev);
350 OsalMutexUnlock(&g_inputManager->mutex);
351 HDF_LOGI("%s: exit succ, devCount is %d", __func__, g_inputManager->devCount);
352 return HDF_SUCCESS;
353
354 EXIT1:
355 DeleteDeviceNode(inputDev);
356 EXIT:
357 OsalMutexUnlock(&g_inputManager->mutex);
358 return ret;
359 }
360
UnregisterInputDevice(InputDevice * inputDev)361 void UnregisterInputDevice(InputDevice *inputDev)
362 {
363 int32_t ret;
364 HDF_LOGI("%s: enter", __func__);
365 if (inputDev == NULL) {
366 HDF_LOGE("%s: inputdev is null", __func__);
367 return;
368 }
369
370 if ((g_inputManager == NULL) || (g_inputManager->initialized == false)) {
371 HDF_LOGE("%s: dev manager is null or initialized failed", __func__);
372 return;
373 }
374
375 OsalMutexLock(&g_inputManager->mutex);
376 if (CheckInputDevice(inputDev) == INPUT_DEV_NOT_EXIST) {
377 HDF_LOGE("%s: dev%d not exist", __func__, inputDev->devId);
378 goto EXIT;
379 }
380
381 DeleteDeviceNode(inputDev);
382 HdfSbufRecycle(inputDev->pkgBuf);
383 inputDev->pkgBuf = NULL;
384 ret = DeleteInputDevice(inputDev);
385 if (ret != HDF_SUCCESS) {
386 goto EXIT;
387 }
388 HdfSbufRecycle(inputDev->eventBuf);
389 inputDev->eventBuf = NULL;
390 #ifndef __LITEOS_M__
391 HdfWorkQueueDestroy(&inputDev->eventWorkQueue);
392 HdfWorkDestroy(&inputDev->eventWork);
393 #endif // __LITEOS_M__
394 OsalMemFree(inputDev);
395 inputDev = NULL;
396 OsalMutexUnlock(&g_inputManager->mutex);
397 HDF_LOGI("%s: exit succ, devCount is %d", __func__, g_inputManager->devCount);
398 return;
399
400 EXIT:
401 OsalMutexUnlock(&g_inputManager->mutex);
402 return;
403 }
404
GetDeviceCount(void)405 static uint32_t GetDeviceCount(void)
406 {
407 HDF_LOGI("%s: devCount = %d", __func__, g_inputManager->devCount);
408 return g_inputManager->devCount;
409 }
410
ScanAllDev(struct HdfSBuf * reply)411 static int32_t ScanAllDev(struct HdfSBuf *reply)
412 {
413 DevDesc sta;
414 InputDevice *tmpDev = g_inputManager->inputDevList;
415 while (tmpDev != NULL) {
416 sta.devType = tmpDev->devType;
417 sta.devId = tmpDev->devId;
418
419 if (!HdfSbufWriteBuffer(reply, &sta, sizeof(DevDesc))) {
420 HDF_LOGE("%s: HdfSbufWriteBuffer failed", __func__);
421 return HDF_FAILURE;
422 }
423 tmpDev = tmpDev->next;
424 }
425 HdfSbufWriteBuffer(reply, NULL, 0); // end flag
426 return HDF_SUCCESS;
427 }
428
ScanDevice(struct HdfDeviceIoClient * client,int32_t cmd,struct HdfSBuf * data,struct HdfSBuf * reply)429 static int32_t ScanDevice(struct HdfDeviceIoClient *client, int32_t cmd,
430 struct HdfSBuf *data, struct HdfSBuf *reply)
431 {
432 (void)cmd;
433 int32_t ret;
434 if ((client == NULL) || (data == NULL) || (reply == NULL)) {
435 HDF_LOGE("%s: param is null", __func__);
436 return HDF_FAILURE;
437 }
438 ret = ScanAllDev(reply);
439 if (ret != HDF_SUCCESS) {
440 HDF_LOGE("%s: scan all dev failed", __func__);
441 }
442 return ret;
443 }
444
HdfInputManagerBind(struct HdfDeviceObject * device)445 static int32_t HdfInputManagerBind(struct HdfDeviceObject *device)
446 {
447 if (device == NULL) {
448 HDF_LOGE("%s: device is null", __func__);
449 return HDF_ERR_INVALID_PARAM;
450 }
451
452 static IInputManagerService managerService = {
453 .getDeviceCount = GetDeviceCount,
454 .ioService.Dispatch = ScanDevice,
455 };
456
457 device->service = &managerService.ioService;
458 return HDF_SUCCESS;
459 }
460
InputManagerInstance(void)461 static InputManager *InputManagerInstance(void)
462 {
463 InputManager *manager = (InputManager *)OsalMemAlloc(sizeof(InputManager));
464 if (manager == NULL) {
465 HDF_LOGE("%s: instance input manager failed", __func__);
466 return NULL;
467 }
468 (void)memset_s(manager, sizeof(InputManager), 0, sizeof(InputManager));
469 return manager;
470 }
471
HdfInputManagerInit(struct HdfDeviceObject * device)472 static int32_t HdfInputManagerInit(struct HdfDeviceObject *device)
473 {
474 HDF_LOGI("%s: enter", __func__);
475 if (device == NULL) {
476 HDF_LOGE("%s: device is null", __func__);
477 return HDF_ERR_INVALID_PARAM;
478 }
479
480 g_inputManager = InputManagerInstance();
481 if (g_inputManager == NULL) {
482 return HDF_ERR_MALLOC_FAIL;
483 }
484
485 if (OsalMutexInit(&g_inputManager->mutex) != HDF_SUCCESS) {
486 HDF_LOGE("%s: mutex init failed", __func__);
487 OsalMemFree(g_inputManager);
488 g_inputManager = NULL;
489 return HDF_FAILURE;
490 }
491
492 if (OsalSpinInit(&g_inputManager->lock) != HDF_SUCCESS) {
493 HDF_LOGE("%s: spin lock init failed", __func__);
494 OsalMemFree(g_inputManager);
495 g_inputManager = NULL;
496 return HDF_FAILURE;
497 }
498 g_inputManager->initialized = true;
499 g_inputManager->hdfDevObj = device;
500 HDF_LOGI("%s: exit succ", __func__);
501 return HDF_SUCCESS;
502 }
503
HdfInputManagerRelease(struct HdfDeviceObject * device)504 static void HdfInputManagerRelease(struct HdfDeviceObject *device)
505 {
506 if (device == NULL) {
507 HDF_LOGE("%s: device is null", __func__);
508 return;
509 }
510 if (g_inputManager != NULL) {
511 OsalMutexDestroy(&g_inputManager->mutex);
512 OsalSpinDestroy(&g_inputManager->lock);
513 OsalMemFree(g_inputManager);
514 g_inputManager = NULL;
515 }
516 }
517
518 struct HdfDriverEntry g_hdfInputEntry = {
519 .moduleVersion = 1,
520 .moduleName = "HDF_INPUT_MANAGER",
521 .Bind = HdfInputManagerBind,
522 .Init = HdfInputManagerInit,
523 .Release = HdfInputManagerRelease,
524 };
525
526 HDF_INIT(g_hdfInputEntry);
527