• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 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 
16 #include "input_device_manager.h"
17 #include <algorithm>
18 #include <cstdio>
19 #include <cstdlib>
20 #include <cstring>
21 #include <dirent.h>
22 #include <fcntl.h>
23 #include <fstream>
24 #include <functional>
25 #include <future>
26 #include <iostream>
27 #include <memory>
28 #include <sstream>
29 #include <sys/epoll.h>
30 #include <sys/inotify.h>
31 #include <sys/ioctl.h>
32 #include <unistd.h>
33 #include <vector>
34 #include "input_uhdf_log.h"
35 #include "osal_mem.h"
36 #include "securec.h"
37 
38 #define HDF_LOG_TAG InputDeviceHdiManager
39 
40 namespace OHOS {
41 namespace Input {
42 using namespace std;
43 constexpr uint32_t DEV_INDEX_MAX = 32;
44 constexpr uint32_t RELOAD_INTERVAL_MAX = 800;
45 const int32_t INVALID_ID = -1;
46 const int32_t MEMCPY_ERROR = -1;
47 const int32_t CREATE_SUCCESS = 1;
48 const int32_t CREATE_ERROR = 0;
Init()49 void InputDeviceManager::Init()
50 {
51     inputDevList_.clear();
52     reportEventPkgCallBackLock_.lock();
53     reportEventPkgCallback_.clear();
54     reportEventPkgCallBackLock_.unlock();
55     std::vector<std::string> flist = GetFiles(devPath_);
56     LoadInputDevices(flist);
57     std::thread reloadThread(&InputDeviceManager::ReloadInputDevices, this, flist);
58     reloadThread.detach();
59     std::thread t1([this] {this->WorkerThread();});
60     std::string wholeName1 = std::to_string(getpid()) + "_" + std::to_string(gettid());
61     thread_ = std::move(t1);
62     thread_.detach();
63     for (auto &inputDev : inputDevList_) {
64         dumpInfoList(inputDev.second);
65     }
66 }
67 
FreeEventPkgs(InputEventPackage ** eventPkgs,size_t count)68 static void FreeEventPkgs(InputEventPackage **eventPkgs, size_t count)
69 {
70     for (size_t i = 0; i < count; i++) {
71         if (eventPkgs[i] != NULL) {
72             OsalMemFree(eventPkgs[i]);
73             eventPkgs[i] = nullptr;
74         }
75     }
76     return;
77 }
78 
79 // get the nodefile list
GetFiles(string path)80 vector<string> InputDeviceManager::GetFiles(string path)
81 {
82     vector<string> fileList;
83     struct dirent *dEnt = nullptr;
84 
85     DIR *dir = opendir(path.c_str());
86     if (dir == nullptr) {
87         HDF_LOGE("%{public}s: no files", __func__);
88         return fileList;
89     }
90     string sDot = ".";
91     string sDotDot = "..";
92     while ((dEnt = readdir(dir)) != nullptr) {
93         if ((string(dEnt->d_name) != sDot) &&
94             (string(dEnt->d_name) != sDotDot)) {
95             if (dEnt->d_type != DT_DIR) {
96                 string d_name(dEnt->d_name);
97                 fileList.push_back(string(dEnt->d_name));
98             }
99         }
100     }
101     // sort the returned files
102     sort(fileList.begin(), fileList.end());
103     closedir(dir);
104     return fileList;
105 }
106 
ReportEventPkg(int32_t iFd,InputEventPackage ** iEvtPkg,size_t iCount)107 void InputDeviceManager::ReportEventPkg(int32_t iFd, InputEventPackage **iEvtPkg, size_t iCount)
108 {
109     HDF_LOGI("%{public}s start", __func__);
110     if (iEvtPkg == nullptr) {
111         HDF_LOGE("%{public}s: param invalid, line: %{public}d", __func__, __LINE__);
112         return;
113     }
114     std::lock_guard<std::mutex> guard(reportEventPkgCallBackLock_);
115     for (auto &callbackFunc : reportEventPkgCallback_) {
116         uint32_t index {0};
117         auto ret = FindIndexFromFd(iFd, &index);
118         if (callbackFunc.second != nullptr && ret != INPUT_FAILURE) {
119             callbackFunc.second->EventPkgCallback(const_cast<const InputEventPackage **>(iEvtPkg), iCount, index);
120         }
121     }
122     return;
123 }
124 
CheckReadResult(int32_t readResult)125 int32_t CheckReadResult(int32_t readResult)
126 {
127     if (readResult == 0 || (readResult < 0 && errno == ENODEV)) {
128         return INPUT_FAILURE;
129     }
130     if (readResult < 0) {
131         if (errno != EAGAIN && errno != EINTR) {
132             HDF_LOGE("%{public}s: could not get event (errno = %{public}d)", __func__, errno);
133         }
134         return INPUT_FAILURE;
135     }
136     if ((readResult % sizeof(struct input_event)) != 0) {
137         HDF_LOGE("%{public}s: could not get one event size %{public}lu readResult size: %{public}d", __func__,
138             sizeof(struct input_event), readResult);
139         return INPUT_FAILURE;
140     }
141     return INPUT_SUCCESS;
142 }
143 
144 // read action
DoRead(int32_t fd,struct input_event * event,size_t size)145 void InputDeviceManager::DoRead(int32_t fd, struct input_event *event, size_t size)
146 {
147     HDF_LOGI("%{public}s start", __func__);
148     int32_t readLen = read(fd, event, sizeof(struct input_event) * size);
149     if (CheckReadResult(readLen) == INPUT_FAILURE) {
150         return;
151     }
152     size_t count = size_t(readLen) / sizeof(struct input_event);
153     InputEventPackage **evtPkg = (InputEventPackage **)OsalMemAlloc(sizeof(InputEventPackage *) * count);
154     if (evtPkg == nullptr) {
155         HDF_LOGE("%{public}s: OsalMemAlloc failed, line: %{public}d", __func__, __LINE__);
156         return;
157     }
158     for (size_t i = 0; i < count; i++) {
159         struct input_event &iEvent = event[i];
160         // device action events happened
161         *(evtPkg + i) = (InputEventPackage *)OsalMemAlloc(sizeof(InputEventPackage));
162         if (evtPkg[i] == nullptr) {
163             HDF_LOGE("%{public}s: OsalMemAlloc failed, line: %{public}d", __func__, __LINE__);
164             FreeEventPkgs(evtPkg, i);
165             OsalMemFree(evtPkg);
166             evtPkg = nullptr;
167             return;
168         }
169         evtPkg[i]->type = iEvent.type;
170         evtPkg[i]->code = iEvent.code;
171         evtPkg[i]->value = iEvent.value;
172         evtPkg[i]->timestamp = (uint64_t)iEvent.time.tv_sec * MS_THOUSAND * MS_THOUSAND +
173                                (uint64_t)iEvent.time.tv_usec;
174     }
175     ReportEventPkg(fd, evtPkg, count);
176     for (size_t i = 0; i < count; i++) {
177         OsalMemFree(evtPkg[i]);
178         evtPkg[i] = nullptr;
179     }
180     OsalMemFree(evtPkg);
181     evtPkg = nullptr;
182 }
183 
184 // open input device node
OpenInputDevice(string devPath)185 int32_t InputDeviceManager::OpenInputDevice(string devPath)
186 {
187     char devRealPath[PATH_MAX + 1] = { '\0' };
188     if (realpath(devPath.c_str(), devRealPath) == nullptr) {
189         HDF_LOGE("%{public}s: The absolute path does not exist.", __func__);
190         return INPUT_FAILURE;
191     }
192 
193     int32_t nodeFd = open(devRealPath, O_RDWR | O_CLOEXEC | O_NONBLOCK);
194     if (nodeFd < 0) {
195         HDF_LOGE("%{public}s: could not open %{public}s, %{public}d %{public}s", __func__,
196             devRealPath, errno, strerror(errno));
197         return INPUT_FAILURE;
198     }
199     return nodeFd;
200 }
201 
202 // close input device node
CloseInputDevice(string devPath)203 RetStatus InputDeviceManager::CloseInputDevice(string devPath)
204 {
205     for (auto &inputDev : inputDevList_) {
206         if (string(inputDev.second.devPathNode) == devPath) {
207             int32_t fd = inputDev.second.fd;
208             if (fd > 0) {
209                 RemoveEpoll(mEpollId_, fd);
210                 close(fd);
211                 inputDev.second.fd = -1;
212                 inputDev.second.status = INPUT_DEVICE_STATUS_CLOSED;
213                 return INPUT_SUCCESS;
214             }
215         }
216     }
217     // device list remove this node
218     return INPUT_FAILURE;
219 }
220 
GetInputDeviceInfo(int32_t fd,InputDeviceInfo * detailInfo)221 int32_t InputDeviceManager::GetInputDeviceInfo(int32_t fd, InputDeviceInfo *detailInfo)
222 {
223     char buffer[DEVICE_INFO_SIZE] {};
224     struct input_id inputId {};
225     // get the abilitys.
226     (void)ioctl(fd, EVIOCGBIT(EV_KEY, sizeof(detailInfo->abilitySet.keyCode)), &detailInfo->abilitySet.keyCode);
227     (void)ioctl(fd, EVIOCGBIT(EV_REL, sizeof(detailInfo->abilitySet.relCode)), &detailInfo->abilitySet.relCode);
228     (void)ioctl(fd, EVIOCGBIT(EV_ABS, sizeof(detailInfo->abilitySet.absCode)), &detailInfo->abilitySet.absCode);
229     (void)ioctl(fd, EVIOCGBIT(EV_MSC, sizeof(detailInfo->abilitySet.miscCode)), &detailInfo->abilitySet.miscCode);
230     (void)ioctl(fd, EVIOCGBIT(EV_SW, sizeof(detailInfo->abilitySet.switchCode)), &detailInfo->abilitySet.switchCode);
231     (void)ioctl(fd, EVIOCGBIT(EV_LED, sizeof(detailInfo->abilitySet.ledType)), &detailInfo->abilitySet.ledType);
232     (void)ioctl(fd, EVIOCGBIT(EV_SND, sizeof(detailInfo->abilitySet.soundCode)), &detailInfo->abilitySet.soundCode);
233     (void)ioctl(fd, EVIOCGBIT(EV_FF, sizeof(detailInfo->abilitySet.forceCode)), &detailInfo->abilitySet.forceCode);
234     // device name.
235     if (ioctl(fd, EVIOCGNAME(sizeof(buffer) - 1), &buffer) < 1) {
236         HDF_LOGE("%{public}s: get device name failed errormsg %{public}s", __func__, strerror(errno));
237     } else {
238         buffer[sizeof(buffer) - 1] = '\0';
239         int32_t ret = strcpy_s(detailInfo->attrSet.devName, DEV_NAME_LEN, buffer);
240         if (ret) {
241             HDF_LOGE("%{public}s: strcpy_s failed, ret %{public}d", __func__, ret);
242             return INPUT_FAILURE;
243         }
244     }
245     // device detailInfo.
246     if (ioctl(fd, EVIOCGID, &inputId)) {
247         HDF_LOGE("%{public}s: get device input id errormsg %{public}s", __func__, strerror(errno));
248     }
249     detailInfo->attrSet.id.busType = inputId.bustype;
250     detailInfo->attrSet.id.product = inputId.product;
251     detailInfo->attrSet.id.vendor = inputId.vendor;
252     detailInfo->attrSet.id.version = inputId.version;
253     // ABS Info
254     for (uint32_t i = 0; i < BITS_TO_UINT64(ABS_CNT); i++) {
255         if (detailInfo->abilitySet.absCode[i] > 0) {
256             if (ioctl(fd, EVIOCGABS(i), &detailInfo->attrSet.axisInfo[i])) {
257                 HDF_LOGE("%{public}s: get axis info failed fd = %{public}d name = %{public}s errormsg = %{public}s",
258                          __func__, fd, detailInfo->attrSet.devName, strerror(errno));
259                 continue;
260             }
261         }
262     }
263     return INPUT_SUCCESS;
264 }
265 
GetInputDeviceTypeInfo(const string & devName)266 uint32_t GetInputDeviceTypeInfo(const string &devName)
267 {
268     uint32_t type {INDEV_TYPE_UNKNOWN};
269     if (devName.find("input_mt_wrapper") != std::string::npos) {
270         type = INDEV_TYPE_TOUCH;
271     } else if ((devName.find("Keyboard") != std::string::npos) &&
272                (devName.find("Headset") == std::string::npos)) {
273         type = INDEV_TYPE_KEYBOARD;
274     } else if (devName.find("Mouse") != std::string::npos) {
275         type = INDEV_TYPE_MOUSE;
276     } else if ((devName.find("_gpio_key") != std::string::npos) ||
277                (devName.find("ponkey_on") != std::string::npos)) {
278         type = INDEV_TYPE_KEY;
279     } else if (devName.find("Touchpad") != std::string::npos) {
280         type = INDEV_TYPE_TOUCHPAD;
281     }
282     return type;
283 }
284 
GetCurDevIndex()285 int32_t InputDeviceManager::GetCurDevIndex()
286 {
287     if (inputDevList_.size() >= DEV_INDEX_MAX) {
288         HDF_LOGE("%{public}s: The number of devices has reached max_num", __func__);
289         return INVALID_ID;
290     }
291     if (inputDevList_.count(devIndex_) == 0) {
292         return static_cast<int32_t>(devIndex_);
293     }
294     uint32_t newId = inputDevList_.size();
295     while (inputDevList_.count(newId) != 0) {
296         newId++;
297     }
298     return static_cast<int32_t>(newId);
299 }
300 
CreateInputDevListNode(InputDevListNode & inputDevNode,std::string & fileName)301 int32_t InputDeviceManager::CreateInputDevListNode(InputDevListNode &inputDevNode, std::string &fileName)
302 {
303     std::string devPathNode = devPath_ + "/" + fileName;
304     std::string::size_type n = devPathNode.find("event");
305     if (n == std::string::npos) {
306         HDF_LOGE("%{public}s: not found event node", __func__);
307         return CREATE_ERROR;
308     }
309     auto fd = OpenInputDevice(devPathNode);
310     if (fd < 0) {
311         HDF_LOGE("%{public}s: open node failed", __func__);
312         return CREATE_ERROR;
313     }
314     std::shared_ptr<InputDeviceInfo> detailInfo = std::make_shared<InputDeviceInfo>();
315     (void)memset_s(detailInfo.get(), sizeof(InputDeviceInfo), 0, sizeof(InputDeviceInfo));
316     (void)memset_s(&inputDevNode, sizeof(inputDevNode), 0, sizeof(inputDevNode));
317     (void)GetInputDeviceInfo(fd, detailInfo.get());
318     auto sDevName = string(detailInfo->attrSet.devName);
319     uint32_t type = GetInputDeviceTypeInfo(sDevName);
320     if (type == INDEV_TYPE_UNKNOWN) {
321         close(fd);
322         HDF_LOGE("%{public}s: input device type unknow: %{public}d", __func__, type);
323         return CREATE_ERROR;
324     }
325     inputDevNode.index = devIndex_;
326     inputDevNode.status = INPUT_DEVICE_STATUS_OPENED;
327     inputDevNode.fd = fd;
328     detailInfo->devIndex = devIndex_;
329     detailInfo->devType = type;
330     if (memcpy_s(&inputDevNode.devPathNode, devPathNode.length(),
331         devPathNode.c_str(), devPathNode.length()) != EOK ||
332         memcpy_s(&inputDevNode.detailInfo, sizeof(InputDeviceInfo), detailInfo.get(),
333         sizeof(InputDeviceInfo)) != EOK) {
334         close(fd);
335         HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
336         return MEMCPY_ERROR;
337     }
338     return CREATE_SUCCESS;
339 }
340 
LoadInputDevices(std::vector<std::string> & flist)341 void InputDeviceManager::LoadInputDevices(std::vector<std::string> &flist)
342 {
343     inputDevList_.clear();
344     InputDevListNode inputDevNode {};
345 
346     for (unsigned i = 0; i < flist.size(); i++) {
347         int32_t curDevIndex = GetCurDevIndex();
348         if (curDevIndex == INVALID_ID) {
349             return;
350         }
351         devIndex_ = static_cast<uint32_t>(curDevIndex);
352         int32_t ret = CreateInputDevListNode(inputDevNode, flist[i]);
353         if (ret == MEMCPY_ERROR) {
354             return;
355         }
356         if (ret == CREATE_SUCCESS) {
357             inputDevList_.insert_or_assign(devIndex_, inputDevNode);
358             devIndex_ += 1;
359         }
360     }
361 }
362 
ReloadInputDevices(std::vector<std::string> flist)363 void InputDeviceManager::ReloadInputDevices(std::vector<std::string> flist)
364 {
365     // 线程等待,保证input节点创建完成
366     std::this_thread::sleep_for(std::chrono::milliseconds(RELOAD_INTERVAL_MAX));
367     std::vector<std::string> curFileList = GetFiles(devPath_);
368     // 当前节点与首次加载数量不一致,需加载新的节点
369     if (curFileList.size() <= flist.size()) {
370         return;
371     }
372     InputDevListNode inputDevNode {};
373     for (unsigned i = 0; i < curFileList.size(); i++) {
374         if (std::find(flist.begin(), flist.end(), curFileList[i]) != flist.end()) {
375             continue;
376         }
377         int32_t curDevIndex = GetCurDevIndex();
378         if (curDevIndex == INVALID_ID) {
379             return;
380         }
381         devIndex_ = static_cast<uint32_t>(curDevIndex);
382         int32_t ret = CreateInputDevListNode(inputDevNode, flist[i]);
383         if (ret == MEMCPY_ERROR) {
384             return;
385         }
386         if (ret == CREATE_SUCCESS) {
387             inputDevList_.insert_or_assign(devIndex_, inputDevNode);
388             devIndex_ += 1;
389         }
390     }
391 }
392 
DoInputDeviceAction(void)393 int32_t InputDeviceManager::DoInputDeviceAction(void)
394 {
395     struct input_event evtBuffer[EVENT_BUFFER_SIZE] {};
396     int32_t result = 0;
397 
398     mEpollId_ = epoll_create1(EPOLL_CLOEXEC);
399     if (mEpollId_ == INPUT_FAILURE) {
400         HDF_LOGE("%{public}s: epoll create failed", __func__);
401         return mEpollId_;
402     }
403     mInotifyId_ = inotify_init();
404     result = inotify_add_watch(mInotifyId_, devPath_.c_str(), IN_DELETE | IN_CREATE);
405     if (result == INPUT_FAILURE) {
406         HDF_LOGE("%{public}s: add file watch failed", __func__);
407         return result;
408     }
409     AddToEpoll(mEpollId_, mInotifyId_);
410     while (true) {
411         result = epoll_wait(mEpollId_, epollEventList_, EPOLL_MAX_EVENTS, EPOLL_WAIT_TIMEOUT);
412         if (result <= 0) {
413             continue;
414         }
415         for (int32_t i = 0; i < result; i++) {
416             if (epollEventList_[i].data.fd != mInotifyId_) {
417                 DoRead(epollEventList_[i].data.fd, evtBuffer, EVENT_BUFFER_SIZE);
418                 continue;
419             }
420             if (INPUT_FAILURE == InotifyEventHandler(mEpollId_, mInotifyId_)) {
421                 HDF_LOGE("%{public}s: inotify handler failed", __func__);
422                 return INPUT_FAILURE;
423             }
424         }
425     }
426     return INPUT_SUCCESS;
427 }
428 
DeleteDevListNode(int index)429 void InputDeviceManager::DeleteDevListNode(int index)
430 {
431     for (auto it = inputDevList_.begin(); it != inputDevList_.end();) {
432         if (it->first == (uint32_t)index) {
433             it = inputDevList_.erase(it);
434             if (devIndex_ < 1 || devIndex_ > DEV_INDEX_MAX) {
435                 return;
436             }
437             devIndex_ = it->first;
438         } else {
439             ++it;
440         }
441     }
442     return;
443 }
444 
AddDeviceNodeToList(int32_t & epollFd,int32_t & fd,string devPath,std::shared_ptr<InputDeviceInfo> & detailInfo)445 int32_t InputDeviceManager::AddDeviceNodeToList(
446     int32_t &epollFd, int32_t &fd, string devPath, std::shared_ptr<InputDeviceInfo> &detailInfo)
447 {
448     if (epollFd < 0 || fd < 0) {
449         HDF_LOGE("%{public}s: param invalid, %{public}d", __func__, __LINE__);
450         return INPUT_FAILURE;
451     }
452     int32_t curDevIndex = GetCurDevIndex();
453     if (curDevIndex == INVALID_ID) {
454         HDF_LOGE("%{public}s: input device exceeds the maximum limit, %{public}d", __func__, __LINE__);
455         return INPUT_FAILURE;
456     }
457     devIndex_ = static_cast<uint32_t>(curDevIndex);
458     InputDevListNode inputDevList {};
459     inputDevList.index = devIndex_;
460     inputDevList.status = INPUT_DEVICE_STATUS_OPENED;
461     inputDevList.fd = fd;
462     detailInfo->devIndex = devIndex_;
463     if (memcpy_s(inputDevList.devPathNode, devPath.length(), devPath.c_str(), devPath.length()) != EOK ||
464         memcpy_s(&inputDevList.detailInfo, sizeof(InputDeviceInfo), detailInfo.get(),
465         sizeof(InputDeviceInfo)) != EOK) {
466         HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
467         return INPUT_FAILURE;
468     }
469     inputDevList_.insert_or_assign(devIndex_, inputDevList);
470     if (AddToEpoll(epollFd, inputDevList.fd) != INPUT_SUCCESS) {
471         HDF_LOGE("%{public}s: add to epoll failed, line: %{public}d", __func__, __LINE__);
472         DeleteDevListNode(devIndex_);
473         return INPUT_FAILURE;
474     }
475     devIndex_ += 1;
476     return INPUT_SUCCESS;
477 }
478 
DoWithEventDeviceAdd(int32_t & epollFd,int32_t & fd,string devPath)479 void InputDeviceManager::DoWithEventDeviceAdd(int32_t &epollFd, int32_t &fd, string devPath)
480 {
481     bool findDeviceFlag = false;
482     uint32_t type {};
483     uint32_t index {};
484     uint32_t status {};
485 
486     std::shared_ptr<InputDeviceInfo> detailInfo = std::make_shared<InputDeviceInfo>();
487     (void)memset_s(detailInfo.get(), sizeof(InputDeviceInfo), 0, sizeof(InputDeviceInfo));
488     (void)GetInputDeviceInfo(fd, detailInfo.get());
489     auto sDevName = string(detailInfo->attrSet.devName);
490     for (auto it = inputDevList_.begin(); it != inputDevList_.end();) {
491         if (string(it->second.devPathNode) == devPath && string(it->second.detailInfo.attrSet.devName) == sDevName) {
492             it->second.fd = fd;
493             it->second.status = INPUT_DEVICE_STATUS_OPENED;
494             findDeviceFlag = true;
495             index = it->first;
496             break;
497         } else {
498             ++it;
499         }
500     }
501     if (sDevName.find("Keyboard") != std::string::npos) {
502         detailInfo->devType = INDEV_TYPE_KEYBOARD;
503     }
504     if (sDevName.find("Mouse") != std::string::npos) {
505         detailInfo->devType = INDEV_TYPE_MOUSE;
506     }
507     type = detailInfo->devType;
508     if (!findDeviceFlag) {
509         if (AddDeviceNodeToList(epollFd, fd, devPath, detailInfo) != INPUT_SUCCESS) {
510             HDF_LOGE("%{public}s: add device node failed, line: %{public}d", __func__, __LINE__);
511             return;
512         }
513     }
514     status = INPUT_DEVICE_STATUS_OPENED;
515     HDF_LOGI("%{public}s end", __func__);
516     SendHotPlugEvent(type, index, status);
517 }
518 
SendHotPlugEvent(uint32_t & type,uint32_t & index,uint32_t status)519 void InputDeviceManager::SendHotPlugEvent(uint32_t &type, uint32_t &index, uint32_t status)
520 {
521     HDF_LOGI("%{public}s start", __func__);
522     // hot plug evnets happened
523     InputHotPlugEvent *evtPlusPkg = (InputHotPlugEvent *)OsalMemAlloc(sizeof(InputHotPlugEvent));
524     if (evtPlusPkg == nullptr) {
525         HDF_LOGE("%{public}s: OsalMemAlloc failed", __func__);
526         return;
527     }
528 
529     evtPlusPkg->devType = type;
530     evtPlusPkg->devIndex = index;
531     evtPlusPkg->status = status;
532 
533     if (reportHotPlugEventCallback_ != nullptr) {
534         HDF_LOGD("devType: %{public}u devIndex: %{public}u status: %{public}u", type, index, status);
535         reportHotPlugEventCallback_->HotPlugCallback(evtPlusPkg);
536     }
537 
538     OsalMemFree(evtPlusPkg);
539     evtPlusPkg = nullptr;
540 }
541 
DoWithEventDeviceDel(int32_t & epollFd,uint32_t & index)542 void InputDeviceManager::DoWithEventDeviceDel(int32_t &epollFd, uint32_t &index)
543 {
544     uint32_t type {};
545     uint32_t devIndex {};
546     uint32_t status {};
547 
548     // hot plug evnets happened
549     auto sDevName = string(inputDevList_[index].detailInfo.attrSet.devName);
550     if (sDevName.find("Keyboard") != std::string::npos) {
551         type = INDEV_TYPE_KEYBOARD;
552     }
553     if (sDevName.find("Mouse") != std::string::npos) {
554         type = INDEV_TYPE_MOUSE;
555     }
556     auto ret = FindIndexFromDevName(sDevName, &devIndex);
557     if (ret != INPUT_SUCCESS) {
558         SendHotPlugEvent(type, devIndex_, status);
559         HDF_LOGE("%{public}s: no found device maybe it has been removed", __func__);
560         return;
561     }
562     status = INPUT_DEVICE_STATUS_CLOSED;
563     SendHotPlugEvent(type, devIndex, status);
564     CloseInputDevice(inputDevList_[index].devPathNode);
565     DeleteDevListNode(index);
566     HDF_LOGI("%{public}s: end", __func__);
567 }
568 
InotifyEventHandler(int32_t epollFd,int32_t notifyFd)569 int32_t InputDeviceManager::InotifyEventHandler(int32_t epollFd, int32_t notifyFd)
570 {
571     char InfoBuf[BUFFER_SIZE];
572     struct inotify_event *event {};
573     char nodeRealPath[PATH_MAX + 1] = { '\0' };
574     char *p {};
575     int32_t tmpFd {};
576 
577     (void)memset_s(InfoBuf, BUFFER_SIZE, 0, BUFFER_SIZE);
578     int32_t result = read(notifyFd, InfoBuf, BUFFER_SIZE);
579     for (p = InfoBuf; p < InfoBuf + result;) {
580         event = (struct inotify_event *)(p);
581         auto nodePath = devPath_ + "/" + string(event->name);
582         if (event->mask & IN_CREATE) {
583             if (realpath(nodePath.c_str(), nodeRealPath) == nullptr) {
584                 HDF_LOGE("%{public}s: The absolute path does not exist.", __func__);
585                 return INPUT_FAILURE;
586             }
587             tmpFd = open(nodeRealPath, O_RDWR);
588             if (tmpFd == INPUT_FAILURE) {
589                 HDF_LOGE("%{public}s: open file failure: %{public}s", __func__, nodeRealPath);
590                 return INPUT_FAILURE;
591             }
592             if (nodePath.find("event") == std::string::npos) {
593                 break;
594             }
595             DoWithEventDeviceAdd(epollFd, tmpFd, nodePath);
596         } else if (event->mask & IN_DELETE) {
597             for (auto &inputDev : inputDevList_) {
598                 if (!strcmp(inputDev.second.devPathNode, nodePath.c_str())) {
599                     DoWithEventDeviceDel(epollFd, inputDev.second.index);
600                     break;
601                 }
602             }
603         } else {
604             // do nothing
605             HDF_LOGI("%{public}s: others actions has done", __func__);
606         }
607         p += sizeof(struct inotify_event) + event->len;
608     }
609     return 0;
610 }
611 
AddToEpoll(int32_t epollFd,int32_t fileFd)612 int32_t InputDeviceManager::AddToEpoll(int32_t epollFd, int32_t fileFd)
613 {
614     int32_t result {0};
615     struct epoll_event eventItem {};
616 
617     (void)memset_s(&eventItem, sizeof(eventItem), 0, sizeof(eventItem));
618     eventItem.events = EPOLLIN;
619     eventItem.data.fd = fileFd;
620     result = epoll_ctl(epollFd, EPOLL_CTL_ADD, fileFd, &eventItem);
621     return result;
622 }
RemoveEpoll(int32_t epollFd,int32_t fileFd)623 void InputDeviceManager::RemoveEpoll(int32_t epollFd, int32_t fileFd)
624 {
625     epoll_ctl(epollFd, EPOLL_CTL_DEL, fileFd, nullptr);
626 }
627 
FindIndexFromFd(int32_t & fd,uint32_t * index)628 int32_t InputDeviceManager::FindIndexFromFd(int32_t &fd, uint32_t *index)
629 {
630     std::lock_guard<std::mutex> guard(lock_);
631     for (const auto &inputDev : inputDevList_) {
632         if (fd == inputDev.second.fd) {
633             *index = inputDev.first;
634             return INPUT_SUCCESS;
635         }
636     }
637     return INPUT_FAILURE;
638 }
639 
FindIndexFromDevName(string devName,uint32_t * index)640 int32_t InputDeviceManager::FindIndexFromDevName(string devName, uint32_t *index)
641 {
642     std::lock_guard<std::mutex> guard(lock_);
643     for (const auto &inputDev : inputDevList_) {
644         if (!strcmp(devName.c_str(), inputDev.second.detailInfo.attrSet.devName)) {
645             *index =  inputDev.first;
646             return INPUT_SUCCESS;
647         }
648     }
649     return INPUT_FAILURE;
650 }
651 
652 // InputManager
ScanDevice(InputDevDesc * staArr,uint32_t arrLen)653 RetStatus InputDeviceManager::ScanDevice(InputDevDesc *staArr, uint32_t arrLen)
654 {
655     if (staArr == nullptr) {
656         HDF_LOGE("%{public}s: param is null", __func__);
657         return INPUT_NULL_PTR;
658     }
659 
660     auto scanCount = (arrLen >= inputDevList_.size() ? inputDevList_.size() : arrLen);
661     if (inputDevList_.size() == 0) {
662         HDF_LOGE("%{public}s: inputDevList_.size is 0", __func__);
663         return INPUT_FAILURE;
664     }
665 
666     for (size_t i = 0; i <= scanCount; i++) {
667         (staArr + i)->devIndex = inputDevList_[i].index;
668         (staArr + i)->devType = inputDevList_[i].detailInfo.devType;
669     }
670 
671     return INPUT_SUCCESS;
672 }
673 
OpenDevice(uint32_t deviceIndex)674 RetStatus InputDeviceManager::OpenDevice(uint32_t deviceIndex)
675 {
676     std::lock_guard<std::mutex> guard(lock_);
677     auto ret = INPUT_FAILURE;
678 
679     if (deviceIndex >= inputDevList_.size()) {
680         HDF_LOGE("%{public}s: param is wrong", __func__);
681         return ret;
682     }
683     auto searchIndex = inputDevList_.find(deviceIndex);
684     if (searchIndex != inputDevList_.end()) {
685         if (searchIndex->second.status != INPUT_DEVICE_STATUS_OPENED) {
686             auto openRet = OpenInputDevice(searchIndex->second.devPathNode);
687             if (openRet > 0) {
688                 AddToEpoll(mEpollId_, openRet);
689                 ret = INPUT_SUCCESS;
690             } else {
691                 HDF_LOGE("%{public}s: open error: %{public}d errormsg: %{public}s",
692                          __func__, openRet, strerror(errno));
693                 return ret;
694             }
695             searchIndex->second.fd = openRet;
696         } else {
697             HDF_LOGD("%{public}s: open devPathNoth: %{public}s fd: %{public}d",
698                      __func__, searchIndex->second.devPathNode, searchIndex->second.fd);
699             HDF_LOGD("%{public}s: open devPathNoth: %{public}s status: %{public}d index: %{public}d",
700                      __func__, searchIndex->second.devPathNode, searchIndex->second.status, searchIndex->first);
701             AddToEpoll(mEpollId_, searchIndex->second.fd);
702             ret = INPUT_SUCCESS;
703         }
704     }
705     for (auto &e : inputDevList_) {
706         dumpInfoList(e.second);
707     }
708     return ret;
709 }
710 
CloseDevice(uint32_t deviceIndex)711 RetStatus InputDeviceManager::CloseDevice(uint32_t deviceIndex)
712 {
713     std::lock_guard<std::mutex> guard(lock_);
714     auto ret = INPUT_FAILURE;
715 
716     if (deviceIndex >= inputDevList_.size()) {
717         HDF_LOGE("%{public}s: param is wrong", __func__);
718         return ret;
719     }
720     auto searchIndex = inputDevList_.find(deviceIndex);
721     if (searchIndex != inputDevList_.end()) {
722         ret = CloseInputDevice(searchIndex->second.devPathNode);
723     }
724     HDF_LOGD("%{public}s: close devIndex: %{public}u ret: %{public}d inputDevList_ size:%{public}lu ",
725              __func__, deviceIndex, ret, inputDevList_.size());
726     return ret;
727 }
728 
GetDevice(int32_t deviceIndex,InputDeviceInfo ** devInfo)729 int32_t InputDeviceManager::GetDevice(int32_t deviceIndex, InputDeviceInfo **devInfo)
730 {
731     std::lock_guard<std::mutex> guard(lock_);
732     auto ret = INPUT_FAILURE;
733 
734     if (devInfo == nullptr || deviceIndex >= static_cast<int32_t>(inputDevList_.size()) || *devInfo != nullptr) {
735         HDF_LOGE("%{public}s: param is wrong", __func__);
736         return ret;
737     }
738     auto it = inputDevList_.find(deviceIndex);
739     if (it != inputDevList_.end()) {
740         int inputDeviceInfoSize = sizeof(InputDeviceInfo);
741         *devInfo = reinterpret_cast<InputDeviceInfo *>(OsalMemAlloc(inputDeviceInfoSize));
742         if (*devInfo == nullptr) {
743             HDF_LOGE("%{public}s: %{public}d OsalMemAlloc failed", __func__, __LINE__);
744             return ret;
745         }
746         if (memcpy_s(*devInfo, inputDeviceInfoSize, &it->second.detailInfo, inputDeviceInfoSize) != EOK) {
747             OsalMemFree(*devInfo);
748             HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
749             return ret;
750         }
751         ret = INPUT_SUCCESS;
752     }
753     HDF_LOGD("%{public}s: devIndex: %{public}d ret: %{public}d", __func__, deviceIndex, ret);
754     return ret;
755 }
756 
GetDeviceList(uint32_t * devNum,InputDeviceInfo ** deviceList,uint32_t size)757 int32_t InputDeviceManager::GetDeviceList(uint32_t *devNum, InputDeviceInfo **deviceList, uint32_t size)
758 {
759     std::lock_guard<std::mutex> guard(lock_);
760     auto ret = INPUT_FAILURE;
761 
762     auto scanCount = (size >= inputDevList_.size() ? inputDevList_.size() : size);
763     if ((devNum == nullptr) || (deviceList == nullptr) || inputDevList_.size() == 0 || *deviceList != nullptr) {
764         HDF_LOGE("%{public}s: param is wrong", __func__);
765         return ret;
766     }
767 
768     int inputDeviceInfoSize = sizeof(InputDeviceInfo);
769     *deviceList = reinterpret_cast<InputDeviceInfo *>(OsalMemAlloc(inputDeviceInfoSize * scanCount));
770     if (*deviceList == nullptr) {
771         HDF_LOGE("%{public}s: %{public}d OsalMemAlloc failed", __func__, __LINE__);
772         return ret;
773     }
774     for (size_t i = 0; i < scanCount; i++) {
775         if (memcpy_s((*deviceList) + i, inputDeviceInfoSize, &inputDevList_[i].detailInfo, inputDeviceInfoSize) !=
776             EOK) {
777             OsalMemFree(*deviceList);
778             HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
779             return ret;
780         }
781     }
782     *devNum = inputDevList_.size();
783     ret = INPUT_SUCCESS;
784     HDF_LOGD("%{public}s: devNum: %{public}u devIndex_: %{public}d", __func__, *devNum, devIndex_);
785 
786     return ret;
787 }
788 
789 // InputController
SetPowerStatus(uint32_t devIndex,uint32_t status)790 RetStatus InputDeviceManager::SetPowerStatus(uint32_t devIndex, uint32_t status)
791 {
792     RetStatus rc = INPUT_SUCCESS;
793     if ((devIndex >= inputDevList_.size()) || (status >= INPUT_POWER_STATUS_UNKNOWN)) {
794         HDF_LOGE("%{public}s: param is wrong", __func__);
795         return INPUT_FAILURE;
796     }
797     return rc;
798 }
799 
GetPowerStatus(uint32_t devIndex,uint32_t * status)800 RetStatus InputDeviceManager::GetPowerStatus(uint32_t devIndex, uint32_t *status)
801 {
802     RetStatus rc = INPUT_SUCCESS;
803     if ((devIndex >= inputDevList_.size()) || (status == nullptr)) {
804         HDF_LOGE("%{public}s: param is wrong", __func__);
805         return INPUT_FAILURE;
806     }
807     return rc;
808 }
809 
GetDeviceType(uint32_t devIndex,uint32_t * deviceType)810 RetStatus InputDeviceManager::GetDeviceType(uint32_t devIndex, uint32_t *deviceType)
811 {
812     RetStatus rc = INPUT_SUCCESS;
813     if ((devIndex >= inputDevList_.size()) || (deviceType == nullptr)) {
814         HDF_LOGE("%{public}s: param is wrong", __func__);
815         return INPUT_FAILURE;
816     }
817 
818     *deviceType = inputDevList_[devIndex].detailInfo.devType;
819     HDF_LOGI("%{public}s: devType: %{public}u", __func__, *deviceType);
820     return rc;
821 }
822 
GetChipInfo(uint32_t devIndex,char * chipInfo,uint32_t length)823 RetStatus InputDeviceManager::GetChipInfo(uint32_t devIndex, char *chipInfo, uint32_t length)
824 {
825     RetStatus rc = INPUT_SUCCESS;
826     if ((devIndex >= inputDevList_.size()) || (chipInfo == nullptr)) {
827         HDF_LOGE("%{public}s: param is wrong", __func__);
828         return INPUT_FAILURE;
829     }
830 
831     if (memcpy_s(chipInfo, length, inputDevList_[devIndex].detailInfo.chipInfo, length) != EOK) {
832         HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
833         rc = INPUT_FAILURE;
834     }
835     HDF_LOGI("%{public}s: chipInfo: %{public}s", __func__, chipInfo);
836     return rc;
837 }
838 
GetVendorName(uint32_t devIndex,char * vendorName,uint32_t length)839 RetStatus InputDeviceManager::GetVendorName(uint32_t devIndex, char *vendorName, uint32_t length)
840 {
841     RetStatus rc = INPUT_SUCCESS;
842     if ((devIndex >= inputDevList_.size()) || (vendorName == nullptr)) {
843         HDF_LOGE("%{public}s: param is wrong", __func__);
844         return INPUT_FAILURE;
845     }
846 
847     if (memcpy_s(vendorName, length, inputDevList_[devIndex].detailInfo.vendorName, length) != EOK) {
848         HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
849         rc = INPUT_FAILURE;
850     }
851     HDF_LOGI("%{public}s: vendorName: %{public}s", __func__, vendorName);
852     return rc;
853 }
854 
GetChipName(uint32_t devIndex,char * chipName,uint32_t length)855 RetStatus InputDeviceManager::GetChipName(uint32_t devIndex, char *chipName, uint32_t length)
856 {
857     RetStatus rc = INPUT_SUCCESS;
858     if ((devIndex >= inputDevList_.size()) || (chipName == nullptr)) {
859         HDF_LOGE("%{public}s: param is wrong", __func__);
860         return INPUT_FAILURE;
861     }
862 
863     if (memcpy_s(chipName, length, inputDevList_[devIndex].detailInfo.chipName, length) != EOK) {
864         HDF_LOGE("%{public}s: memcpy_s failed, line: %{public}d", __func__, __LINE__);
865         rc = INPUT_FAILURE;
866     }
867     HDF_LOGI("%{public}s: chipName: %{public}s", __func__, chipName);
868     return rc;
869 }
870 
SetGestureMode(uint32_t devIndex,uint32_t gestureMode)871 RetStatus InputDeviceManager::SetGestureMode(uint32_t devIndex, uint32_t gestureMode)
872 {
873     RetStatus rc = INPUT_SUCCESS;
874     if ((devIndex >= inputDevList_.size())) {
875         HDF_LOGE("%{public}s: param is wrong", __func__);
876         return INPUT_FAILURE;
877     }
878     return rc;
879 }
880 
RunCapacitanceTest(uint32_t devIndex,uint32_t testType,char * result,uint32_t length)881 RetStatus InputDeviceManager::RunCapacitanceTest(uint32_t devIndex, uint32_t testType, char *result, uint32_t length)
882 {
883     RetStatus rc = INPUT_SUCCESS;
884     if ((devIndex >= inputDevList_.size()) || (testType >= TEST_TYPE_UNKNOWN) ||
885         (result == nullptr) || (length < SELF_TEST_RESULT_LEN)) {
886         HDF_LOGE("%{public}s: param is wrong", __func__);
887         return INPUT_FAILURE;
888     }
889     return rc;
890 }
891 
RunExtraCommand(uint32_t devIndex,InputExtraCmd * cmd)892 RetStatus InputDeviceManager::RunExtraCommand(uint32_t devIndex, InputExtraCmd *cmd)
893 {
894     RetStatus rc = INPUT_SUCCESS;
895     if ((devIndex >= inputDevList_.size()) || (cmd == nullptr) || (cmd->cmdCode == nullptr ||
896         (cmd->cmdValue == nullptr))) {
897         HDF_LOGE("%{public}s: param is wrong", __func__);
898         return INPUT_FAILURE;
899     }
900     return rc;
901 }
902 
903 // InputReporter
RegisterReportCallback(uint32_t devIndex,InputEventCb * callback)904 RetStatus InputDeviceManager::RegisterReportCallback(uint32_t devIndex, InputEventCb *callback)
905 {
906     RetStatus rc = INPUT_SUCCESS;
907     if ((devIndex >= inputDevList_.size()) || (callback == nullptr) || (callback->EventPkgCallback == nullptr)) {
908         HDF_LOGE("%{public}s: param is wrong", __func__);
909         return INPUT_FAILURE;
910     }
911     std::lock_guard<std::mutex> guard(reportEventPkgCallBackLock_);
912     reportEventPkgCallback_[devIndex] = callback;
913     return rc;
914 }
915 
UnregisterReportCallback(uint32_t devIndex)916 RetStatus InputDeviceManager::UnregisterReportCallback(uint32_t devIndex)
917 {
918     HDF_LOGI("%{public}s: %{public}d dev is unregister", __func__, devIndex);
919     RetStatus rc = INPUT_SUCCESS;
920     if (devIndex >= inputDevList_.size()) {
921         HDF_LOGE("%{public}s: param is wrong", __func__);
922         return INPUT_FAILURE;
923     }
924     std::lock_guard<std::mutex> guard(reportEventPkgCallBackLock_);
925     reportEventPkgCallback_[devIndex] = nullptr;
926     return rc;
927 }
928 
RegisterHotPlugCallback(InputHostCb * callback)929 RetStatus InputDeviceManager::RegisterHotPlugCallback(InputHostCb *callback)
930 {
931     RetStatus rc = INPUT_SUCCESS;
932     reportHotPlugEventCallback_ = callback;
933     HDF_LOGI("%{public}s: called line %{public}d ret %{public}d", __func__, __LINE__, rc);
934     return rc;
935 }
936 
UnregisterHotPlugCallback(void)937 RetStatus InputDeviceManager::UnregisterHotPlugCallback(void)
938 {
939     RetStatus rc = INPUT_SUCCESS;
940     reportHotPlugEventCallback_ = nullptr;
941     HDF_LOGI("%{public}s: called line %{public}d ret:%{public}d", __func__, __LINE__, rc);
942     return rc;
943 }
944 
WorkerThread()945 void InputDeviceManager::WorkerThread()
946 {
947     HDF_LOGI("%{public}s: called line %{public}d ", __func__, __LINE__);
948     std::future<void> fuResult = std::async(std::launch::async, [this]() {
949         DoInputDeviceAction();
950         return;
951     });
952     fuResult.get();
953 }
954 }
955 }
956