1/*
2 * Copyright (c) 2021 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#include <hdf_log.h>
16#include "audio_internal.h"
17#include "audio_adapter_info_common.h"
18#include "audio_bluetooth_manager.h"
19#include "audio_render.h"
20#include "hitrace_meter.h"
21namespace OHOS::HDI::Audio_Bluetooth {
22/* 1 buffer: 8000(8kHz sample rate) * 2(bytes, PCM_16_BIT) * 1(channel) */
23/* 1 frame: 1024(sample) * 2(bytes, PCM_16_BIT) * 1(channel) */
24constexpr int FRAME_SIZE = 1024;
25
26int32_t PcmBytesToFrames(const struct AudioFrameRenderMode *frameRenderMode, uint64_t bytes, uint32_t *frameCount)
27{
28    if (frameRenderMode == NULL || frameCount == NULL) {
29        return HDF_FAILURE;
30    }
31    uint32_t formatBits = 0;
32    int32_t ret = FormatToBits(frameRenderMode->attrs.format, &formatBits);
33    if (ret != HDF_SUCCESS) {
34        return ret;
35    }
36    uint32_t frameSize = frameRenderMode->attrs.channelCount * (formatBits >> 3); // Bit to byte >> 3
37    if (frameSize == 0) {
38        return HDF_FAILURE;
39    }
40    *frameCount = (uint32_t)bytes / frameSize;
41    return HDF_SUCCESS;
42}
43
44int32_t AudioRenderStart(AudioHandle handle)
45{
46    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
47    if (hwRender == NULL) {
48        return AUDIO_HAL_ERR_INVALID_PARAM;
49    }
50    if (hwRender->renderParam.frameRenderMode.buffer != NULL) {
51        HDF_LOGE("AudioRender already start!");
52        return AUDIO_HAL_ERR_AO_BUSY; // render is busy now
53    }
54
55    HDF_LOGI("%s, StartPlaying", __func__);
56#ifndef A2DP_HDI_SERVICE
57    if (OHOS::Bluetooth::GetPlayingState() == false) {
58        OHOS::Bluetooth::StartPlaying();
59    }
60#endif
61
62    char *buffer = static_cast<char *>(calloc(1, FRAME_DATA));
63    if (buffer == NULL) {
64        HDF_LOGE("Calloc Render buffer Fail!");
65        return AUDIO_HAL_ERR_MALLOC_FAIL;
66    }
67    hwRender->renderParam.frameRenderMode.buffer = buffer;
68    return AUDIO_HAL_SUCCESS;
69}
70
71int32_t AudioRenderStop(AudioHandle handle)
72{
73    HDF_LOGI("AudioRenderStop");
74    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
75    if (hwRender == NULL) {
76        return AUDIO_HAL_ERR_INVALID_PARAM;
77    }
78    if (hwRender->renderParam.frameRenderMode.buffer != NULL) {
79        AudioMemFree(reinterpret_cast<void **>(&hwRender->renderParam.frameRenderMode.buffer));
80    } else {
81        HDF_LOGE("Repeat invalid stop operation!");
82        return AUDIO_HAL_ERR_NOT_SUPPORT;
83    }
84
85    HDF_LOGI("%s, StopPlaying", __func__);
86#ifndef A2DP_HDI_SERVICE
87    if (OHOS::Bluetooth::GetPlayingState() == true) {
88        OHOS::Bluetooth::StopPlaying();
89    }
90#else
91    OHOS::Bluetooth::StopPlaying();
92#endif
93
94    hwRender->renderParam.renderMode.ctlParam.pause = false;
95    return AUDIO_HAL_SUCCESS;
96}
97
98int32_t AudioRenderPause(AudioHandle handle)
99{
100    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
101    if (hwRender == NULL) {
102        return AUDIO_HAL_ERR_INVALID_PARAM;
103    }
104    if (hwRender->renderParam.frameRenderMode.buffer == NULL) {
105        HDF_LOGE("AudioRender already stop!");
106        return AUDIO_HAL_ERR_INTERNAL;
107    }
108    if (hwRender->renderParam.renderMode.ctlParam.pause) {
109        HDF_LOGE("Audio is already pause!");
110        return AUDIO_HAL_ERR_NOT_SUPPORT;
111    }
112
113    HDF_LOGI("%s, SuspendPlaying", __func__);
114#ifndef A2DP_HDI_SERVICE
115    if (OHOS::Bluetooth::GetPlayingState() == true) {
116        OHOS::Bluetooth::SuspendPlaying();
117    }
118#else
119    OHOS::Bluetooth::SuspendPlaying();
120#endif
121
122    hwRender->renderParam.renderMode.ctlParam.pause = true;
123    return AUDIO_HAL_SUCCESS;
124}
125
126int32_t AudioRenderResume(AudioHandle handle)
127{
128    HDF_LOGI("AudioRenderResume");
129    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
130    if (hwRender == NULL) {
131        return AUDIO_HAL_ERR_INVALID_PARAM;
132    }
133    if (!hwRender->renderParam.renderMode.ctlParam.pause) {
134        HDF_LOGE("Audio is already Resume !");
135        return AUDIO_HAL_ERR_NOT_SUPPORT;
136    }
137
138    HDF_LOGI("%s, StartPlaying", __func__);
139#ifndef A2DP_HDI_SERVICE
140    if (OHOS::Bluetooth::GetPlayingState() == false) {
141        OHOS::Bluetooth::StartPlaying();
142    }
143#endif
144
145    hwRender->renderParam.renderMode.ctlParam.pause = false;
146    return AUDIO_HAL_SUCCESS;
147}
148
149int32_t AudioRenderFlush(AudioHandle handle)
150{
151    HDF_LOGI("AudioRenderFlush");
152    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
153    if (hwRender == NULL) {
154        return AUDIO_HAL_ERR_INVALID_PARAM;
155    }
156    return AUDIO_HAL_ERR_NOT_SUPPORT;
157}
158
159int32_t AudioRenderGetFrameSize(AudioHandle handle, uint64_t *size)
160{
161    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
162    const int shift = 3;
163    if (hwRender == NULL || size == NULL) {
164        return AUDIO_HAL_ERR_INVALID_PARAM;
165    }
166    uint32_t channelCount = hwRender->renderParam.frameRenderMode.attrs.channelCount;
167    AudioFormat format = hwRender->renderParam.frameRenderMode.attrs.format;
168    uint32_t formatBits = 0;
169    int32_t ret = FormatToBits(format, &formatBits);
170    if (ret != AUDIO_HAL_SUCCESS) {
171        return ret;
172    }
173    *size = FRAME_SIZE * channelCount * (formatBits >> shift);
174    return AUDIO_HAL_SUCCESS;
175}
176
177int32_t AudioRenderGetFrameCount(AudioHandle handle, uint64_t *count)
178{
179    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
180    if (hwRender == NULL || count == NULL) {
181        return AUDIO_HAL_ERR_INVALID_PARAM;
182    }
183    *count = hwRender->renderParam.frameRenderMode.frames;
184    return AUDIO_HAL_SUCCESS;
185}
186
187int32_t AudioRenderSetSampleAttributes(AudioHandle handle, const struct AudioSampleAttributes *attrs)
188{
189    (void)attrs;
190    return AUDIO_HAL_SUCCESS;
191}
192
193int32_t AudioRenderGetSampleAttributes(AudioHandle handle, struct AudioSampleAttributes *attrs)
194{
195    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
196    if (hwRender == NULL || attrs == NULL) {
197        return AUDIO_HAL_ERR_INVALID_PARAM;
198    }
199    attrs->format = hwRender->renderParam.frameRenderMode.attrs.format;
200    attrs->sampleRate = hwRender->renderParam.frameRenderMode.attrs.sampleRate;
201    attrs->channelCount = hwRender->renderParam.frameRenderMode.attrs.channelCount;
202    attrs->type = hwRender->renderParam.frameRenderMode.attrs.type;
203    attrs->interleaved = hwRender->renderParam.frameRenderMode.attrs.interleaved;
204    attrs->period = hwRender->renderParam.frameRenderMode.attrs.period;
205    attrs->frameSize = hwRender->renderParam.frameRenderMode.attrs.frameSize;
206    attrs->isBigEndian = hwRender->renderParam.frameRenderMode.attrs.isBigEndian;
207    attrs->isSignedData = hwRender->renderParam.frameRenderMode.attrs.isSignedData;
208    attrs->startThreshold = hwRender->renderParam.frameRenderMode.attrs.startThreshold;
209    attrs->stopThreshold = hwRender->renderParam.frameRenderMode.attrs.stopThreshold;
210    attrs->silenceThreshold = hwRender->renderParam.frameRenderMode.attrs.silenceThreshold;
211    return AUDIO_HAL_SUCCESS;
212}
213
214int32_t AudioRenderGetCurrentChannelId(AudioHandle handle, uint32_t *channelId)
215{
216    HDF_LOGI("AudioRenderGetCurrentChannelId");
217    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(handle);
218    if (hwRender == NULL || channelId == NULL) {
219        return AUDIO_HAL_ERR_INVALID_PARAM;
220    }
221    *channelId = hwRender->renderParam.frameRenderMode.attrs.channelCount;
222    return AUDIO_HAL_SUCCESS;
223}
224
225int32_t AudioRenderCheckSceneCapability(AudioHandle handle, const struct AudioSceneDescriptor *scene,
226                                        bool *supported)
227{
228    (void)scene;
229    (void)supported;
230    HDF_LOGI("AudioRenderCheckSceneCapability");
231    return AUDIO_HAL_SUCCESS;
232}
233
234int32_t AudioRenderSelectScene(AudioHandle handle, const struct AudioSceneDescriptor *scene)
235{
236    (void)scene;
237    return AUDIO_HAL_SUCCESS;
238}
239
240int32_t AudioRenderSetMute(AudioHandle handle, bool mute)
241{
242    (void)mute;
243    return AUDIO_HAL_SUCCESS;
244}
245
246int32_t AudioRenderGetMute(AudioHandle handle, bool *mute)
247{
248    (void)mute;
249    return AUDIO_HAL_SUCCESS;
250}
251
252int32_t AudioRenderSetVolume(AudioHandle handle, float volume)
253{
254    (void)volume;
255    return AUDIO_HAL_SUCCESS;
256}
257
258int32_t AudioRenderGetVolume(AudioHandle handle, float *volume)
259{
260    (void)volume;
261    return AUDIO_HAL_SUCCESS;
262}
263
264int32_t AudioRenderGetGainThreshold(AudioHandle handle, float *min, float *max)
265{
266    (void)min;
267    (void)max;
268    HDF_LOGI("AudioRenderGetGainThreshold");
269    return AUDIO_HAL_SUCCESS;
270}
271
272int32_t AudioRenderGetGain(AudioHandle handle, float *gain)
273{
274    (void)gain;
275    HDF_LOGI("AudioRenderGetGain");
276    return AUDIO_HAL_SUCCESS;
277}
278
279int32_t AudioRenderSetGain(AudioHandle handle, float gain)
280{
281    (void)gain;
282    HDF_LOGI("AudioRenderSetGain");
283    return AUDIO_HAL_SUCCESS;
284}
285
286int32_t AudioRenderGetLatency(struct AudioRender *render, uint32_t *ms)
287{
288    HITRACE_METER_NAME(HITRACE_TAG_BLUETOOTH, "BtAudioRenderGetLatency");
289    struct AudioHwRender *impl = reinterpret_cast<struct AudioHwRender *>(render);
290    if (impl == NULL || ms == NULL) {
291        return AUDIO_HAL_ERR_INVALID_PARAM;
292    }
293    uint32_t byteRate = impl->renderParam.frameRenderMode.byteRate;
294    uint32_t periodSize = impl->renderParam.frameRenderMode.periodSize;
295    uint32_t periodCount = impl->renderParam.frameRenderMode.periodCount;
296    if (byteRate == 0) {
297        return AUDIO_HAL_ERR_INTERNAL;
298    }
299    uint32_t periodMs = (periodCount * periodSize * 1000) / byteRate;
300    *ms = periodMs;
301#ifdef A2DP_HDI_SERVICE
302    uint32_t latency = 0;
303    OHOS::Bluetooth::GetLatency(latency);
304    *ms = latency;
305#endif
306    return AUDIO_HAL_SUCCESS;
307}
308
309int32_t AudioRenderRenderFramSplit(struct AudioHwRender *hwRender)
310{
311    return HDF_SUCCESS;
312}
313
314int32_t AudioRenderRenderFrame(struct AudioRender *render, const void *frame,
315                               uint64_t requestBytes, uint64_t *replyBytes)
316{
317    HITRACE_METER_FMT(HITRACE_TAG_BLUETOOTH, "renderFrame:%d", requestBytes);
318    HDF_LOGD("AudioRenderRenderFrame");
319    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(render);
320    if (hwRender == NULL || frame == NULL || replyBytes == NULL ||
321        hwRender->renderParam.frameRenderMode.buffer == NULL) {
322        HDF_LOGE("Render Frame Paras is NULL!");
323        return AUDIO_HAL_ERR_INVALID_PARAM;
324    }
325    if (FRAME_DATA < requestBytes) {
326        HDF_LOGE("Out of FRAME_DATA size!");
327        return AUDIO_HAL_ERR_INTERNAL;
328    }
329    int32_t ret = memcpy_s(hwRender->renderParam.frameRenderMode.buffer, FRAME_DATA, frame, (uint32_t)requestBytes);
330    if (ret != EOK) {
331        HDF_LOGE("memcpy_s fail");
332        return AUDIO_HAL_ERR_INTERNAL;
333    }
334    hwRender->renderParam.frameRenderMode.bufferSize = requestBytes;
335    uint32_t frameCount = 0;
336    ret = PcmBytesToFrames(&hwRender->renderParam.frameRenderMode, requestBytes, &frameCount);
337    if (ret != AUDIO_HAL_SUCCESS) {
338        return ret;
339    }
340    hwRender->renderParam.frameRenderMode.bufferFrameSize = (uint64_t)frameCount;
341    if (AudioRenderRenderFramSplit(hwRender) < 0) {
342        return AUDIO_HAL_ERR_INTERNAL;
343    }
344    *replyBytes = requestBytes;
345    hwRender->renderParam.frameRenderMode.frames += hwRender->renderParam.frameRenderMode.bufferFrameSize;
346    if (hwRender->renderParam.frameRenderMode.attrs.sampleRate == 0) {
347        HDF_LOGE("Divisor cannot be zero!");
348        return AUDIO_HAL_ERR_INTERNAL;
349    }
350    if (TimeToAudioTimeStamp(hwRender->renderParam.frameRenderMode.bufferFrameSize,
351        &hwRender->renderParam.frameRenderMode.time,
352        hwRender->renderParam.frameRenderMode.attrs.sampleRate) == HDF_FAILURE) {
353        HDF_LOGE("Frame is NULL");
354        return AUDIO_HAL_ERR_INTERNAL;
355    }
356
357    LOGV("%s, WriteFrame", __func__);
358    const uint8_t *data = reinterpret_cast<const uint8_t *>(frame);
359    AudioSampleAttributes *attrs = &hwRender->renderParam.frameRenderMode.attrs;
360    return OHOS::Bluetooth::WriteFrame(data, static_cast<uint32_t>(requestBytes), attrs);
361}
362
363int32_t AudioRenderGetRenderPosition(struct AudioRender *render, uint64_t *frames, struct AudioTimeStamp *time)
364{
365    struct AudioHwRender *impl = reinterpret_cast<struct AudioHwRender *>(render);
366    if (impl == NULL || frames == NULL || time == NULL) {
367        return AUDIO_HAL_ERR_INVALID_PARAM;
368    }
369    *frames = impl->renderParam.frameRenderMode.frames;
370    *time = impl->renderParam.frameRenderMode.time;
371    return AUDIO_HAL_SUCCESS;
372}
373
374int32_t AudioRenderSetRenderSpeed(struct AudioRender *render, float speed)
375{
376    (void)speed;
377    HDF_LOGI("AudioRenderSetRenderSpeed");
378    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(render);
379    if (hwRender == NULL) {
380        return AUDIO_HAL_ERR_INVALID_PARAM;
381    }
382    return AUDIO_HAL_ERR_NOT_SUPPORT;
383}
384
385int32_t AudioRenderGetRenderSpeed(struct AudioRender *render, float *speed)
386{
387    HDF_LOGI("AudioRenderGetRenderSpeed");
388    struct AudioHwRender *hwRender = reinterpret_cast<struct AudioHwRender *>(render);
389    if (hwRender == NULL || speed == NULL) {
390        return AUDIO_HAL_ERR_INVALID_PARAM;
391    }
392    return AUDIO_HAL_ERR_NOT_SUPPORT;
393}
394
395int32_t AudioRenderSetChannelMode(struct AudioRender *render, AudioChannelMode mode)
396{
397    (void)render;
398    HDF_LOGI("AudioRenderSetChannelMode");
399    return AUDIO_HAL_SUCCESS;
400}
401
402int32_t AudioRenderGetChannelMode(struct AudioRender *render, AudioChannelMode *mode)
403{
404    (void)render;
405    HDF_LOGI("AudioRenderGetChannelMode");
406    return AUDIO_HAL_SUCCESS;
407}
408
409int32_t SetValue(struct ExtraParams mExtraParams, struct AudioHwRender *render)
410{
411    if (render == NULL) {
412        return HDF_FAILURE;
413    }
414    if (mExtraParams.route != -1) {
415        render->renderParam.renderMode.hwInfo.pathroute = (PathRoute)mExtraParams.route;
416    }
417    if (mExtraParams.format != -1) {
418        render->renderParam.frameRenderMode.attrs.format = (AudioFormat)mExtraParams.format;
419    }
420    if (mExtraParams.channels != 0) {
421        render->renderParam.frameRenderMode.attrs.channelCount = mExtraParams.channels;
422    }
423    if (mExtraParams.flag) {
424        render->renderParam.frameRenderMode.frames = mExtraParams.frames;
425    }
426    if (mExtraParams.sampleRate != 0) {
427        render->renderParam.frameRenderMode.attrs.sampleRate = mExtraParams.sampleRate;
428    }
429#ifdef A2DP_HDI_SERVICE
430    if (mExtraParams.audioStreamCtl == 1) {
431        HDF_LOGI("SetValue, try to suspendPlaying");
432        OHOS::Bluetooth::SuspendPlaying();
433    }
434#endif
435    return HDF_SUCCESS;
436}
437
438int32_t AudioRenderSetExtraParams(AudioHandle handle, const char *keyValueList)
439{
440    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
441    if (render == NULL || keyValueList == NULL) {
442        return AUDIO_HAL_ERR_INVALID_PARAM;
443    }
444    int32_t count = 0;
445    int32_t sumOk = 0;
446    struct ExtraParams mExtraParams;
447    if (AudioSetExtraParams(keyValueList, &count, &mExtraParams, &sumOk) < 0) {
448        return AUDIO_HAL_ERR_INTERNAL;
449    }
450    if (count != 0 && sumOk == count) {
451        SetValue(mExtraParams, render);
452        return AUDIO_HAL_SUCCESS;
453    } else {
454        return AUDIO_HAL_ERR_INTERNAL;
455    }
456}
457
458int32_t AudioRenderGetExtraParams(AudioHandle handle, char *keyValueList, int32_t listLenth)
459{
460    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
461    if (render == NULL || keyValueList == NULL || listLenth <= 0) {
462        return AUDIO_HAL_ERR_INVALID_PARAM;
463    }
464    int32_t bufferSize = strlen(ROUTE_SAMPLE) + strlen(FORMAT_SAMPLE) + strlen(CHANNELS_SAMPLE)
465                    + strlen(FRAME_COUNT_SAMPLE) + strlen(SAMPLING_RATE_SAMPLE) + 1;
466    if (listLenth < bufferSize) {
467        return AUDIO_HAL_ERR_INTERNAL;
468    }
469    int32_t ret = AddElementToList(keyValueList, listLenth, AUDIO_ATTR_PARAM_ROUTE,
470        &render->renderParam.renderMode.hwInfo.pathroute);
471    if (ret < 0) {
472        return AUDIO_HAL_ERR_INTERNAL;
473    }
474    ret = AddElementToList(keyValueList, listLenth, AUDIO_ATTR_PARAM_FORMAT,
475        &render->renderParam.frameRenderMode.attrs.format);
476    if (ret < 0) {
477        return AUDIO_HAL_ERR_INTERNAL;
478    }
479    ret = AddElementToList(keyValueList, listLenth, AUDIO_ATTR_PARAM_CHANNELS,
480        &render->renderParam.frameRenderMode.attrs.channelCount);
481    if (ret < 0) {
482        return AUDIO_HAL_ERR_INTERNAL;
483    }
484    ret = AddElementToList(keyValueList, listLenth, AUDIO_ATTR_PARAM_FRAME_COUNT,
485        &render->renderParam.frameRenderMode.frames);
486    if (ret < 0) {
487        return AUDIO_HAL_ERR_INTERNAL;
488    }
489    ret = AddElementToList(keyValueList, listLenth, AUDIO_ATTR_PARAM_SAMPLING_RATE,
490        &render->renderParam.frameRenderMode.attrs.sampleRate);
491    if (ret < 0) {
492        return AUDIO_HAL_ERR_INTERNAL;
493    }
494    return AUDIO_HAL_SUCCESS;
495}
496
497int32_t AudioRenderReqMmapBuffer(AudioHandle handle, int32_t reqSize, struct AudioMmapBufferDescriptor *desc)
498{
499    (void)desc;
500    HDF_LOGI("AudioRenderReqMmapBuffer Success!");
501    return AUDIO_HAL_SUCCESS;
502}
503
504int32_t AudioRenderGetMmapPosition(AudioHandle handle, uint64_t *frames, struct AudioTimeStamp *time)
505{
506    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
507    if (render == NULL || frames == NULL || time == NULL) {
508        return AUDIO_HAL_ERR_INVALID_PARAM;
509    }
510    *frames = render->renderParam.frameRenderMode.frames;
511    render->renderParam.frameRenderMode.time.tvSec = (int64_t)render->renderParam.frameRenderMode.frames /
512                                       (int64_t)render->renderParam.frameRenderMode.attrs.sampleRate;
513    int64_t lastBufFrames = render->renderParam.frameRenderMode.frames %
514                        ((int64_t)render->renderParam.frameRenderMode.attrs.sampleRate);
515    render->renderParam.frameRenderMode.time.tvNSec =
516        (lastBufFrames * SEC_TO_NSEC) / ((int64_t)render->renderParam.frameRenderMode.attrs.sampleRate);
517    *time = render->renderParam.frameRenderMode.time;
518    return AUDIO_HAL_SUCCESS;
519}
520
521int32_t AudioRenderTurnStandbyMode(AudioHandle handle)
522{
523    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
524    if (render == NULL) {
525        return AUDIO_HAL_ERR_INVALID_PARAM;
526    }
527    int32_t ret = AudioRenderStop((AudioHandle)render);
528    if (ret < 0) {
529        return AUDIO_HAL_ERR_INTERNAL;
530    }
531    return AUDIO_HAL_SUCCESS;
532}
533
534int32_t AudioRenderAudioDevDump(AudioHandle handle, int32_t range, int32_t fd)
535{
536    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
537    if (render == NULL) {
538        return AUDIO_HAL_ERR_INVALID_PARAM;
539    }
540    dprintf(fd, "%s%d\n", "Number of errors: ", render->errorLog.totalErrors);
541    if (range < RANGE_MIN - 1 || range > RANGE_MAX) {
542        dprintf(fd, "%s\n", "Out of range, invalid output");
543        return AUDIO_HAL_SUCCESS;
544    }
545    uint32_t mSize = render->errorLog.iter;
546    if (range < RANGE_MIN) {
547        dprintf(fd, "%-5s  %-10s  %s\n", "count", "errorCode", "Time");
548        for (uint32_t i = 0; i < mSize; i++) {
549            dprintf(fd, FORMAT_TWO, render->errorLog.errorDump[i].count + 1,
550                    render->errorLog.errorDump[i].errorCode,
551                    render->errorLog.errorDump[i].currentTime);
552        }
553    } else {
554        dprintf(fd, "%-5s  %-10s  %-20s  %-15s  %s\n", "count", "errorCode", "frames", "fail reason", "Time");
555        for (uint32_t i = 0; i < mSize; i++) {
556            dprintf(fd, FORMAT_ONE, render->errorLog.errorDump[i].count + 1,
557                    render->errorLog.errorDump[i].errorCode,
558                    render->errorLog.errorDump[i].frames,
559                    render->errorLog.errorDump[i].reason,
560                    render->errorLog.errorDump[i].currentTime);
561        }
562    }
563    return AUDIO_HAL_SUCCESS;
564}
565int32_t CallbackProcessing(AudioHandle handle, AudioCallbackType callBackType)
566{
567    struct AudioHwRender *render = reinterpret_cast<struct AudioHwRender *>(handle);
568    if (render == NULL) {
569        HDF_LOGI("Unregistered callback.\n");
570        return HDF_FAILURE;
571    }
572    if (render->renderParam.frameRenderMode.callback == NULL) {
573        return HDF_FAILURE;
574    }
575    bool isCallBack = true;
576    switch (callBackType) {
577        case AUDIO_NONBLOCK_WRITE_COMPLETED:
578        case AUDIO_DRAIN_COMPLETED:
579        case AUDIO_FLUSH_COMPLETED:
580        case AUDIO_RENDER_FULL:
581        case AUDIO_ERROR_OCCUR:
582            isCallBack = true;
583            break;
584        default:
585            isCallBack = false;
586            break;
587    }
588    if (!isCallBack) {
589        HDF_LOGI("No callback processing is required.\n");
590        return HDF_ERR_NOT_SUPPORT;
591    }
592    render->renderParam.frameRenderMode.callback(callBackType, NULL, render->renderParam.frameRenderMode.cookie);
593    return HDF_SUCCESS;
594}
595
596int32_t AudioRenderRegCallback(struct AudioRender *render, RenderCallback callback, void *cookie)
597{
598    struct AudioHwRender *pRender = reinterpret_cast<struct AudioHwRender *>(render);
599    if (pRender == NULL) {
600        return AUDIO_HAL_ERR_INVALID_PARAM;
601    }
602    pRender->renderParam.frameRenderMode.callback = callback;
603    pRender->renderParam.frameRenderMode.cookie = cookie;
604    return AUDIO_HAL_SUCCESS;
605}
606
607int32_t AudioRenderDrainBuffer(struct AudioRender *render, AudioDrainNotifyType *type)
608{
609    struct AudioHwRender *pRender = reinterpret_cast<struct AudioHwRender *>(render);
610    if (pRender == NULL || type == NULL) {
611        return AUDIO_HAL_ERR_INVALID_PARAM;
612    }
613    return AUDIO_HAL_ERR_NOT_SUPPORT;
614}
615}