• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #include "input_common.h"
16 #include <hdf_base.h>
17 #include <hdf_log.h>
18 #include <osal_mem.h>
19 #include <hdf_device_desc.h>
20 #include <stdlib.h>
21 #include <securec.h>
22 
23 #define DEV_MANAGER_SERVICE_NAME "hdf_input_host"
24 #define SHELL_LEN                50
25 #define ONLINE                   0
26 
27 static InputDevManager *g_hotPlugManager;
28 static InputHostCb hotPlug;
29 
HotPlugCallback(const HotPlugEvent * msg)30 static void HotPlugCallback(const HotPlugEvent *msg)
31 {
32     int32_t ret;
33     char shell[SHELL_LEN];
34     if (msg == NULL) {
35         HDF_LOGE("msg is null");
36         return;
37     }
38     if (msg->status == ONLINE) {
39         ret = sprintf_s(shell, SHELL_LEN, "chown system:system /dev/hdf_input_event%d", msg->devIndex);
40         if (ret < 0) {
41             HDF_LOGE("%s: sprintf shell cmd failed", __func__);
42             return;
43         }
44         system(shell);
45     }
46 }
47 
HotPlugEventListenerCallback(struct HdfDevEventlistener * listener,struct HdfIoService * service,uint32_t id,struct HdfSBuf * data)48 static int32_t HotPlugEventListenerCallback(struct HdfDevEventlistener *listener,
49     struct HdfIoService *service, uint32_t id, struct HdfSBuf *data)
50 {
51     (void)listener;
52     (void)id;
53     uint32_t len = 0;
54     HotPlugEvent *event = NULL;
55     bool ret = false;
56 
57     if (service == NULL || data == NULL) {
58         HDF_LOGE("%s: invalid param", __func__);
59         return INPUT_INVALID_PARAM;
60     }
61 
62     ret = HdfSbufReadBuffer(data, (const void **)&event, &len);
63     if (!ret) {
64         HDF_LOGE("%s: read sbuf failed", __func__);
65         return INPUT_FAILURE;
66     }
67     g_hotPlugManager->hostDev.hostCb->HotPlugCallback((const HotPlugEvent *)event);
68 
69     return INPUT_SUCCESS;
70 }
71 
HotPlugEventListenerInstance(void)72 static struct HdfDevEventlistener *HotPlugEventListenerInstance(void)
73 {
74     int32_t ret;
75     struct HdfDevEventlistener *listener = (struct HdfDevEventlistener *)malloc(sizeof(struct HdfDevEventlistener));
76     if (listener == NULL) {
77         HDF_LOGE("%s: instance listener failed", __func__);
78         return NULL;
79     }
80 
81     ret = memset_s(listener, sizeof(struct HdfDevEventlistener), 0, sizeof(struct HdfDevEventlistener));
82     if (ret != 0) {
83         HDF_LOGE("%s: memset failed, ret = %d", __func__, ret);
84         free(listener);
85         listener = NULL;
86         return NULL;
87     }
88     listener->onReceive = HotPlugEventListenerCallback;
89     return listener;
90 }
91 
RegisterHotPlugCallback(InputHostCb * callback)92 static int32_t RegisterHotPlugCallback(InputHostCb *callback)
93 {
94     int32_t ret;
95     if ((callback == NULL) || (callback->HotPlugCallback == NULL)) {
96         HDF_LOGE("%s: invalid param", __func__);
97         return INPUT_INVALID_PARAM;
98     }
99 
100     g_hotPlugManager = (InputDevManager *)malloc(sizeof(InputDevManager));
101     if (g_hotPlugManager == NULL) {
102         HDF_LOGE("%s: malloc fail", __func__);
103         return INPUT_NOMEM;
104     }
105 
106     ret = memset_s(g_hotPlugManager, sizeof(InputDevManager), 0, sizeof(InputDevManager));
107     if (ret != 0) {
108         HDF_LOGE("%s: memset failed, ret = %d", __func__, ret);
109         goto EXIT;
110     }
111 
112     g_hotPlugManager->hostDev.service = HdfIoServiceBind(DEV_MANAGER_SERVICE_NAME);
113     if (g_hotPlugManager->hostDev.service == NULL) {
114         HDF_LOGE("%s: bind service failed", __func__);
115         goto EXIT;
116     }
117 
118     struct HdfDevEventlistener *listener = HotPlugEventListenerInstance();
119     if (listener == NULL) {
120         HDF_LOGE("%s: fail to instance listener", __func__);
121         goto EXIT;
122     }
123     if (HdfDeviceRegisterEventListener(g_hotPlugManager->hostDev.service, listener) != INPUT_SUCCESS) {
124         HDF_LOGE("%s: fail to register listener", __func__);
125         free(listener);
126         listener = NULL;
127         goto EXIT;
128     }
129     g_hotPlugManager->hostDev.hostCb = callback;
130     g_hotPlugManager->hostDev.listener = listener;
131     return INPUT_SUCCESS;
132 EXIT:
133     free(g_hotPlugManager);
134     g_hotPlugManager = NULL;
135     return INPUT_FAILURE;
136 }
137 
138 
HdfHotPlugDriverRelease(struct HdfDeviceObject * deviceObject)139 static void HdfHotPlugDriverRelease(struct HdfDeviceObject *deviceObject)
140 {
141     (void)deviceObject;
142     if (g_hotPlugManager == NULL) {
143         return;
144     }
145     if (g_hotPlugManager->hostDev.listener != NULL) {
146         free(g_hotPlugManager->hostDev.listener);
147         g_hotPlugManager->hostDev.listener = NULL;
148     }
149     if (g_hotPlugManager != NULL) {
150         free(g_hotPlugManager);
151         g_hotPlugManager = NULL;
152     }
153 }
154 
HdfHotPlugDriverBind(struct HdfDeviceObject * deviceObject)155 static int HdfHotPlugDriverBind(struct HdfDeviceObject *deviceObject)
156 {
157     (void)deviceObject;
158     return HDF_SUCCESS;
159 }
160 
HdfHotPlugDriverInit(struct HdfDeviceObject * deviceObject)161 static int HdfHotPlugDriverInit(struct HdfDeviceObject *deviceObject)
162 {
163     (void)deviceObject;
164     int32_t ret;
165 
166     hotPlug.HotPlugCallback = HotPlugCallback;
167     ret = RegisterHotPlugCallback(&hotPlug);
168     if (ret != HDF_SUCCESS) {
169         HDF_LOGE("%s: register hot plug callback failed, ret = %d", __func__, ret);
170         return HDF_FAILURE;
171     }
172 
173     return HDF_SUCCESS;
174 }
175 
176 struct HdfDriverEntry g_inputuserHostDriverEntry = {
177     .moduleVersion = 1,
178     .moduleName = "libhdf_input_hotplug.z.so",
179     .Bind = HdfHotPlugDriverBind,
180     .Init = HdfHotPlugDriverInit,
181     .Release = HdfHotPlugDriverRelease,
182 };
183 
184 HDF_INIT(g_inputuserHostDriverEntry);