1 /*
2 * Copyright (c) 2021-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 "virtual_device.h"
17
18 #include <fcntl.h>
19 #include <securec.h>
20 #include <unistd.h>
21
22 #include "mmi_log.h"
23
24 #undef MMI_LOG_TAG
25 #define MMI_LOG_TAG "VirtualDevice"
26
27 namespace OHOS {
28 namespace MMI {
29 namespace {
30 using namespace OHOS::HiviewDFX;
31 constexpr uint32_t MAX_NAME_LENGTH { 80 };
32
DoIoctl(int32_t fd,int32_t request,const uint32_t value)33 bool DoIoctl(int32_t fd, int32_t request, const uint32_t value)
34 {
35 int32_t rc = ioctl(fd, request, value);
36 if (rc < 0) {
37 MMI_HILOGE("Failed to ioctl");
38 return false;
39 }
40 return true;
41 }
42 } // namespace
43
VirtualDevice(const char * deviceName,uint16_t productId)44 VirtualDevice::VirtualDevice(const char *deviceName, uint16_t productId)
45 : deviceName_(deviceName),
46 busType_(BUS_USB),
47 vendorId_(0x6006),
48 productId_(productId),
49 version_(1) {}
50
~VirtualDevice()51 VirtualDevice::~VirtualDevice()
52 {
53 if (fd_ >= 0) {
54 ioctl(fd_, UI_DEV_DESTROY);
55 close(fd_);
56 fd_ = -1;
57 }
58 }
59
SetUp()60 bool VirtualDevice::SetUp()
61 {
62 fd_ = open("/dev/uinput", O_WRONLY | O_NONBLOCK);
63 if (fd_ < 0) {
64 MMI_HILOGE("Failed to open uinput");
65 return false;
66 }
67 for (const auto &item : GetEventTypes()) {
68 if (!DoIoctl(fd_, UI_SET_EVBIT, item)) {
69 MMI_HILOGE("Error setting event type:%{public}u", item);
70 return false;
71 }
72 }
73 for (const auto &item : GetKeys()) {
74 if (!DoIoctl(fd_, UI_SET_KEYBIT, item)) {
75 MMI_HILOGE("Error setting key:%{public}u", item);
76 return false;
77 }
78 }
79 for (const auto &item : GetProperties()) {
80 if (!DoIoctl(fd_, UI_SET_PROPBIT, item)) {
81 MMI_HILOGE("Error setting property:%{public}u", item);
82 return false;
83 }
84 }
85 for (const auto &item : GetAbs()) {
86 if (!DoIoctl(fd_, UI_SET_ABSBIT, item)) {
87 MMI_HILOGE("Error setting property:%{public}u", item);
88 return false;
89 }
90 }
91 for (const auto &item : GetRelBits()) {
92 if (!DoIoctl(fd_, UI_SET_RELBIT, item)) {
93 MMI_HILOGE("Error setting rel:%{public}u", item);
94 return false;
95 }
96 }
97
98 return SetUpExt();
99 }
100
SetUpExt()101 bool VirtualDevice::SetUpExt()
102 {
103 errno_t ret = strncpy_s(dev_.name, MAX_NAME_LENGTH, deviceName_, sizeof(dev_.name));
104 if (ret != EOK) {
105 MMI_HILOGE("Failed to copy deviceName");
106 return false;
107 }
108 dev_.id.bustype = busType_;
109 dev_.id.vendor = vendorId_;
110 dev_.id.product = productId_;
111 dev_.id.version = version_;
112 if (write(fd_, &dev_, sizeof(dev_)) < 0) {
113 MMI_HILOGE("Unable to set input device info");
114 return false;
115 }
116 if (ioctl(fd_, UI_DEV_CREATE) < 0) {
117 MMI_HILOGE("Unable to create input device");
118 return false;
119 }
120 return true;
121 }
122
EmitEvent(uint16_t type,uint16_t code,uint32_t value) const123 bool VirtualDevice::EmitEvent(uint16_t type, uint16_t code, uint32_t value) const
124 {
125 struct input_event event {};
126 event.type = type;
127 event.code = code;
128 event.value = value;
129 #ifndef __MUSL__
130 gettimeofday(&event.time, nullptr);
131 #endif
132 if (write(fd_, &event, sizeof(event)) < static_cast<ssize_t>(sizeof(event))) {
133 MMI_HILOGE("Event write failed");
134 return false;
135 }
136 return true;
137 }
138
GetEventTypes() const139 const std::vector<uint32_t> &VirtualDevice::GetEventTypes() const
140 {
141 static const std::vector<uint32_t> evtTypes {};
142 return evtTypes;
143 }
144
GetKeys() const145 const std::vector<uint32_t> &VirtualDevice::GetKeys() const
146 {
147 static const std::vector<uint32_t> keys {};
148 return keys;
149 }
150
GetProperties() const151 const std::vector<uint32_t> &VirtualDevice::GetProperties() const
152 {
153 static const std::vector<uint32_t> properties {};
154 return properties;
155 }
156
GetAbs() const157 const std::vector<uint32_t> &VirtualDevice::GetAbs() const
158 {
159 static const std::vector<uint32_t> abs {};
160 return abs;
161 }
162
GetRelBits() const163 const std::vector<uint32_t> &VirtualDevice::GetRelBits() const
164 {
165 static const std::vector<uint32_t> relBits {};
166 return relBits;
167 }
168 }
169 }
170