1 /*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
3 *
4 * HDF is dual licensed: you can use it either under the terms of
5 * the GPL, or the BSD license, at your option.
6 * See the LICENSE file in the root of this repository for complete details.
7 */
8
9 #include "rtc_if.h"
10 #include "hdf_io_service_if.h"
11 #include "hdf_log.h"
12 #include "hdf_sbuf.h"
13 #include "osal_mem.h"
14 #include "securec.h"
15
16 #define HDF_LOG_TAG rtc_if_u_c
17
RtcPutObjByPointer(const void * obj)18 static void RtcPutObjByPointer(const void *obj)
19 {
20 if (obj == NULL) {
21 return;
22 }
23 HdfIoServiceRecycle((struct HdfIoService *)obj);
24 };
25
RtcOpen()26 DevHandle RtcOpen()
27 {
28 void *host = NULL;
29
30 host = HdfIoServiceBind("HDF_PLATFORM_RTC");
31 if (host == NULL) {
32 HDF_LOGE("%s: rtc service bind fail", __func__);
33 return NULL;
34 }
35
36 return (DevHandle)host;
37 }
38
RtcClose(DevHandle handle)39 void RtcClose(DevHandle handle)
40 {
41 struct RtcHost *host = NULL;
42
43 if (handle == NULL) {
44 HDF_LOGE("%s: handle is NULL", __func__);
45 return;
46 }
47
48 host = (struct RtcHost *)handle;
49 RtcPutObjByPointer(host);
50 }
51
RtcReadTime(DevHandle handle,struct RtcTime * time)52 int32_t RtcReadTime(DevHandle handle, struct RtcTime *time)
53 {
54 int32_t ret;
55 uint32_t len = 0;
56 struct RtcHost *host = NULL;
57 struct HdfSBuf *reply = NULL;
58 struct HdfIoService *service = NULL;
59 struct RtcTime *temp = NULL;
60
61 if (handle == NULL || time == NULL) {
62 HDF_LOGE("%s: handle or time is NULL.", __func__);
63 return HDF_ERR_INVALID_OBJECT;
64 }
65
66 host = (struct RtcHost *)handle;
67
68 reply = HdfSbufObtainDefaultSize();
69 if (reply == NULL) {
70 HDF_LOGE("%s: fail to obtain reply!", __func__);
71 return HDF_ERR_MALLOC_FAIL;
72 }
73
74 service = (struct HdfIoService *)host;
75 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
76 HDF_LOGE("%s: service is invalid", __func__);
77 ret = HDF_ERR_MALLOC_FAIL;
78 goto EXIT;
79 }
80
81 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_READTIME, NULL, reply);
82 if (ret != HDF_SUCCESS) {
83 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
84 goto EXIT;
85 }
86
87 if (!HdfSbufReadBuffer(reply, (const void **)&temp, &len) || temp == NULL) {
88 HDF_LOGE("%s: read buffer fail", __func__);
89 ret = HDF_ERR_IO;
90 goto EXIT;
91 }
92
93 if (len != sizeof(*time)) {
94 HDF_LOGE("%s: read error, len: %u, size: %zu", __func__, len, sizeof(*time));
95 ret = HDF_FAILURE;
96 goto EXIT;
97 }
98
99 if (memcpy_s(time, sizeof(*time), temp, len) != EOK) {
100 HDF_LOGE("%s: memcpy time fail!", __func__);
101 ret = HDF_ERR_IO;
102 goto EXIT;
103 }
104
105 EXIT:
106 HdfSbufRecycle(reply);
107 return ret;
108 }
109
RtcWriteTime(DevHandle handle,const struct RtcTime * time)110 int32_t RtcWriteTime(DevHandle handle, const struct RtcTime *time)
111 {
112 int32_t ret;
113 struct RtcHost *host = NULL;
114 struct HdfSBuf *data = NULL;
115 struct HdfIoService *service = NULL;
116
117 if (handle == NULL || time == NULL) {
118 HDF_LOGE("%s: handle or time is NULL.", __func__);
119 return HDF_ERR_INVALID_OBJECT;
120 }
121
122 host = (struct RtcHost *)handle;
123
124 data = HdfSbufObtainDefaultSize();
125 if (data == NULL) {
126 HDF_LOGE("%s: fail to obtain data", __func__);
127 return HDF_ERR_MALLOC_FAIL;
128 }
129
130 if (!HdfSbufWriteBuffer(data, time, sizeof(*time))) {
131 HDF_LOGE("%s: write rtc time fail!", __func__);
132 HdfSbufRecycle(data);
133 return HDF_ERR_IO;
134 }
135
136 service = (struct HdfIoService *)host;
137 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
138 HDF_LOGE("%s: service is invalid", __func__);
139 HdfSbufRecycle(data);
140 return HDF_ERR_MALLOC_FAIL;
141 }
142
143 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_WRITETIME, data, NULL);
144 if (ret != HDF_SUCCESS) {
145 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
146 HdfSbufRecycle(data);
147 return ret;
148 }
149
150 HdfSbufRecycle(data);
151 return HDF_SUCCESS;
152 }
153
RtcReadAlarm(DevHandle handle,enum RtcAlarmIndex alarmIndex,struct RtcTime * time)154 int32_t RtcReadAlarm(DevHandle handle, enum RtcAlarmIndex alarmIndex, struct RtcTime *time)
155 {
156 int32_t ret;
157 uint32_t len = 0;
158 struct RtcHost *host = NULL;
159 struct HdfSBuf *data = NULL;
160 struct HdfSBuf *reply = NULL;
161 struct RtcTime *temp = NULL;
162 struct HdfIoService *service = NULL;
163
164 if (handle == NULL || time == NULL) {
165 HDF_LOGE("%s: handle or time is NULL.", __func__);
166 return HDF_ERR_INVALID_OBJECT;
167 }
168
169 host = (struct RtcHost *)handle;
170
171 data = HdfSbufObtainDefaultSize();
172 if (data == NULL) {
173 HDF_LOGE("%s: fail to obtain data", __func__);
174 return HDF_ERR_MALLOC_FAIL;
175 }
176
177 reply = HdfSbufObtainDefaultSize();
178 if (reply == NULL) {
179 HDF_LOGE("%s: fail to obtain reply!", __func__);
180 HdfSbufRecycle(data);
181 return HDF_ERR_MALLOC_FAIL;
182 }
183
184 if (!HdfSbufWriteUint32(data, (uint32_t)alarmIndex)) {
185 HDF_LOGE("%s: write alarmIndex fail!", __func__);
186 ret = HDF_ERR_IO;
187 goto EXIT;
188 }
189
190 service = (struct HdfIoService *)host;
191 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
192 HDF_LOGE("%s: service is invalid", __func__);
193 ret = HDF_ERR_MALLOC_FAIL;
194 goto EXIT;
195 }
196
197 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_READALARM, data, reply);
198 if (ret != HDF_SUCCESS) {
199 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
200 goto EXIT;
201 }
202
203 if (!HdfSbufReadBuffer(reply, (const void **)&temp, &len) || temp == NULL) {
204 HDF_LOGE("%s: read buffer fail", __func__);
205 ret = HDF_ERR_IO;
206 goto EXIT;
207 }
208
209 if (len != sizeof(*time)) {
210 HDF_LOGE("%s: read error, len: %u, size: %zu", __func__, len, sizeof(*time));
211 ret = HDF_FAILURE;
212 goto EXIT;
213 }
214
215 if (memcpy_s(time, sizeof(*time), temp, len) != EOK) {
216 HDF_LOGE("%s: memcpy time fail!", __func__);
217 ret = HDF_ERR_IO;
218 goto EXIT;
219 }
220
221 EXIT:
222 HdfSbufRecycle(data);
223 HdfSbufRecycle(reply);
224 return ret;
225 }
226
RtcWriteAlarm(DevHandle handle,enum RtcAlarmIndex alarmIndex,const struct RtcTime * time)227 int32_t RtcWriteAlarm(DevHandle handle, enum RtcAlarmIndex alarmIndex, const struct RtcTime *time)
228 {
229 int32_t ret;
230 struct RtcHost *host = NULL;
231 struct HdfSBuf *data = NULL;
232 struct HdfIoService *service = NULL;
233
234 if (handle == NULL || time == NULL) {
235 HDF_LOGE("%s: handle or time is NULL.", __func__);
236 return HDF_ERR_INVALID_OBJECT;
237 }
238
239 host = (struct RtcHost *)handle;
240
241 data = HdfSbufObtainDefaultSize();
242 if (data == NULL) {
243 HDF_LOGE("%s: fail to obtain data", __func__);
244 return HDF_ERR_MALLOC_FAIL;
245 }
246
247 if (!HdfSbufWriteUint32(data, (uint32_t)alarmIndex)) {
248 HDF_LOGE("%s: write rtc time fail!", __func__);
249 HdfSbufRecycle(data);
250 return HDF_ERR_IO;
251 }
252
253 if (!HdfSbufWriteBuffer(data, time, sizeof(*time))) {
254 HDF_LOGE("%s: write rtc time fail!", __func__);
255 HdfSbufRecycle(data);
256 return HDF_ERR_IO;
257 }
258
259 service = (struct HdfIoService *)host;
260 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
261 HDF_LOGE("%s: service is invalid", __func__);
262 HdfSbufRecycle(data);
263 return HDF_ERR_MALLOC_FAIL;
264 }
265
266 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_WRITEALARM, data, NULL);
267 if (ret != HDF_SUCCESS) {
268 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
269 HdfSbufRecycle(data);
270 return ret;
271 }
272
273 HdfSbufRecycle(data);
274 return HDF_SUCCESS;
275 }
276
RtcRegisterAlarmCallback(DevHandle handle,enum RtcAlarmIndex alarmIndex,RtcAlarmCallback cb)277 int32_t RtcRegisterAlarmCallback(DevHandle handle, enum RtcAlarmIndex alarmIndex, RtcAlarmCallback cb)
278 {
279 (void)alarmIndex;
280 if (handle == NULL || cb == NULL) {
281 HDF_LOGE("%s: handle or cb is NULL.", __func__);
282 return HDF_ERR_INVALID_OBJECT;
283 }
284
285 return HDF_SUCCESS;
286 }
287
RtcAlarmInterruptEnable(DevHandle handle,enum RtcAlarmIndex alarmIndex,uint8_t enable)288 int32_t RtcAlarmInterruptEnable(DevHandle handle, enum RtcAlarmIndex alarmIndex, uint8_t enable)
289 {
290 int32_t ret;
291 struct RtcHost *host = NULL;
292 struct HdfSBuf *data = NULL;
293 struct HdfIoService *service = NULL;
294
295 if (handle == NULL) {
296 HDF_LOGE("%s: handle is NULL.", __func__);
297 return HDF_ERR_INVALID_OBJECT;
298 }
299
300 host = (struct RtcHost *)handle;
301
302 data = HdfSbufObtainDefaultSize();
303 if (data == NULL) {
304 HDF_LOGE("%s: fail to obtain data", __func__);
305 return HDF_ERR_MALLOC_FAIL;
306 }
307
308 if (!HdfSbufWriteUint32(data, (uint32_t)alarmIndex)) {
309 HDF_LOGE("%s: write alarmIndex fail!", __func__);
310 HdfSbufRecycle(data);
311 return HDF_ERR_IO;
312 }
313
314 if (!HdfSbufWriteUint8(data, enable)) {
315 HDF_LOGE("%s: write enable fail!", __func__);
316 HdfSbufRecycle(data);
317 return HDF_ERR_IO;
318 }
319
320 service = (struct HdfIoService *)host;
321 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
322 HDF_LOGE("%s: service is invalid", __func__);
323 HdfSbufRecycle(data);
324 return HDF_ERR_MALLOC_FAIL;
325 }
326
327 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_ALARMINTERRUPTENABLE, data, NULL);
328 if (ret != HDF_SUCCESS) {
329 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
330 HdfSbufRecycle(data);
331 return ret;
332 }
333
334 HdfSbufRecycle(data);
335 return HDF_SUCCESS;
336 }
337
RtcGetFreq(DevHandle handle,uint32_t * freq)338 int32_t RtcGetFreq(DevHandle handle, uint32_t *freq)
339 {
340 int32_t ret;
341 struct RtcHost *host = NULL;
342 struct HdfSBuf *reply = NULL;
343 struct HdfIoService *service = NULL;
344
345 if (handle == NULL || freq == NULL) {
346 HDF_LOGE("%s: handle or freq is NULL.", __func__);
347 return HDF_ERR_INVALID_OBJECT;
348 }
349
350 host = (struct RtcHost *)handle;
351
352 reply = HdfSbufObtainDefaultSize();
353 if (reply == NULL) {
354 HDF_LOGE("%s: fail to obtain data", __func__);
355 return HDF_ERR_MALLOC_FAIL;
356 }
357
358 service = (struct HdfIoService *)host;
359 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
360 HDF_LOGE("%s: service is invalid", __func__);
361 ret = HDF_ERR_MALLOC_FAIL;
362 goto EXIT;
363 }
364
365 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_GETFREQ, NULL, reply);
366 if (ret != HDF_SUCCESS) {
367 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
368 goto EXIT;
369 }
370
371 if (!HdfSbufReadUint32(reply, freq)) {
372 HDF_LOGE("%s: read buffer fail", __func__);
373 goto EXIT;
374 }
375
376 EXIT:
377 HdfSbufRecycle(reply);
378 return ret;
379 }
380
RtcSetFreq(DevHandle handle,uint32_t freq)381 int32_t RtcSetFreq(DevHandle handle, uint32_t freq)
382 {
383 int32_t ret;
384 struct RtcHost *host = NULL;
385 struct HdfSBuf *data = NULL;
386 struct HdfIoService *service = NULL;
387
388 if (handle == NULL) {
389 HDF_LOGE("%s: handle is NULL.", __func__);
390 return HDF_ERR_INVALID_OBJECT;
391 }
392
393 host = (struct RtcHost *)handle;
394
395 data = HdfSbufObtainDefaultSize();
396 if (data == NULL) {
397 HDF_LOGE("%s: fail to obtain data", __func__);
398 return HDF_ERR_MALLOC_FAIL;
399 }
400
401 if (!HdfSbufWriteUint32(data, freq)) {
402 HDF_LOGE("%s: write freq fail", __func__);
403 HdfSbufRecycle(data);
404 return HDF_ERR_IO;
405 }
406
407 service = (struct HdfIoService *)host;
408 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
409 HDF_LOGE("%s: service is invalid", __func__);
410 HdfSbufRecycle(data);
411 return HDF_ERR_MALLOC_FAIL;
412 }
413
414 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_SETFREQ, data, NULL);
415 if (ret != HDF_SUCCESS) {
416 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
417 HdfSbufRecycle(data);
418 return ret;
419 }
420
421 HdfSbufRecycle(data);
422 return HDF_SUCCESS;
423 }
424
RtcReset(DevHandle handle)425 int32_t RtcReset(DevHandle handle)
426 {
427 int32_t ret;
428 struct RtcHost *host = NULL;
429 struct HdfIoService *service = NULL;
430
431 if (handle == NULL) {
432 HDF_LOGE("%s: handle is NULL", __func__);
433 return HDF_ERR_INVALID_OBJECT;
434 }
435
436 host = (struct RtcHost *)handle;
437
438 service = (struct HdfIoService *)host;
439 if (service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
440 HDF_LOGE("%s: service is invalid", __func__);
441 return HDF_ERR_INVALID_PARAM;
442 }
443
444 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_RESET, NULL, NULL);
445 if (ret != HDF_SUCCESS) {
446 HDF_LOGE("%s: rtc reset fail, ret %d", __func__, ret);
447 return ret;
448 }
449
450 return HDF_SUCCESS;
451 }
452
RtcReadReg(DevHandle handle,uint8_t usrDefIndex,uint8_t * value)453 int32_t RtcReadReg(DevHandle handle, uint8_t usrDefIndex, uint8_t *value)
454 {
455 int32_t ret;
456 struct RtcHost *host = NULL;
457 struct HdfSBuf *data = NULL;
458 struct HdfSBuf *reply = NULL;
459 struct HdfIoService *service = NULL;
460
461 if (handle == NULL || value == NULL) {
462 HDF_LOGE("%s: handle or value is NULL.", __func__);
463 return HDF_ERR_INVALID_OBJECT;
464 }
465
466 host = (struct RtcHost *)handle;
467
468 data = HdfSbufObtainDefaultSize();
469 if (data == NULL) {
470 HDF_LOGE("%s: fail to obtain data", __func__);
471 return HDF_ERR_MALLOC_FAIL;
472 }
473
474 reply = HdfSbufObtainDefaultSize();
475 if (reply == NULL) {
476 HDF_LOGE("%s: fail to obtain reply!", __func__);
477 HdfSbufRecycle(data);
478 return HDF_ERR_MALLOC_FAIL;
479 }
480
481 if (!HdfSbufWriteUint8(data, usrDefIndex)) {
482 HDF_LOGE("%s: write usrDefIndex fail!", __func__);
483 ret = HDF_ERR_IO;
484 goto EXIT;
485 }
486
487 service = (struct HdfIoService *)host;
488 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
489 HDF_LOGE("%s: service is invalid", __func__);
490 ret = HDF_ERR_MALLOC_FAIL;
491 goto EXIT;
492 }
493
494 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_READREG, data, reply);
495 if (ret != HDF_SUCCESS) {
496 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
497 goto EXIT;
498 }
499
500 if (!HdfSbufReadUint8(reply, value)) {
501 HDF_LOGE("%s: read value fail", __func__);
502 ret = HDF_ERR_IO;
503 goto EXIT;
504 }
505
506 EXIT:
507 HdfSbufRecycle(data);
508 HdfSbufRecycle(reply);
509 return ret;
510 }
511
RtcWriteReg(DevHandle handle,uint8_t usrDefIndex,uint8_t value)512 int32_t RtcWriteReg(DevHandle handle, uint8_t usrDefIndex, uint8_t value)
513 {
514 int32_t ret;
515 struct RtcHost *host = NULL;
516 struct HdfSBuf *data = NULL;
517 struct HdfIoService *service = NULL;
518
519 if (handle == NULL) {
520 HDF_LOGE("%s: handle is NULL.", __func__);
521 return HDF_ERR_INVALID_OBJECT;
522 }
523
524 host = (struct RtcHost *)handle;
525
526 data = HdfSbufObtainDefaultSize();
527 if (data == NULL) {
528 HDF_LOGE("%s: fail to obtain data", __func__);
529 return HDF_ERR_MALLOC_FAIL;
530 }
531
532 if (!HdfSbufWriteUint8(data, usrDefIndex)) {
533 HDF_LOGE("%s: write usrDefIndex fail!", __func__);
534 HdfSbufRecycle(data);
535 return HDF_ERR_IO;
536 }
537
538 if (!HdfSbufWriteUint8(data, value)) {
539 HDF_LOGE("%s: write value fail!", __func__);
540 HdfSbufRecycle(data);
541 return HDF_ERR_IO;
542 }
543
544 service = (struct HdfIoService *)host;
545 if (service == NULL || service->dispatcher == NULL || service->dispatcher->Dispatch == NULL) {
546 HDF_LOGE("%s: service is invalid", __func__);
547 HdfSbufRecycle(data);
548 return HDF_ERR_MALLOC_FAIL;
549 }
550
551 ret = service->dispatcher->Dispatch(&service->object, RTC_IO_WRITEREG, data, NULL);
552 if (ret != HDF_SUCCESS) {
553 HDF_LOGE("%s: fail, ret is %d", __func__, ret);
554 HdfSbufRecycle(data);
555 return ret;
556 }
557
558 HdfSbufRecycle(data);
559 return HDF_SUCCESS;
560 }
561