1 /*
2  * Copyright (c) 2021-2024 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 "miscdevice_service_stub.h"
17 
18 #include <string>
19 #include <unistd.h>
20 
21 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
22 #include "hisysevent.h"
23 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
24 #include "ipc_skeleton.h"
25 #include "message_parcel.h"
26 #include "securec.h"
27 
28 #include "permission_util.h"
29 #include "sensors_errors.h"
30 
31 #undef LOG_TAG
32 #define LOG_TAG "MiscdeviceServiceStub"
33 
34 namespace OHOS {
35 namespace Sensors {
36 using namespace OHOS::HiviewDFX;
37 
38 namespace {
39 const std::string VIBRATE_PERMISSION = "ohos.permission.VIBRATE";
40 const std::string LIGHT_PERMISSION = "ohos.permission.SYSTEM_LIGHT_CONTROL";
41 }  // namespace
42 
MiscdeviceServiceStub()43 MiscdeviceServiceStub::MiscdeviceServiceStub() {}
44 
~MiscdeviceServiceStub()45 MiscdeviceServiceStub::~MiscdeviceServiceStub() {}
46 
VibrateStub(MessageParcel &data, MessageParcel &reply)47 int32_t MiscdeviceServiceStub::VibrateStub(MessageParcel &data, MessageParcel &reply)
48 {
49     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
50     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
51     if (ret != PERMISSION_GRANTED) {
52 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
53         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
54             HiSysEvent::EventType::SECURITY, "PKG_NAME", "VibrateStub", "ERROR_CODE", ret);
55 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
56         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
57         return PERMISSION_DENIED;
58     }
59     int32_t vibratorId;
60     int32_t duration;
61     int32_t usage;
62     bool systemUsage;
63     if ((!data.ReadInt32(vibratorId)) || (!data.ReadInt32(duration)) || (!data.ReadInt32(usage))||
64         (!data.ReadBool(systemUsage))) {
65         MISC_HILOGE("Parcel read failed");
66         return ERROR;
67     }
68     return Vibrate(vibratorId, duration, usage, systemUsage);
69 }
70 
StopVibratorAllStub(MessageParcel &data, MessageParcel &reply)71 int32_t MiscdeviceServiceStub::StopVibratorAllStub(MessageParcel &data, MessageParcel &reply)
72 {
73     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
74     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
75     if (ret != PERMISSION_GRANTED) {
76 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
77         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
78             HiSysEvent::EventType::SECURITY, "PKG_NAME", "StopVibratorStub", "ERROR_CODE", ret);
79 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
80         MISC_HILOGE("Result:%{public}d", ret);
81         return PERMISSION_DENIED;
82     }
83     int32_t vibratorId;
84     if (!data.ReadInt32(vibratorId)) {
85         MISC_HILOGE("Parcel read failed");
86         return ERROR;
87     }
88     return StopVibrator(vibratorId);
89 }
90 
PlayVibratorEffectStub(MessageParcel &data, MessageParcel &reply)91 int32_t MiscdeviceServiceStub::PlayVibratorEffectStub(MessageParcel &data, MessageParcel &reply)
92 {
93     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
94     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
95     if (ret != PERMISSION_GRANTED) {
96 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
97         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
98             HiSysEvent::EventType::SECURITY, "PKG_NAME", "PlayVibratorEffectStub", "ERROR_CODE", ret);
99 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
100         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
101         return PERMISSION_DENIED;
102     }
103     int32_t vibratorId;
104     std::string effect;
105     int32_t count;
106     int32_t usage;
107     bool systemUsage;
108     if ((!data.ReadInt32(vibratorId)) || (!data.ReadString(effect)) ||
109         (!data.ReadInt32(count)) || (!data.ReadInt32(usage)) || (!data.ReadBool(systemUsage))) {
110         MISC_HILOGE("Parcel read failed");
111         return ERROR;
112     }
113     return PlayVibratorEffect(vibratorId, effect, count, usage, systemUsage);
114 }
115 
StopVibratorByModeStub(MessageParcel &data, MessageParcel &reply)116 int32_t MiscdeviceServiceStub::StopVibratorByModeStub(MessageParcel &data, MessageParcel &reply)
117 {
118     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
119     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
120     if (ret != PERMISSION_GRANTED) {
121 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
122         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
123             HiSysEvent::EventType::SECURITY, "PKG_NAME", "StopVibratorByModeStub", "ERROR_CODE", ret);
124 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
125         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
126         return PERMISSION_DENIED;
127     }
128     int32_t vibratorId;
129     std::string mode;
130     if ((!data.ReadInt32(vibratorId)) || (!data.ReadString(mode))) {
131         MISC_HILOGE("Parcel read failed");
132         return ERROR;
133     }
134     return StopVibrator(vibratorId, mode);
135 }
136 
IsSupportEffectStub(MessageParcel &data, MessageParcel &reply)137 int32_t MiscdeviceServiceStub::IsSupportEffectStub(MessageParcel &data, MessageParcel &reply)
138 {
139     std::string effect;
140     if (!data.ReadString(effect)) {
141         MISC_HILOGE("Parcel read effect failed");
142         return ERROR;
143     }
144     bool state = false;
145     int32_t ret = IsSupportEffect(effect, state);
146     if (ret != NO_ERROR) {
147         MISC_HILOGE("Query support effect failed");
148         return ret;
149     }
150     if (!reply.WriteBool(state)) {
151         MISC_HILOGE("Parcel write state failed");
152     }
153     return ret;
154 }
155 
156 #ifdef OHOS_BUILD_ENABLE_VIBRATOR_CUSTOM
PlayVibratorCustomStub(MessageParcel &data, MessageParcel &reply)157 int32_t MiscdeviceServiceStub::PlayVibratorCustomStub(MessageParcel &data, MessageParcel &reply)
158 {
159     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
160     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
161     if (ret != PERMISSION_GRANTED) {
162 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
163         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
164             HiSysEvent::EventType::SECURITY, "PKG_NAME", "PlayVibratorCustomStub", "ERROR_CODE", ret);
165 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
166         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
167         return PERMISSION_DENIED;
168     }
169     int32_t vibratorId;
170     if (!data.ReadInt32(vibratorId)) {
171         MISC_HILOGE("Parcel read vibratorId failed");
172         return ERROR;
173     }
174     int32_t usage;
175     bool systemUsage;
176     if (!data.ReadInt32(usage) || !data.ReadBool(systemUsage)) {
177         MISC_HILOGE("Parcel read failed");
178         return ERROR;
179     }
180     VibrateParameter vibrateParameter;
181     auto parameter = vibrateParameter.Unmarshalling(data);
182     if (!parameter.has_value()) {
183         MISC_HILOGE("Parameter Unmarshalling failed");
184         return ERROR;
185     }
186     RawFileDescriptor rawFd;
187     if (!data.ReadInt64(rawFd.offset)) {
188         MISC_HILOGE("Parcel read offset failed");
189         return ERROR;
190     }
191     if (!data.ReadInt64(rawFd.length)) {
192         MISC_HILOGE("Parcel read length failed");
193         return ERROR;
194     }
195     rawFd.fd = data.ReadFileDescriptor();
196     if (rawFd.fd < 0) {
197         MISC_HILOGE("Parcel ReadFileDescriptor failed");
198         return ERROR;
199     }
200     ret = PlayVibratorCustom(vibratorId, rawFd, usage, systemUsage, parameter.value());
201     if (ret != ERR_OK) {
202         MISC_HILOGD("PlayVibratorCustom failed, ret:%{public}d", ret);
203         return ret;
204     }
205     return ret;
206 }
207 #endif // OHOS_BUILD_ENABLE_VIBRATOR_CUSTOM
208 
GetLightListStub(MessageParcel &data, MessageParcel &reply)209 int32_t MiscdeviceServiceStub::GetLightListStub(MessageParcel &data, MessageParcel &reply)
210 {
211     (void)data;
212     std::vector<LightInfoIPC> lightInfos(GetLightList());
213     size_t lightCount = lightInfos.size();
214     MISC_HILOGI("lightCount:%{public}zu", lightCount);
215     if (!reply.WriteUint32(lightCount)) {
216         MISC_HILOGE("Parcel write failed");
217         return WRITE_MSG_ERR;
218     }
219     for (size_t i = 0; i < lightCount; ++i) {
220         if (!lightInfos[i].Marshalling(reply)) {
221             MISC_HILOGE("lightInfo %{public}zu marshalling failed", i);
222             return WRITE_MSG_ERR;
223         }
224     }
225     return NO_ERROR;
226 }
227 
TurnOnStub(MessageParcel &data, MessageParcel &reply)228 int32_t MiscdeviceServiceStub::TurnOnStub(MessageParcel &data, MessageParcel &reply)
229 {
230     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
231     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), LIGHT_PERMISSION);
232     if (ret != PERMISSION_GRANTED) {
233 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
234         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "LIGHT_PERMISSIONS_EXCEPTION",
235             HiSysEvent::EventType::SECURITY, "PKG_NAME", "turnOnStub", "ERROR_CODE", ret);
236 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
237         MISC_HILOGE("CheckLightPermission failed, ret:%{public}d", ret);
238         return PERMISSION_DENIED;
239     }
240     int32_t lightId = data.ReadInt32();
241     LightColor lightColor;
242     lightColor.singleColor = data.ReadInt32();
243     LightAnimationIPC lightAnimation;
244     auto tmpAnimation = lightAnimation.Unmarshalling(data);
245     CHKPR(tmpAnimation, ERROR);
246     return TurnOn(lightId, lightColor, *tmpAnimation);
247 }
248 
TurnOffStub(MessageParcel &data, MessageParcel &reply)249 int32_t MiscdeviceServiceStub::TurnOffStub(MessageParcel &data, MessageParcel &reply)
250 {
251     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
252     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), LIGHT_PERMISSION);
253     if (ret != PERMISSION_GRANTED) {
254 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
255         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "LIGHT_PERMISSIONS_EXCEPTION",
256             HiSysEvent::EventType::SECURITY, "PKG_NAME", "TurnOffStub", "ERROR_CODE", ret);
257 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
258         MISC_HILOGE("CheckLightPermission failed, ret:%{public}d", ret);
259         return PERMISSION_DENIED;
260     }
261     int32_t lightId = data.ReadInt32();
262     return TurnOff(lightId);
263 }
264 
ProcessRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option)265 int32_t MiscdeviceServiceStub::ProcessRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply,
266     MessageOption &option)
267 {
268     switch (code) {
269         case static_cast<int32_t>(MiscdeviceInterfaceCode::VIBRATE): {
270             return VibrateStub(data, reply);
271         }
272         case static_cast<int32_t>(MiscdeviceInterfaceCode::PLAY_VIBRATOR_EFFECT): {
273             return PlayVibratorEffectStub(data, reply);
274         }
275 #ifdef OHOS_BUILD_ENABLE_VIBRATOR_CUSTOM
276         case static_cast<int32_t>(MiscdeviceInterfaceCode::PLAY_VIBRATOR_CUSTOM): {
277             return PlayVibratorCustomStub(data, reply);
278         }
279 #endif // OHOS_BUILD_ENABLE_VIBRATOR_CUSTOM
280         case static_cast<int32_t>(MiscdeviceInterfaceCode::STOP_VIBRATOR_ALL): {
281             return StopVibratorAllStub(data, reply);
282         }
283         case static_cast<int32_t>(MiscdeviceInterfaceCode::STOP_VIBRATOR_BY_MODE): {
284             return StopVibratorByModeStub(data, reply);
285         }
286         case static_cast<int32_t>(MiscdeviceInterfaceCode::IS_SUPPORT_EFFECT): {
287             return IsSupportEffectStub(data, reply);
288         }
289         case static_cast<int32_t>(MiscdeviceInterfaceCode::GET_LIGHT_LIST): {
290             return GetLightListStub(data, reply);
291         }
292         case static_cast<int32_t>(MiscdeviceInterfaceCode::TURN_ON): {
293             return TurnOnStub(data, reply);
294         }
295         case static_cast<int32_t>(MiscdeviceInterfaceCode::TURN_OFF): {
296             return TurnOffStub(data, reply);
297         }
298         case static_cast<int32_t>(MiscdeviceInterfaceCode::PlAY_PATTERN): {
299             return PlayPatternStub(data, reply);
300         }
301         case static_cast<int32_t>(MiscdeviceInterfaceCode::GET_DELAY_TIME): {
302             return GetDelayTimeStub(data, reply);
303         }
304         case static_cast<int32_t>(MiscdeviceInterfaceCode::TRANSFER_CLIENT_REMOTE_OBJECT): {
305             return TransferClientRemoteObjectStub(data, reply);
306         }
307         case static_cast<int32_t>(MiscdeviceInterfaceCode::PLAY_PRIMITIVE_EFFECT): {
308             return PlayPrimitiveEffectStub(data, reply);
309         }
310         case static_cast<int32_t>(MiscdeviceInterfaceCode::GET_VIBRATOR_CAPACITY): {
311             return GetVibratorCapacityStub(data, reply);
312         }
313         default: {
314             MISC_HILOGD("Remoterequest no member function default process");
315             return IPCObjectStub::OnRemoteRequest(code, data, reply, option);
316         }
317     }
318 }
319 
OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option)320 int32_t MiscdeviceServiceStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply,
321                                                MessageOption &option)
322 {
323     MISC_HILOGD("Remoterequest begin, cmd:%{public}u", code);
324     std::u16string descriptor = MiscdeviceServiceStub::GetDescriptor();
325     std::u16string remoteDescriptor = data.ReadInterfaceToken();
326     if (descriptor != remoteDescriptor) {
327         MISC_HILOGE("Client and service descriptors are inconsistent");
328         return OBJECT_NULL;
329     }
330     return ProcessRemoteRequest(code, data, reply, option);
331 }
332 
PlayPatternStub(MessageParcel &data, MessageParcel &reply)333 int32_t MiscdeviceServiceStub::PlayPatternStub(MessageParcel &data, MessageParcel &reply)
334 {
335     CALL_LOG_ENTER;
336     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
337     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
338     if (ret != PERMISSION_GRANTED) {
339 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
340         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
341             HiSysEvent::EventType::SECURITY, "PKG_NAME", "PlayPatternStub", "ERROR_CODE", ret);
342 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
343         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
344         return PERMISSION_DENIED;
345     }
346     VibratePattern vibratePattern;
347     auto pattern = vibratePattern.Unmarshalling(data);
348     if (!pattern.has_value()) {
349         MISC_HILOGE("Pattern Unmarshalling failed");
350         return ERROR;
351     }
352     int32_t usage = 0;
353     if (!data.ReadInt32(usage)) {
354         MISC_HILOGE("Parcel read usage failed");
355         return ERROR;
356     }
357     bool systemUsage = false;
358     if (!data.ReadBool(systemUsage)) {
359         MISC_HILOGE("Parcel read systemUsage failed");
360         return ERROR;
361     }
362     VibrateParameter vibrateParameter;
363     auto parameter = vibrateParameter.Unmarshalling(data);
364     if (!parameter.has_value()) {
365         MISC_HILOGE("Parameter Unmarshalling failed");
366         return ERROR;
367     }
368     return PlayPattern(pattern.value(), usage, systemUsage, parameter.value());
369 }
370 
GetDelayTimeStub(MessageParcel &data, MessageParcel &reply)371 int32_t MiscdeviceServiceStub::GetDelayTimeStub(MessageParcel &data, MessageParcel &reply)
372 {
373     CALL_LOG_ENTER;
374     int32_t delayTime = 0;
375     if (GetDelayTime(delayTime) != ERR_OK) {
376         MISC_HILOGE("GetDelayTime failed");
377         return ERROR;
378     }
379     if (!reply.WriteInt32(delayTime)) {
380         MISC_HILOGE("Failed, write delayTime failed");
381         return ERROR;
382     }
383     return NO_ERROR;
384 }
385 
TransferClientRemoteObjectStub(MessageParcel &data, MessageParcel &reply)386 int32_t MiscdeviceServiceStub::TransferClientRemoteObjectStub(MessageParcel &data, MessageParcel &reply)
387 {
388     CALL_LOG_ENTER;
389     sptr<IRemoteObject> vibratorServiceClient = data.ReadRemoteObject();
390     if (vibratorServiceClient == nullptr) {
391         MISC_HILOGE("vibratorServiceClient is null");
392         return ERROR;
393     }
394     return TransferClientRemoteObject(vibratorServiceClient);
395 }
396 
PlayPrimitiveEffectStub(MessageParcel &data, MessageParcel &reply)397 int32_t MiscdeviceServiceStub::PlayPrimitiveEffectStub(MessageParcel &data, MessageParcel &reply)
398 {
399     PermissionUtil &permissionUtil = PermissionUtil::GetInstance();
400     int32_t ret = permissionUtil.CheckVibratePermission(this->GetCallingTokenID(), VIBRATE_PERMISSION);
401     if (ret != PERMISSION_GRANTED) {
402 #ifdef HIVIEWDFX_HISYSEVENT_ENABLE
403         HiSysEventWrite(HiSysEvent::Domain::MISCDEVICE, "VIBRATOR_PERMISSIONS_EXCEPTION",
404             HiSysEvent::EventType::SECURITY, "PKG_NAME", "PlayPrimitiveEffectStub", "ERROR_CODE", ret);
405 #endif // HIVIEWDFX_HISYSEVENT_ENABLE
406         MISC_HILOGE("CheckVibratePermission failed, ret:%{public}d", ret);
407         return PERMISSION_DENIED;
408     }
409     int32_t vibratorId = 0;
410     std::string effect;
411     int32_t intensity = 0;
412     int32_t usage = 0;
413     bool systemUsage = false;
414     int32_t count = 0;
415     if ((!data.ReadInt32(vibratorId)) || (!data.ReadString(effect)) ||
416         (!data.ReadInt32(intensity)) || (!data.ReadInt32(usage)) || (!data.ReadBool(systemUsage)) ||
417         (!data.ReadInt32(count))) {
418         MISC_HILOGE("Parcel read failed");
419         return ERROR;
420     }
421     return PlayPrimitiveEffect(vibratorId, effect, intensity, usage, systemUsage, count);
422 }
423 
GetVibratorCapacityStub(MessageParcel &data, MessageParcel &reply)424 int32_t MiscdeviceServiceStub::GetVibratorCapacityStub(MessageParcel &data, MessageParcel &reply)
425 {
426     VibratorCapacity capacity;
427     int32_t ret = GetVibratorCapacity(capacity);
428     if (ret != NO_ERROR) {
429         MISC_HILOGE("Query support custom vibration failed");
430         return ret;
431     }
432     if (!capacity.Marshalling(reply)) {
433         MISC_HILOGE("VibratorCapacity marshalling failed");
434         return WRITE_MSG_ERR;
435     }
436     return ret;
437 }
438 }  // namespace Sensors
439 }  // namespace OHOS
440