1 /*
2 * Copyright (c) 2021-2023 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 "vibrator_controller.h"
17 #include <securec.h>
18 #include "hdf_base.h"
19 #include "vibrator_uhdf_log.h"
20 #include "osal_mem.h"
21
22 #define HDF_LOG_TAG uhdf_vibrator_service
23 #define EFFECT_SUN 64
24 #define EFFECT_DURATION 2000
25 #define VIBRATOR_SERVICE_NAME "hdf_misc_vibrator"
26 #define DEFAULT_START_UP_TIME 20
27 #define ERROR_STATE (-1)
28
GetVibratorDevicePriv(void)29 static struct VibratorDevice *GetVibratorDevicePriv(void)
30 {
31 static struct VibratorDevice vibratorDeviceData = {
32 .initState = false,
33 .ioService = NULL,
34 };
35
36 return &vibratorDeviceData;
37 }
38
SendVibratorMsg(uint32_t cmd,struct HdfSBuf * msg,struct HdfSBuf * reply)39 static int32_t SendVibratorMsg(uint32_t cmd, struct HdfSBuf *msg, struct HdfSBuf *reply)
40 {
41 struct VibratorDevice *priv = GetVibratorDevicePriv();
42
43 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
44 CHECK_NULL_PTR_RETURN_VALUE(priv->ioService, HDF_FAILURE);
45 CHECK_NULL_PTR_RETURN_VALUE(priv->ioService->dispatcher, HDF_FAILURE);
46 CHECK_NULL_PTR_RETURN_VALUE(priv->ioService->dispatcher->Dispatch, HDF_FAILURE);
47
48 int32_t ret = priv->ioService->dispatcher->Dispatch(&priv->ioService->object, cmd, msg, reply);
49 if (ret != HDF_SUCCESS) {
50 HDF_LOGE("%{public}s: Vibrator dispatch failed", __func__);
51 return ret;
52 }
53
54 return HDF_SUCCESS;
55 }
56
ReadVibratorInfo(struct HdfSBuf * reply,struct VibratorDevice * priv)57 static int32_t ReadVibratorInfo(struct HdfSBuf *reply, struct VibratorDevice *priv)
58 {
59 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
60 uint32_t len;
61 struct VibratorInfo *buf = NULL;
62
63 if (!HdfSbufReadBuffer(reply, (const void **)&buf, &len)) {
64 return HDF_FAILURE;
65 }
66
67 if (buf == NULL || len != sizeof(struct VibratorInfo)) {
68 HDF_LOGE("%{public}s: read size is error, len = %{public}d, size = %{public}zu\n",\
69 __func__, len, sizeof(struct VibratorInfo));
70 return HDF_FAILURE;
71 }
72
73 if (memcpy_s(&priv->vibratorInfoEntry, sizeof(priv->vibratorInfoEntry), buf, sizeof(*buf)) != EOK) {
74 HDF_LOGE("%s: Memcpy buf failed", __func__);
75 return HDF_FAILURE;
76 }
77
78 return HDF_SUCCESS;
79 }
80
GetVibratorInfo(struct VibratorInfo ** vibratorInfo)81 static int32_t GetVibratorInfo(struct VibratorInfo **vibratorInfo)
82 {
83 int32_t ret;
84 if (vibratorInfo == NULL) {
85 HDF_LOGE("%s:line:%{public}d pointer is null and return ret", __func__, __LINE__);
86 return HDF_FAILURE;
87 }
88 struct VibratorDevice *priv = GetVibratorDevicePriv();
89
90 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
91
92 (void)OsalMutexLock(&priv->mutex);
93 struct HdfSBuf *reply = HdfSbufObtainDefaultSize();
94 if (reply == NULL) {
95 HDF_LOGE("%s: get sbuf failed", __func__);
96 (void)OsalMutexUnlock(&priv->mutex);
97 return HDF_FAILURE;
98 }
99
100 ret = SendVibratorMsg(VIBRATOR_IO_GET_INFO, NULL, reply);
101 if (ret != HDF_SUCCESS) {
102 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
103 HdfSbufRecycle(reply);
104 (void)OsalMutexUnlock(&priv->mutex);
105 return ret;
106 }
107
108 if (ReadVibratorInfo(reply, priv) != HDF_SUCCESS) {
109 HdfSbufRecycle(reply);
110 (void)OsalMutexUnlock(&priv->mutex);
111 return HDF_FAILURE;
112 }
113
114 HdfSbufRecycle(reply);
115 (void)OsalMutexUnlock(&priv->mutex);
116
117 *vibratorInfo = &priv->vibratorInfoEntry;
118
119 return HDF_SUCCESS;
120 }
121
ValidityJudgment(uint32_t duration,uint16_t intensity,int16_t frequency)122 static int32_t ValidityJudgment(uint32_t duration, uint16_t intensity, int16_t frequency)
123 {
124 struct VibratorDevice *priv = GetVibratorDevicePriv();
125 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
126 if (duration == 0) {
127 HDF_LOGE("%s:invalid vibration period", __func__);
128 return VIBRATOR_NOT_PERIOD;
129 }
130
131 if ((priv->vibratorInfoEntry.isSupportIntensity == 0) || (intensity < priv->vibratorInfoEntry.intensityMinValue) ||
132 (intensity > priv->vibratorInfoEntry.intensityMaxValue)) {
133 HDF_LOGE("%s:intensity not supported", __func__);
134 return VIBRATOR_NOT_INTENSITY;
135 }
136
137 if ((priv->vibratorInfoEntry.isSupportFrequency == 0) || (frequency < priv->vibratorInfoEntry.frequencyMinValue) ||
138 (frequency > priv->vibratorInfoEntry.frequencyMaxValue)) {
139 HDF_LOGE("%s:frequency not supported", __func__);
140 return VIBRATOR_NOT_FREQUENCY;
141 }
142
143 return VIBRATOR_SUCCESS;
144 }
145
EnableVibratorModulation(uint32_t duration,uint16_t intensity,int16_t frequency)146 static int32_t EnableVibratorModulation(uint32_t duration, uint16_t intensity, int16_t frequency)
147 {
148 int32_t ret;
149 struct VibratorDevice *priv = GetVibratorDevicePriv();
150
151 ret = ValidityJudgment(duration, intensity, frequency);
152 if (ret != HDF_SUCCESS) {
153 HDF_LOGE("%{public}s: effect is false", __func__);
154 return ret;
155 }
156
157 (void)OsalMutexLock(&priv->mutex);
158 struct HdfSBuf *msg = HdfSbufObtainDefaultSize();
159 if (msg == NULL) {
160 HDF_LOGE("%{public}s: get sbuf failed", __func__);
161 (void)OsalMutexUnlock(&priv->mutex);
162 return HDF_FAILURE;
163 }
164
165 if (!HdfSbufWriteUint32(msg, duration)) {
166 HDF_LOGE("%{public}s: write duration failed.", __func__);
167 HdfSbufRecycle(msg);
168 (void)OsalMutexUnlock(&priv->mutex);
169 return HDF_FAILURE;
170 }
171
172 if (!HdfSbufWriteUint16(msg, intensity)) {
173 HDF_LOGE("%{public}s: write intensity failed.", __func__);
174 HdfSbufRecycle(msg);
175 (void)OsalMutexUnlock(&priv->mutex);
176 return HDF_FAILURE;
177 }
178
179 if (!HdfSbufWriteInt16(msg, frequency)) {
180 HDF_LOGE("%{public}s: write frequency failed.", __func__);
181 HdfSbufRecycle(msg);
182 (void)OsalMutexUnlock(&priv->mutex);
183 return HDF_FAILURE;
184 }
185 ret = SendVibratorMsg(VIBRATOR_IO_ENABLE_MODULATION_PARAMETER, msg, NULL);
186 if (ret != HDF_SUCCESS) {
187 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
188 }
189 HdfSbufRecycle(msg);
190 (void)OsalMutexUnlock(&priv->mutex);
191
192 return ret;
193 }
194
StartOnce(uint32_t duration)195 static int32_t StartOnce(uint32_t duration)
196 {
197 int32_t ret;
198 struct VibratorDevice *priv = GetVibratorDevicePriv();
199 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
200
201 (void)OsalMutexLock(&priv->mutex);
202 struct HdfSBuf *msg = HdfSbufObtainDefaultSize();
203 if (msg == NULL) {
204 HDF_LOGE("%s: get sbuf failed", __func__);
205 (void)OsalMutexUnlock(&priv->mutex);
206 return HDF_FAILURE;
207 }
208
209 if (!HdfSbufWriteUint32(msg, duration)) {
210 HDF_LOGE("%s: write duration failed", __func__);
211 HdfSbufRecycle(msg);
212 (void)OsalMutexUnlock(&priv->mutex);
213 return HDF_FAILURE;
214 }
215
216 ret = SendVibratorMsg(VIBRATOR_IO_START_ONCE, msg, NULL);
217 if (ret != HDF_SUCCESS) {
218 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
219 }
220 HdfSbufRecycle(msg);
221 (void)OsalMutexUnlock(&priv->mutex);
222
223 return ret;
224 }
225
Start(const char * effect)226 static int32_t Start(const char *effect)
227 {
228 int32_t ret;
229 struct VibratorDevice *priv = GetVibratorDevicePriv();
230 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
231
232 if (effect == NULL) {
233 HDF_LOGE("%s: start vibrator effect type invalid", __func__);
234 return HDF_ERR_INVALID_PARAM;
235 }
236
237 (void)OsalMutexLock(&priv->mutex);
238 struct HdfSBuf *msg = HdfSbufObtainDefaultSize();
239 if (msg == NULL) {
240 HDF_LOGE("%s: get sbuf failed", __func__);
241 HdfSbufRecycle(msg);
242 (void)OsalMutexUnlock(&priv->mutex);
243 return HDF_FAILURE;
244 }
245
246 if (!HdfSbufWriteString(msg, effect)) {
247 HDF_LOGE("%s: write effectName failed", __func__);
248 HdfSbufRecycle(msg);
249 (void)OsalMutexUnlock(&priv->mutex);
250 return HDF_FAILURE;
251 }
252
253 ret = SendVibratorMsg(VIBRATOR_IO_START_EFFECT, msg, NULL);
254 if (ret != HDF_SUCCESS) {
255 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
256 }
257 HdfSbufRecycle(msg);
258 (void)OsalMutexUnlock(&priv->mutex);
259
260 return ret;
261 }
262
GetEffectInfo(const char * effect,struct EffectInfo * effectInfo)263 static int32_t GetEffectInfo(const char *effect, struct EffectInfo *effectInfo)
264 {
265 CHECK_NULL_PTR_RETURN_VALUE(effectInfo, HDF_FAILURE);
266 for (int i = 0; i < EFFECT_TYPE_MAX; i++) {
267 if (!strcmp(effect, g_effectmap[i].effectName)) {
268 effectInfo->isSupportEffect = g_effectmap[i].issupport;
269 effectInfo->duration = g_effectmap[i].duration;
270 }
271 }
272 return HDF_SUCCESS;
273 }
274
Stop(enum VibratorMode mode)275 static int32_t Stop(enum VibratorMode mode)
276 {
277 if (mode < VIBRATOR_MODE_ONCE || mode >= VIBRATOR_MODE_BUTT) {
278 return HDF_ERR_INVALID_PARAM;
279 }
280 if (mode == VIBRATOR_MODE_HDHAPTIC) {
281 return HDF_ERR_NOT_SUPPORT;
282 }
283 int32_t ret;
284 struct VibratorDevice *priv = GetVibratorDevicePriv();
285 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
286
287 (void)OsalMutexLock(&priv->mutex);
288 struct HdfSBuf *msg = HdfSbufObtainDefaultSize();
289 if (msg == NULL) {
290 HDF_LOGE("%s: get sbuf failed", __func__);
291 (void)OsalMutexUnlock(&priv->mutex);
292 return HDF_FAILURE;
293 }
294
295 if (!HdfSbufWriteInt32(msg, mode)) {
296 HDF_LOGE("%s: write mode failed", __func__);
297 HdfSbufRecycle(msg);
298 (void)OsalMutexUnlock(&priv->mutex);
299 return HDF_FAILURE;
300 }
301
302 ret = SendVibratorMsg(VIBRATOR_IO_STOP, msg, NULL);
303 if (ret != HDF_SUCCESS) {
304 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
305 }
306 HdfSbufRecycle(msg);
307 (void)OsalMutexUnlock(&priv->mutex);
308
309 return ret;
310 }
311
PlayHapticPattern(struct HapticPaket * pkg)312 static int32_t PlayHapticPattern(struct HapticPaket *pkg)
313 {
314 (void)pkg;
315 return HDF_SUCCESS;
316 }
317
GetHapticCapacity(struct HapticCapacity * hapticCapacity)318 static int32_t GetHapticCapacity(struct HapticCapacity *hapticCapacity)
319 {
320 (void)hapticCapacity;
321 return HDF_SUCCESS;
322 }
323
GetHapticStartUpTime(int32_t mode,int32_t * startUpTime)324 static int32_t GetHapticStartUpTime(int32_t mode, int32_t *startUpTime)
325 {
326 *startUpTime = DEFAULT_START_UP_TIME;
327 HDF_LOGE("%{public}s: mode = %{public}d", __func__, mode);
328 HDF_LOGE("%{public}s: startUpTime = %{public}d", __func__, *startUpTime);
329 return HDF_SUCCESS;
330 }
331
IsVibratorRunning(bool * state)332 static int32_t IsVibratorRunning(bool *state)
333 {
334 HDF_LOGI("%{public}s: in", __func__);
335 if (state == NULL) {
336 HDF_LOGE("%{public}s: state is NULL", __func__);
337 return HDF_FAILURE;
338 }
339 int32_t ret;
340 struct VibratorDevice *priv = GetVibratorDevicePriv();
341
342 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
343
344 (void)OsalMutexLock(&priv->mutex);
345 struct HdfSBuf *reply = HdfSbufObtainDefaultSize();
346 if (reply == NULL) {
347 HDF_LOGE("%s: get sbuf failed", __func__);
348 (void)OsalMutexUnlock(&priv->mutex);
349 return HDF_FAILURE;
350 }
351
352 ret = SendVibratorMsg(VIBRATOR_IO_IS_VIBRATOR_RUNNING, NULL, reply);
353 if (ret != HDF_SUCCESS) {
354 HDF_LOGE("%{public}s: Vibrator send cmd failed, ret[%{public}d]", __func__, ret);
355 HdfSbufRecycle(reply);
356 (void)OsalMutexUnlock(&priv->mutex);
357 return ret;
358 }
359
360 int32_t stateNum = ERROR_STATE;
361 if (!HdfSbufReadInt32(reply, &stateNum)) {
362 HDF_LOGE("%{public}s: HdfSbufReadInt32 failed", __func__);
363 HdfSbufRecycle(reply);
364 (void)OsalMutexUnlock(&priv->mutex);
365 return HDF_FAILURE;
366 }
367
368 *state = stateNum;
369 HdfSbufRecycle(reply);
370 (void)OsalMutexUnlock(&priv->mutex);
371
372 HDF_LOGI("%{public}s: *state %{public}d", __func__, *state);
373
374 return HDF_SUCCESS;
375 }
376
NewVibratorInterfaceInstance(void)377 const struct VibratorInterface *NewVibratorInterfaceInstance(void)
378 {
379 static struct VibratorInterface vibratorDevInstance;
380 struct VibratorDevice *priv = GetVibratorDevicePriv();
381
382 if (priv == NULL) {
383 return &vibratorDevInstance;
384 }
385 if (priv->initState) {
386 return &vibratorDevInstance;
387 }
388
389 OsalMutexInit(&priv->mutex);
390 vibratorDevInstance.Start = Start;
391 vibratorDevInstance.StartOnce = StartOnce;
392 vibratorDevInstance.Stop = Stop;
393 vibratorDevInstance.GetVibratorInfo = GetVibratorInfo;
394 vibratorDevInstance.GetEffectInfo = GetEffectInfo;
395 vibratorDevInstance.EnableVibratorModulation = EnableVibratorModulation;
396 vibratorDevInstance.PlayHapticPattern = PlayHapticPattern;
397 vibratorDevInstance.GetHapticCapacity = GetHapticCapacity;
398 vibratorDevInstance.GetHapticStartUpTime = GetHapticStartUpTime;
399 vibratorDevInstance.IsVibratorRunning = IsVibratorRunning;
400
401 priv->ioService = HdfIoServiceBind(VIBRATOR_SERVICE_NAME);
402 if (priv->ioService == NULL) {
403 HDF_LOGE("%s: get vibrator ioService failed", __func__);
404 OsalMutexDestroy(&priv->mutex);
405 return NULL;
406 }
407
408 priv->initState = true;
409 HDF_LOGD("get vibrator devInstance success");
410 return &vibratorDevInstance;
411 }
412
FreeVibratorInterfaceInstance(void)413 int32_t FreeVibratorInterfaceInstance(void)
414 {
415 struct VibratorDevice *priv = GetVibratorDevicePriv();
416
417 CHECK_NULL_PTR_RETURN_VALUE(priv, HDF_FAILURE);
418
419 if (!priv->initState) {
420 HDF_LOGD("%s: vibrator instance had released", __func__);
421 return HDF_SUCCESS;
422 }
423
424 if (priv->ioService != NULL) {
425 HdfIoServiceRecycle(priv->ioService);
426 }
427
428 OsalMutexDestroy(&priv->mutex);
429
430 return HDF_SUCCESS;
431 }