• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 
16 /**
17  * @addtogroup Audio
18  * @{
19  *
20  * @brief Defines audio-related APIs, including custom data types and functions for loading drivers,
21  * accessing a driver adapter, and rendering and capturing audios.
22  *
23  * @since 1.0
24  * @version 1.0
25  */
26 
27 /**
28  * @file audio_adapter.h
29  *
30  * @brief Declares APIs for operations related to the audio adapter.
31  *
32  * @since 1.0
33  * @version 1.0
34  */
35 
36 #include "audio_hdi_common.h"
37 
38 #define SREREO_CHANNEL 2
39 #define MONO_CHANNEL   1
40 #define AUDIO_CHANNELCOUNT 2
41 
42 using namespace std;
43 
44 static int g_frameStatus = 1;
45 static int g_writeCompleted = 0;
46 static int g_renderFull = 0;
47 static int g_flushCompleted = 0;
48 const int32_t AUDIO_CAPTURE_CHANNELCOUNT = 1;
49 const int32_t SILENCE_THRESHOLD = 16 * 1024;
50 namespace OHOS {
51 namespace Audio {
52 
InitAttrsCommon(struct AudioSampleAttributes & attrs)53 void InitAttrsCommon(struct AudioSampleAttributes &attrs)
54 {
55     /* Initialization of audio parameters for playback */
56     attrs.sampleRate = SAMPLE_RATE_48000;
57 }
58 
InitAttrs(struct AudioSampleAttributes & attrs)59 void InitAttrs(struct AudioSampleAttributes &attrs)
60 {
61     attrs.sampleRate = SAMPLERATE;
62     attrs.format = AUDIO_FORMAT_PCM_16_BIT;
63     attrs.channelCount = CHANNELCOUNT;
64     attrs.interleaved = 0;
65     attrs.type = AUDIO_IN_MEDIA;
66     attrs.period = DEEP_BUFFER_RENDER_PERIOD_SIZE;
67     attrs.frameSize = PCM_16_BIT * CHANNELCOUNT / MOVE_LEFT_NUM;
68     attrs.isBigEndian = false;
69     attrs.isSignedData = true;
70     attrs.startThreshold = DEEP_BUFFER_RENDER_PERIOD_SIZE / (PCM_16_BIT * attrs.channelCount / MOVE_LEFT_NUM);
71     attrs.stopThreshold = INT_32_MAX;
72     attrs.silenceThreshold = BUFFER_LENTH;
73 }
74 
InitAttrsRender(struct AudioSampleAttributes & attrs)75 void InitAttrsRender(struct AudioSampleAttributes &attrs)
76 {
77     InitAttrsCommon(attrs);
78     attrs.format = AUDIO_FORMAT_PCM_32_BIT;
79     attrs.channelCount = AUDIO_CHANNELCOUNT;
80     attrs.interleaved = 1;
81     attrs.type = AUDIO_IN_MEDIA;
82     attrs.silenceThreshold = 0;
83 }
84 
InitAttrsCapture(struct AudioSampleAttributes & attrs)85 void InitAttrsCapture(struct AudioSampleAttributes &attrs)
86 {
87     InitAttrsCommon(attrs);
88     attrs.format = AUDIO_FORMAT_PCM_16_BIT;
89     attrs.channelCount = AUDIO_CAPTURE_CHANNELCOUNT;
90     attrs.silenceThreshold = SILENCE_THRESHOLD;
91 }
92 
InitAttrsUpdate(struct AudioSampleAttributes & attrs,int format,uint32_t channelCount,uint32_t sampleRate,uint32_t silenceThreshold)93 void InitAttrsUpdate(struct AudioSampleAttributes &attrs, int format, uint32_t channelCount,
94     uint32_t sampleRate, uint32_t silenceThreshold)
95 {
96 #ifdef FEATURE_SMALL_DEVICE
97     InitAttrs(attrs);
98 #else
99     InitAttrsRender(attrs);
100 #endif
101     attrs.format = (enum AudioFormat)format;
102     attrs.sampleRate = sampleRate;
103     attrs.channelCount = channelCount;
104     attrs.silenceThreshold = silenceThreshold;
105 }
AudioRenderSetGetSampleAttributes(struct AudioSampleAttributes attrs,struct AudioSampleAttributes & attrsValue,struct AudioRender * render)106 int32_t AudioRenderSetGetSampleAttributes(struct AudioSampleAttributes attrs, struct AudioSampleAttributes &attrsValue,
107     struct AudioRender *render)
108 {
109     int32_t ret = -1;
110     if (render == nullptr) {
111         return HDF_ERR_INVALID_PARAM;
112     }
113     ret = render->attr.SetSampleAttributes(render, &attrs);
114     if (ret < 0) {
115         return ret;
116     }
117     ret = render->attr.GetSampleAttributes(render, &attrsValue);
118     if (ret < 0) {
119         return ret;
120     }
121     return HDF_SUCCESS;
122 }
AudioCaptureSetGetSampleAttributes(struct AudioSampleAttributes attrs,struct AudioSampleAttributes & attrsValue,struct AudioCapture * capture)123 int32_t AudioCaptureSetGetSampleAttributes(struct AudioSampleAttributes attrs, struct AudioSampleAttributes &attrsValue,
124     struct AudioCapture *capture)
125 {
126     int32_t ret = -1;
127     if (capture == nullptr) {
128         return HDF_ERR_INVALID_PARAM;
129     }
130     ret = capture->attr.SetSampleAttributes(capture, &attrs);
131     if (ret < 0) {
132         return ret;
133     }
134     ret = capture->attr.GetSampleAttributes(capture, &attrsValue);
135     if (ret < 0) {
136         return ret;
137     }
138     return HDF_SUCCESS;
139 }
140 
StringToInt(std::string flag)141 uint32_t StringToInt(std::string flag)
142 {
143     uint32_t temp = flag[0];
144     for (int i = flag.size() - 1; i >= 0; i--) {
145         temp <<= MOVE_LEFT_NUM;
146         temp += flag[i];
147     }
148     return temp;
149 }
150 
InitDevDesc(struct AudioDeviceDescriptor & devDesc,const uint32_t portId,int pins)151 int32_t InitDevDesc(struct AudioDeviceDescriptor &devDesc, const uint32_t portId, int pins)
152 {
153     devDesc.portId = portId;
154     devDesc.pins = (enum AudioPortPin)pins;
155     devDesc.desc = nullptr;
156     return HDF_SUCCESS;
157 }
158 
SwitchAdapter(struct AudioAdapterDescriptor * descs,const std::string & adapterNameCase,int portFlag,struct AudioPort * & audioPort,int size)159 int32_t SwitchAdapter(struct AudioAdapterDescriptor *descs, const std::string &adapterNameCase,
160     int portFlag, struct AudioPort *&audioPort, int size)
161 {
162     if (descs == nullptr || size > ADAPTER_COUNT) {
163         return HDF_FAILURE;
164     }
165 
166     for (int index = 0; index < size; index++) {
167         struct AudioAdapterDescriptor *desc = &descs[index];
168         if (desc == nullptr || desc->adapterName == nullptr) {
169             continue;
170         }
171         if (strcmp(desc->adapterName, adapterNameCase.c_str())) {
172             continue;
173         }
174         for (uint32_t port = 0; port < desc->portNum; port++) {
175             if (desc->ports[port].dir == portFlag) {
176                 audioPort = &desc->ports[port];
177                 return index;
178             }
179         }
180     }
181     return HDF_FAILURE;
182 }
183 
PcmFormatToBits(int format)184 uint32_t PcmFormatToBits(int format)
185 {
186     switch (format) {
187         case AUDIO_FORMAT_PCM_8_BIT:
188             return PCM_8_BIT;
189         case AUDIO_FORMAT_PCM_16_BIT:
190             return PCM_16_BIT;
191         case AUDIO_FORMAT_PCM_24_BIT:
192             return PCM_24_BIT;
193         case AUDIO_FORMAT_PCM_32_BIT:
194             return PCM_32_BIT;
195         default:
196             return PCM_16_BIT;
197     }
198 }
199 
PcmFramesToBytes(const struct AudioSampleAttributes attrs)200 uint32_t PcmFramesToBytes(const struct AudioSampleAttributes attrs)
201 {
202     if (attrs.channelCount < MONO_CHANNEL || attrs.channelCount > SREREO_CHANNEL) {
203         return 0;
204     }
205     uint32_t formatBits = PcmFormatToBits(attrs.format);
206     if (formatBits < PCM_8_BIT || formatBits > PCM_32_BIT) {
207         return 0;
208     }
209     uint32_t ret = FRAME_SIZE * (attrs.channelCount) * (formatBits >> MOVE_RIGHT_NUM);
210     return ret;
211 }
212 
WavHeadAnalysis(struct AudioHeadInfo & wavHeadInfo,FILE * file,struct AudioSampleAttributes & attrs)213 int32_t WavHeadAnalysis(struct AudioHeadInfo &wavHeadInfo, FILE *file, struct AudioSampleAttributes &attrs)
214 {
215     size_t ret = 0;
216     if (file == nullptr) {
217         return HDF_FAILURE;
218     }
219     ret = fread(&wavHeadInfo, sizeof(wavHeadInfo), 1, file);
220     if (ret != 1) {
221         return HDF_FAILURE;
222     }
223     uint32_t audioRiffId = StringToInt(AUDIO_RIFF);
224     uint32_t audioFileFmt = StringToInt(AUDIO_WAVE);
225     uint32_t audioDataId = StringToInt(AUDIO_DATA);
226     if (wavHeadInfo.testFileRiffId != audioRiffId || wavHeadInfo.testFileFmt != audioFileFmt ||
227         wavHeadInfo.dataId != audioDataId) {
228         return HDF_FAILURE;
229         }
230     attrs.channelCount = wavHeadInfo.audioChannelNum;
231     attrs.sampleRate = wavHeadInfo.audioSampleRate;
232     switch (wavHeadInfo.audioBitsPerSample) {
233         case PCM_8_BIT: {
234             attrs.format = AUDIO_FORMAT_PCM_8_BIT;
235             break;
236         }
237         case PCM_16_BIT: {
238             attrs.format = AUDIO_FORMAT_PCM_16_BIT;
239             break;
240         }
241         case PCM_24_BIT: {
242             attrs.format = AUDIO_FORMAT_PCM_24_BIT;
243             break;
244         }
245         case PCM_32_BIT: {
246             attrs.format = AUDIO_FORMAT_PCM_32_BIT;
247             break;
248         }
249         default:
250             return HDF_FAILURE;
251     }
252     return HDF_SUCCESS;
253 }
GetAdapters(TestAudioManager * manager,struct AudioAdapterDescriptor ** descs,int & size)254 int32_t GetAdapters(TestAudioManager *manager, struct AudioAdapterDescriptor **descs, int &size)
255 {
256     int32_t ret = -1;
257     if (descs == nullptr) {
258         return HDF_ERR_INVALID_PARAM;
259     }
260     ret = manager->GetAllAdapters(manager, descs, &size);
261     if (ret < 0) {
262         return ret;
263     }
264     if (*descs == nullptr) {
265         return HDF_FAILURE;
266     }
267     return HDF_SUCCESS;
268 }
269 
GetLoadAdapter(TestAudioManager * manager,int portType,const std::string & adapterName,struct AudioAdapter ** adapter,struct AudioPort * & audioPort)270 int32_t GetLoadAdapter(TestAudioManager *manager, int portType,
271     const std::string &adapterName, struct AudioAdapter **adapter, struct AudioPort *&audioPort)
272 {
273     int32_t ret = -1;
274     int size = 0;
275     struct AudioAdapterDescriptor *desc = nullptr;
276     struct AudioAdapterDescriptor *descs = nullptr;
277     if (adapter == nullptr) {
278         return HDF_ERR_INVALID_PARAM;
279     }
280     ret = GetAdapters(manager, &descs, size);
281     if (ret < 0) {
282         return ret;
283     }
284     if (descs == nullptr) {
285         return HDF_FAILURE;
286     }
287 
288     int index = SwitchAdapter(descs, adapterName, portType, audioPort, size);
289     if (index < 0) {
290         return HDF_FAILURE;
291     }
292     desc = &descs[index];
293     if (desc == nullptr) {
294         return HDF_ERR_INVALID_PARAM;
295     }
296     ret = manager->LoadAdapter(manager, desc, adapter);
297     if (ret < 0) {
298         return ret;
299     }
300     if (*adapter == nullptr) {
301         return HDF_FAILURE;
302     }
303     return HDF_SUCCESS;
304 }
305 
AudioCreateRender(TestAudioManager * manager,int pins,const std::string & adapterName,struct AudioAdapter ** adapter,struct AudioRender ** render)306 int32_t AudioCreateRender(TestAudioManager *manager, int pins, const std::string &adapterName,
307     struct AudioAdapter **adapter, struct AudioRender **render)
308 {
309     int32_t ret = -1;
310     struct AudioSampleAttributes attrs = {};
311     struct AudioDeviceDescriptor devDesc = {};
312     struct AudioPort *renderPort = nullptr;
313     if (adapter == nullptr || render == nullptr) {
314         return HDF_ERR_INVALID_PARAM;
315     }
316     ret = GetLoadAdapter(manager, PORT_OUT, adapterName, adapter, renderPort);
317     if (ret < 0) {
318         return ret;
319     }
320     if (*adapter == nullptr || (*adapter)->CreateRender == nullptr) {
321         return HDF_FAILURE;
322     }
323 #ifdef FEATURE_SMALL_DEVICE
324     InitAttrs(attrs);
325 #else
326     InitAttrsRender(attrs);
327 #endif
328     InitDevDesc(devDesc, renderPort->portId, pins);
329     ret = (*adapter)->CreateRender(*adapter, &devDesc, &attrs, render);
330     if (ret < 0) {
331         manager->UnloadAdapter(manager, *adapter);
332         return ret;
333     }
334     if (*render == nullptr) {
335         manager->UnloadAdapter(manager, *adapter);
336         return HDF_FAILURE;
337     }
338     return HDF_SUCCESS;
339 }
340 
AudioCreateStartRender(TestAudioManager * manager,struct AudioRender ** render,struct AudioAdapter ** adapter,const std::string & adapterName)341 int32_t AudioCreateStartRender(TestAudioManager *manager, struct AudioRender **render, struct AudioAdapter **adapter,
342     const std::string &adapterName)
343 {
344     int32_t ret = -1;
345 
346     if (adapter == nullptr || render == nullptr) {
347         return HDF_ERR_INVALID_PARAM;
348     }
349     ret = AudioCreateRender(manager, PIN_OUT_SPEAKER, adapterName, adapter, render);
350     if (ret < 0) {
351         return ret;
352     }
353     if (*render == nullptr || *adapter == nullptr) {
354         return HDF_FAILURE;
355     }
356     ret = AudioRenderStartAndOneFrame(*render);
357     if (ret < 0) {
358         (*adapter)->DestroyRender(*adapter, *render);
359         manager->UnloadAdapter(manager, *adapter);
360         return ret;
361     }
362     return HDF_SUCCESS;
363 }
364 
AudioRenderStartAndOneFrame(struct AudioRender * render)365 int32_t AudioRenderStartAndOneFrame(struct AudioRender *render)
366 {
367     int32_t ret = -1;
368     char *frame = nullptr;
369     uint64_t numRead = 0;
370     uint64_t replyBytes = 0;
371     if (render == nullptr || render->control.Start == nullptr || render->RenderFrame == nullptr) {
372         return HDF_ERR_INVALID_PARAM;
373     }
374     ret = render->control.Start((AudioHandle)render);
375     if (ret) {
376         return ret;
377     }
378     ret = RenderFramePrepare(AUDIO_FILE, frame, numRead);
379     if (ret < 0) {
380         if (frame != nullptr) {
381             free(frame);
382             frame = nullptr;
383         }
384         return HDF_FAILURE;
385     }
386     ret = render->RenderFrame(render, frame, numRead, &replyBytes);
387     if (ret < 0) {
388         if (frame != nullptr) {
389             free(frame);
390             frame = nullptr;
391         }
392         return ret;
393     }
394     free(frame);
395     frame = nullptr;
396     return HDF_SUCCESS;
397 }
398 
AudioCreateCapture(TestAudioManager * manager,int pins,const std::string & adapterName,struct AudioAdapter ** adapter,struct AudioCapture ** capture)399 int32_t AudioCreateCapture(TestAudioManager *manager, int pins, const std::string &adapterName,
400     struct AudioAdapter **adapter, struct AudioCapture **capture)
401 {
402     int32_t ret = -1;
403     struct AudioSampleAttributes attrs = {};
404     struct AudioDeviceDescriptor devDesc = {};
405     struct AudioPort *capturePort = nullptr;
406     if (adapter == nullptr || capture == nullptr) {
407         return HDF_ERR_INVALID_PARAM;
408     }
409     ret = GetLoadAdapter(manager, PORT_IN, adapterName, adapter, capturePort);
410     if (ret < 0) {
411         return ret;
412     }
413     if (*adapter == nullptr || (*adapter)->CreateCapture == nullptr) {
414         return HDF_FAILURE;
415     }
416 #ifdef FEATURE_SMALL_DEVICE
417     InitAttrs(attrs);
418 #else
419     InitAttrsCapture(attrs);
420 #endif
421     InitDevDesc(devDesc, capturePort->portId, pins);
422     ret = (*adapter)->CreateCapture(*adapter, &devDesc, &attrs, capture);
423     if (ret < 0) {
424         manager->UnloadAdapter(manager, *adapter);
425         return ret;
426     }
427     if (*capture == nullptr) {
428         manager->UnloadAdapter(manager, *adapter);
429         return HDF_FAILURE;
430     }
431     return HDF_SUCCESS;
432 }
433 
AudioCreateStartCapture(TestAudioManager * manager,struct AudioCapture ** capture,struct AudioAdapter ** adapter,const std::string & adapterName)434 int32_t AudioCreateStartCapture(TestAudioManager *manager, struct AudioCapture **capture,
435     struct AudioAdapter **adapter, const std::string &adapterName)
436 {
437     int32_t ret = -1;
438     struct AudioSampleAttributes attrs = {};
439     if (adapter == nullptr || capture == nullptr) {
440         return HDF_ERR_INVALID_PARAM;
441     }
442     ret = AudioCreateCapture(manager, PIN_IN_MIC, adapterName, adapter, capture);
443     if (ret < 0) {
444         manager->UnloadAdapter(manager, *adapter);
445         return ret;
446     }
447     if (*capture == nullptr || *adapter == nullptr) {
448         manager->UnloadAdapter(manager, *adapter);
449         return HDF_FAILURE;
450     }
451     FILE *file = fopen(AUDIO_CAPTURE_FILE.c_str(), "wb+");
452     if (file == nullptr) {
453         (*adapter)->DestroyCapture(*adapter, *capture);
454         manager->UnloadAdapter(manager, *adapter);
455         return HDF_FAILURE;
456     }
457 #ifdef FEATURE_SMALL_DEVICE
458     InitAttrs(attrs);
459 #else
460     InitAttrsCapture(attrs);
461 #endif
462     ret = FrameStartCapture((*capture), file, attrs);
463     if (ret < 0) {
464         (*adapter)->DestroyCapture(*adapter, *capture);
465         manager->UnloadAdapter(manager, *adapter);
466         fclose(file);
467         return ret;
468     }
469     (void)fclose(file);
470     return HDF_SUCCESS;
471 }
472 
AudioCaptureStartAndOneFrame(struct AudioCapture * capture)473 int32_t AudioCaptureStartAndOneFrame(struct AudioCapture *capture)
474 {
475     int32_t ret = -1;
476     struct AudioSampleAttributes attrs = {};
477 #ifdef FEATURE_SMALL_DEVICE
478     InitAttrs(attrs);
479 #else
480     InitAttrsCapture(attrs);
481 #endif
482     FILE *file = fopen(AUDIO_CAPTURE_FILE.c_str(), "wb+");
483     if (file == nullptr) {
484         return HDF_FAILURE;
485     }
486     ret = FrameStartCapture(capture, file, attrs);
487     if (ret < 0) {
488         fclose(file);
489         return ret;
490     }
491     (void)fclose(file);
492     return HDF_SUCCESS;
493 }
494 
FrameStart(struct AudioHeadInfo wavHeadInfo,struct AudioRender * render,FILE * file,struct AudioSampleAttributes attrs)495 int32_t FrameStart(struct AudioHeadInfo wavHeadInfo, struct AudioRender *render, FILE *file,
496     struct AudioSampleAttributes attrs)
497 {
498     uint32_t readSize = 0;
499     size_t numRead = 0;
500     uint64_t replyBytes = 0;
501     int32_t tryNumFrame = 0;
502     if (render == nullptr || render->control.Start == nullptr || render->RenderFrame == nullptr || file == nullptr) {
503         return HDF_ERR_INVALID_PARAM;
504     }
505     int32_t ret = render->control.Start((AudioHandle)render);
506     if (ret) {
507         return ret;
508     }
509     uint32_t remainingDataSize = wavHeadInfo.dataSize;
510     uint32_t bufferSize = PcmFramesToBytes(attrs);
511     if (bufferSize == 0) {
512         return HDF_FAILURE;
513     }
514     char *frame = nullptr;
515     frame = reinterpret_cast<char *>(calloc(1, bufferSize));
516     if (frame == nullptr) {
517         return HDF_ERR_MALLOC_FAIL;
518     }
519     do {
520         if (g_frameStatus) {
521             readSize = (remainingDataSize) > (bufferSize) ? (bufferSize) : (remainingDataSize);
522             numRead = fread(frame, readSize, 1, file);
523             if (numRead > 0) {
524                 ret = render->RenderFrame(render, frame, readSize, &replyBytes);
525                 if (ret < 0) {
526                     if (ret == -1) {
527                         if (tryNumFrame > TRY_NUM_FRAME) {
528                             free(frame);
529                             return ret;
530                         }
531                         tryNumFrame++;
532                         continue;
533                     }
534                     free(frame);
535                     return ret;
536                 }
537                 tryNumFrame = 0;
538             }
539             remainingDataSize -= readSize;
540         }
541     } while (readSize > 0 && remainingDataSize > 0);
542     free(frame);
543     return HDF_SUCCESS;
544 }
545 
FrameStartCapture(struct AudioCapture * capture,FILE * file,const struct AudioSampleAttributes attrs)546 int32_t FrameStartCapture(struct AudioCapture *capture, FILE *file, const struct AudioSampleAttributes attrs)
547 {
548     int32_t ret = 0;
549     uint32_t bufferSize = 0;
550     uint64_t replyBytes = 0;
551     uint64_t requestBytes = 0;
552     if (capture == nullptr || capture->control.Start == nullptr || capture->CaptureFrame == nullptr) {
553         return HDF_ERR_INVALID_PARAM;
554     }
555     ret = capture->control.Start((AudioHandle)capture);
556     if (ret < 0) {
557         return ret;
558     }
559     uint32_t pcmBytes = PcmFramesToBytes(attrs);
560     if (pcmBytes < PCM_BYTE_MIN || pcmBytes > PCM_BYTE_MAX) {
561         return HDF_FAILURE;
562     }
563     bufferSize = FRAME_COUNT * pcmBytes;
564     if (bufferSize == 0) {
565         return HDF_FAILURE;
566     }
567     char *frame = nullptr;
568     frame = reinterpret_cast<char *>(calloc(1, bufferSize));
569     if (frame == nullptr) {
570         return HDF_ERR_MALLOC_FAIL;
571     }
572     requestBytes = bufferSize;
573     ret = capture->CaptureFrame(capture, frame, requestBytes, &replyBytes);
574     if (ret < 0) {
575         ret = capture->CaptureFrame(capture, frame, requestBytes, &replyBytes);
576         if (ret < 0) {
577             free(frame);
578             return ret;
579         }
580     }
581     uint32_t requestByte = static_cast<uint32_t>(replyBytes);
582     (void)fwrite(frame, requestByte, 1, file);
583     free(frame);
584     return HDF_SUCCESS;
585 }
586 
RenderFramePrepare(const std::string & path,char * & frame,uint64_t & readSize)587 int32_t RenderFramePrepare(const std::string &path, char *&frame, uint64_t &readSize)
588 {
589     int32_t ret = -1;
590     size_t numRead = 0;
591     uint32_t bufferSize = 4096;
592     uint32_t remainingDataSize = 0;
593     struct AudioSampleAttributes attrs = {};
594     struct AudioHeadInfo headInfo = {};
595 #ifdef FEATURE_SMALL_DEVICE
596     InitAttrs(attrs);
597 #else
598     InitAttrsRender(attrs);
599 #endif
600     char absPath[PATH_MAX] = {0};
601     if (realpath(path.c_str(), absPath) == nullptr) {
602         return HDF_FAILURE;
603     }
604     FILE *file = fopen(absPath, "rb");
605     if (file == nullptr) {
606         return HDF_FAILURE;
607     }
608     ret = WavHeadAnalysis(headInfo, file, attrs);
609     if (ret < 0) {
610         fclose(file);
611         return HDF_FAILURE;
612     }
613     frame = reinterpret_cast<char *>(calloc(1, bufferSize));
614     if (frame == nullptr) {
615         fclose(file);
616         return HDF_ERR_MALLOC_FAIL;
617     }
618     remainingDataSize = headInfo.dataSize;
619     readSize = (remainingDataSize) > (bufferSize) ? (bufferSize) : (remainingDataSize);
620     size_t readSizes = static_cast<size_t>(readSize);
621     numRead = fread(frame, readSizes, 1, file);
622     if (numRead < 1) {
623         free(frame);
624         frame = nullptr;
625         fclose(file);
626         return HDF_FAILURE;
627     }
628     (void)fclose(file);
629     return HDF_SUCCESS;
630 }
631 
FrameStatus(int status)632 void FrameStatus(int status)
633 {
634     g_frameStatus = status;
635     return;
636 }
637 
StartRecord(struct AudioCapture * capture,FILE * file,uint64_t filesize)638 int32_t StartRecord(struct AudioCapture *capture, FILE *file, uint64_t filesize)
639 {
640     uint64_t replyBytes = 0;
641     uint64_t requestBytes = BUFFER_LENTH;
642     uint64_t totalSize = 0;
643     int32_t tryNumFrame = 0;
644     if (capture == nullptr || capture->control.Start == nullptr ||
645         capture->CaptureFrame == nullptr || file == nullptr) {
646         return HDF_ERR_INVALID_PARAM;
647     }
648     int32_t ret = capture->control.Start((AudioHandle)capture);
649     if (ret < 0) {
650         return ret;
651     }
652     char *frame = reinterpret_cast<char *>(calloc(1, BUFFER_LENTH));
653     if (frame == nullptr) {
654         return HDF_ERR_MALLOC_FAIL;
655     }
656     do {
657         if (g_frameStatus) {
658             ret = capture->CaptureFrame(capture, frame, requestBytes, &replyBytes);
659             if (ret < 0) {
660                 if (ret == -1) {
661                     if (tryNumFrame++ > TRY_NUM_FRAME) {
662                         free(frame);
663                         frame = nullptr;
664                         return ret;
665                     }
666                     continue;
667                 }
668                 free(frame);
669                 frame = nullptr;
670                 return ret;
671             }
672             tryNumFrame = 0;
673             uint32_t replyByte = static_cast<uint32_t>(replyBytes);
674             size_t writeRet = fwrite(frame, replyByte, 1, file);
675             if (writeRet == 0) {
676                 free(frame);
677                 frame = nullptr;
678                 return HDF_FAILURE;
679             }
680             totalSize += replyBytes;
681         } else {
682             totalSize += 0;
683         }
684     } while (totalSize <= filesize * MEGABYTE);
685     free(frame);
686     frame = nullptr;
687     return HDF_SUCCESS;
688 }
689 
WriteIdToBuf(struct HdfSBuf * sBuf,struct AudioCtlElemId id)690 int32_t WriteIdToBuf(struct HdfSBuf *sBuf, struct AudioCtlElemId id)
691 {
692     if (!HdfSbufWriteInt32(sBuf, id.iface)) {
693         return HDF_FAILURE;
694     }
695     if (!HdfSbufWriteString(sBuf, id.cardServiceName)) {
696         return HDF_FAILURE;
697     }
698     if (!HdfSbufWriteString(sBuf, id.itemName)) {
699         return HDF_FAILURE;
700     }
701     return HDF_SUCCESS;
702 }
703 
WriteEleValueToBuf(struct HdfSBuf * sBuf,struct AudioCtlElemValue elemvalue)704 int32_t WriteEleValueToBuf(struct HdfSBuf *sBuf, struct AudioCtlElemValue elemvalue)
705 {
706     int32_t ret = -1;
707     if (sBuf == nullptr) {
708         return HDF_FAILURE;
709     }
710     if (!HdfSbufWriteInt32(sBuf, elemvalue.value[0])) {
711         return HDF_FAILURE;
712     }
713     ret = WriteIdToBuf(sBuf, elemvalue.id);
714     if (ret != HDF_SUCCESS) {
715         return HDF_FAILURE;
716     }
717     return HDF_SUCCESS;
718 }
719 
ChangeRegisterStatus(struct AudioCtlElemValue elemValue)720 int32_t ChangeRegisterStatus(struct AudioCtlElemValue elemValue)
721 {
722     int32_t ret = -1;
723     struct HdfIoService *service = nullptr;
724     struct HdfSBuf *reply = nullptr;
725     struct HdfSBuf *sBuf = nullptr;
726     service = HdfIoServiceBind(HDF_CONTROL_SERVICE.c_str());
727     if (service == nullptr || service->dispatcher == nullptr) {
728         return HDF_FAILURE;
729     }
730     sBuf = HdfSbufObtainDefaultSize();
731     if (sBuf == nullptr) {
732         HdfIoServiceRecycle(service);
733         return HDF_FAILURE;
734     }
735     ret = WriteEleValueToBuf(sBuf, elemValue);
736     if (ret < 0) {
737         HdfSbufRecycle(sBuf);
738         HdfIoServiceRecycle(service);
739         return HDF_FAILURE;
740     }
741     ret = service->dispatcher->Dispatch(&service->object, AUDIODRV_CTRL_IOCTRL_ELEM_WRITE, sBuf, reply);
742     if (ret < 0) {
743         HdfSbufRecycle(sBuf);
744         HdfIoServiceRecycle(service);
745         return ret;
746     }
747     HdfSbufRecycle(sBuf);
748     HdfIoServiceRecycle(service);
749     return HDF_SUCCESS;
750 }
751 
QueryRegisterStatus(struct AudioCtlElemId id,struct AudioCtlElemValue & elemValue)752 int32_t QueryRegisterStatus(struct AudioCtlElemId id, struct AudioCtlElemValue &elemValue)
753 {
754     struct HdfIoService *service = nullptr;
755     struct HdfSBuf *sBuf = nullptr;
756     struct HdfSBuf *reply = nullptr;
757     int32_t ret = -1;
758     service = HdfIoServiceBind(HDF_CONTROL_SERVICE.c_str());
759     if (service == nullptr || service->dispatcher == nullptr) {
760         return HDF_FAILURE;
761     }
762     sBuf = HdfSbufObtainDefaultSize();
763     if (sBuf == nullptr) {
764         HdfIoServiceRecycle(service);
765         return HDF_FAILURE;
766     }
767     ret = WriteIdToBuf(sBuf, id);
768     if (ret < 0) {
769         HdfSbufRecycle(sBuf);
770         HdfIoServiceRecycle(service);
771         return HDF_FAILURE;
772     }
773     reply = HdfSbufObtainDefaultSize();
774     if (reply == nullptr) {
775         HdfSbufRecycle(sBuf);
776         HdfIoServiceRecycle(service);
777         return HDF_FAILURE;
778     }
779     ret = service->dispatcher->Dispatch(&service->object, AUDIODRV_CTRL_IOCTRL_ELEM_READ, sBuf, reply);
780     if (ret < 0) {
781         HdfSbufRecycle(sBuf);
782         HdfSbufRecycle(reply);
783         HdfIoServiceRecycle(service);
784         return ret;
785     }
786     if (!HdfSbufReadInt32(reply, &elemValue.value[0])) {
787         HdfSbufRecycle(sBuf);
788         HdfSbufRecycle(reply);
789         HdfIoServiceRecycle(service);
790         return HDF_FAILURE;
791     }
792     HdfSbufRecycle(sBuf);
793     HdfSbufRecycle(reply);
794     HdfIoServiceRecycle(service);
795     return HDF_SUCCESS;
796 }
797 
PowerOff(struct AudioCtlElemValue firstElemValue,struct AudioCtlElemValue secondElemValue)798 int32_t PowerOff(struct AudioCtlElemValue firstElemValue, struct AudioCtlElemValue secondElemValue)
799 {
800     int32_t ret = -1;
801     ret = ChangeRegisterStatus(firstElemValue);
802     if (ret < 0) {
803         return ret;
804     }
805     ret = ChangeRegisterStatus(secondElemValue);
806     if (ret < 0) {
807         return ret;
808     }
809     return HDF_SUCCESS;
810 }
811 
CheckRegisterStatus(const struct AudioCtlElemId firstId,const struct AudioCtlElemId secondId,const int firstStatus,const int secondStatus)812 int32_t CheckRegisterStatus(const struct AudioCtlElemId firstId, const struct AudioCtlElemId secondId,
813     const int firstStatus, const int secondStatus)
814 {
815     int32_t ret = -1;
816     struct AudioCtlElemValue elemValue[2] = {{}, {}};
817     ret = QueryRegisterStatus(firstId, elemValue[0]);
818     if (ret < 0) {
819         return ret;
820     }
821     if (firstStatus != elemValue[0].value[0]) {
822         return HDF_FAILURE;
823     }
824     ret = QueryRegisterStatus(secondId, elemValue[1]);
825     if (ret < 0) {
826         return ret;
827     }
828     if (secondStatus != elemValue[1].value[0]) {
829         return HDF_FAILURE;
830     }
831     return HDF_SUCCESS;
832 }
833 
StopAudio(struct PrepareAudioPara & audiopara)834 int32_t StopAudio(struct PrepareAudioPara &audiopara)
835 {
836     if (audiopara.manager == nullptr || audiopara.adapter == nullptr) {
837         return HDF_FAILURE;
838     }
839     int32_t ret = -1;
840     if (audiopara.capture != nullptr) {
841         ret = audiopara.capture->control.Stop((AudioHandle)(audiopara.capture));
842         if (ret < 0) {
843             audiopara.adapter->DestroyCapture(audiopara.adapter, audiopara.capture);
844             audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
845             audiopara.capture = nullptr;
846             audiopara.adapter = nullptr;
847             return ret;
848         }
849         audiopara.adapter->DestroyCapture(audiopara.adapter, audiopara.capture);
850         audiopara.capture = nullptr;
851     }
852     if (audiopara.render != nullptr) {
853         ret = audiopara.render->control.Stop((AudioHandle)(audiopara.render));
854         if (ret < 0) {
855             audiopara.adapter->DestroyRender(audiopara.adapter, audiopara.render);
856             audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
857             audiopara.render = nullptr;
858             audiopara.adapter = nullptr;
859             return ret;
860         }
861         audiopara.adapter->DestroyRender(audiopara.adapter, audiopara.render);
862         audiopara.render = nullptr;
863     }
864     audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
865     audiopara.adapter = nullptr;
866     return HDF_SUCCESS;
867 }
868 
ThreadRelease(struct PrepareAudioPara & audiopara)869 int32_t ThreadRelease(struct PrepareAudioPara &audiopara)
870 {
871     int32_t ret = -1;
872     pthread_join(audiopara.tids, &audiopara.result);
873     ret = (intptr_t)audiopara.result;
874     if (ret < 0) {
875         StopAudio(audiopara);
876         return ret;
877     }
878     ret = StopAudio(audiopara);
879     if (ret < 0) {
880         return ret;
881     }
882     return HDF_SUCCESS;
883 }
PlayAudioFile(struct PrepareAudioPara & audiopara)884 int32_t PlayAudioFile(struct PrepareAudioPara &audiopara)
885 {
886     int32_t ret = -1;
887     char absPath[PATH_MAX] = {0};
888     if (realpath(audiopara.path, absPath) == nullptr) {
889         return HDF_FAILURE;
890     }
891     if (audiopara.manager == nullptr) {
892         return HDF_ERR_INVALID_PARAM;
893     }
894     FILE *file = fopen(absPath, "rb");
895     if (file == nullptr) {
896         return HDF_FAILURE;
897     }
898     if (WavHeadAnalysis(audiopara.headInfo, file, audiopara.attrs) < 0) {
899         fclose(file);
900         return HDF_FAILURE;
901     }
902     ret = AudioCreateRender(audiopara.manager, audiopara.pins, audiopara.adapterName, &audiopara.adapter,
903                             &audiopara.render);
904     if (ret < 0) {
905         fclose(file);
906         return ret;
907     }
908     if (audiopara.render == nullptr) {
909         fclose(file);
910         return HDF_ERR_INVALID_PARAM;
911     }
912     ret = FrameStart(audiopara.headInfo, audiopara.render, file, audiopara.attrs);
913     if (ret == HDF_SUCCESS) {
914         fclose(file);
915     } else {
916         audiopara.adapter->DestroyRender(audiopara.adapter, audiopara.render);
917         audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
918         audiopara.render = nullptr;
919         audiopara.adapter = nullptr;
920         fclose(file);
921         return ret;
922     }
923     return HDF_SUCCESS;
924 }
925 
RecordAudio(struct PrepareAudioPara & audiopara)926 int32_t RecordAudio(struct PrepareAudioPara &audiopara)
927 {
928     int32_t ret = -1;
929     if (audiopara.manager == nullptr) {
930         return HDF_ERR_INVALID_PARAM;
931     }
932     ret = AudioCreateCapture(audiopara.manager, audiopara.pins, audiopara.adapterName, &audiopara.adapter,
933                              &audiopara.capture);
934     if (ret < 0) {
935         return ret;
936     }
937     if (audiopara.capture == nullptr) {
938         return HDF_ERR_INVALID_PARAM;
939     }
940 
941     bool isMute = false;
942     ret = audiopara.capture->volume.SetMute(audiopara.capture, isMute);
943     if (ret < 0) {
944         audiopara.adapter->DestroyCapture(audiopara.adapter, audiopara.capture);
945         audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
946         return ret;
947     }
948 
949     FILE *file = fopen(audiopara.path, "wb+");
950     if (file == nullptr) {
951         audiopara.adapter->DestroyCapture(audiopara.adapter, audiopara.capture);
952         audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
953         return HDF_FAILURE;
954     }
955     ret = StartRecord(audiopara.capture, file, audiopara.fileSize);
956     if (ret < 0) {
957         audiopara.adapter->DestroyCapture(audiopara.adapter, audiopara.capture);
958         audiopara.manager->UnloadAdapter(audiopara.manager, audiopara.adapter);
959         audiopara.capture = nullptr;
960         audiopara.adapter = nullptr;
961         fclose(file);
962         return ret;
963     }
964     (void)fclose(file);
965     return HDF_SUCCESS;
966 }
InitMmapDesc(FILE * fp,struct AudioMmapBufferDescripter & desc,int32_t & reqSize,bool flag)967 int32_t InitMmapDesc(FILE *fp, struct AudioMmapBufferDescripter &desc, int32_t &reqSize, bool flag)
968 {
969     if (fp == NULL) {
970         return HDF_FAILURE;
971     }
972     int fd = fileno(fp);
973     if (fd == -1) {
974         return HDF_FAILURE;
975     }
976     if (flag) {
977         struct AudioHeadInfo wavHeadInfo = {};
978         fseek(fp, 0, SEEK_END);
979         reqSize = ftell(fp);
980         desc.offset = sizeof(wavHeadInfo);
981     } else {
982         reqSize = FILE_CAPTURE_SIZE;
983         ftruncate(fd, FILE_CAPTURE_SIZE);
984         desc.offset = 0;
985     }
986     desc.memoryFd = fd;
987     desc.isShareable = 1;
988     desc.transferFrameSize = DEEP_BUFFER_RENDER_PERIOD_SIZE / FRAME_COUNT;
989     return HDF_SUCCESS;
990 }
991 
PlayMapAudioFile(struct PrepareAudioPara & audiopara)992 int32_t PlayMapAudioFile(struct PrepareAudioPara &audiopara)
993 {
994     int32_t ret = -1;
995     int32_t reqSize = 0;
996     bool isRender = true;
997     FrameStatus(1);
998     struct AudioMmapBufferDescripter desc = {};
999     if (audiopara.render == nullptr) {
1000         return HDF_FAILURE;
1001     }
1002     char absPath[PATH_MAX] = {0};
1003     if (realpath(audiopara.path, absPath) == nullptr) {
1004         return HDF_FAILURE;
1005     }
1006     FILE *fp = fopen(absPath, "rb+");
1007     if (fp == nullptr) {
1008         return HDF_FAILURE;
1009     }
1010     ret = InitMmapDesc(fp, desc, reqSize, isRender);
1011     if (ret < 0) {
1012         fclose(fp);
1013         return HDF_FAILURE;
1014     }
1015     ret = audiopara.render->control.Start((AudioHandle)(audiopara.render));
1016     if (ret < 0) {
1017         fclose(fp);
1018         return ret;
1019     }
1020     ret = audiopara.render->attr.ReqMmapBuffer((AudioHandle)(audiopara.render), reqSize, &desc);
1021     if (ret == 0) {
1022         munmap(desc.memoryAddress, reqSize);
1023     }
1024     (void)fclose(fp);
1025     return ret;
1026 }
RecordMapAudio(struct PrepareAudioPara & audiopara)1027 int32_t RecordMapAudio(struct PrepareAudioPara &audiopara)
1028 {
1029     int32_t ret = -1;
1030     int32_t reqSize = 0;
1031     bool isRender = false;
1032     struct AudioMmapBufferDescripter desc = {};
1033     if (audiopara.capture == nullptr) {
1034         return HDF_FAILURE;
1035     }
1036     FILE *fp = fopen(audiopara.path, "wb+");
1037     if (fp == NULL) {
1038         return HDF_FAILURE;
1039     }
1040     ret = InitMmapDesc(fp, desc, reqSize, isRender);
1041     if (ret < 0) {
1042         fclose(fp);
1043         return HDF_FAILURE;
1044     }
1045     ret = audiopara.capture->control.Start((AudioHandle)(audiopara.capture));
1046     if (ret < 0) {
1047         fclose(fp);
1048         return ret;
1049     }
1050     ret = audiopara.capture->attr.ReqMmapBuffer((AudioHandle)(audiopara.capture), reqSize, &desc);
1051     (void)fclose(fp);
1052     if (ret == 0) {
1053         munmap(desc.memoryAddress, reqSize);
1054     }
1055     return ret;
1056 }
AudioRenderCallback(enum AudioCallbackType type,void * reserved,void * cookie)1057 int32_t AudioRenderCallback(enum AudioCallbackType type, void *reserved, void *cookie)
1058 {
1059     switch (type) {
1060         case AUDIO_NONBLOCK_WRITE_COMPELETED:
1061             g_writeCompleted = AUDIO_WRITE_COMPELETED_VALUE;
1062             return HDF_SUCCESS;
1063         case AUDIO_RENDER_FULL:
1064             g_renderFull = AUDIO_RENDER_FULL_VALUE;
1065             return HDF_SUCCESS;
1066         case AUDIO_FLUSH_COMPLETED:
1067             g_flushCompleted = AUDIO_FLUSH_COMPLETED_VALUE;
1068             return HDF_SUCCESS;
1069         case AUDIO_ERROR_OCCUR:
1070             return HDF_FAILURE;
1071         case AUDIO_DRAIN_COMPELETED:
1072             return HDF_FAILURE;
1073         default:
1074             return HDF_FAILURE;
1075     }
1076 }
CheckWriteCompleteValue()1077 int32_t CheckWriteCompleteValue()
1078 {
1079     if (g_writeCompleted == AUDIO_WRITE_COMPELETED_VALUE)
1080         return HDF_SUCCESS;
1081     else
1082         return HDF_FAILURE;
1083 }
CheckRenderFullValue()1084 int32_t CheckRenderFullValue()
1085 {
1086     if (g_renderFull == AUDIO_RENDER_FULL_VALUE)
1087         return HDF_SUCCESS;
1088     else
1089         return HDF_FAILURE;
1090 }
CheckFlushValue()1091 int32_t CheckFlushValue()
1092 {
1093     if (g_flushCompleted == AUDIO_FLUSH_COMPLETED_VALUE)
1094         return HDF_SUCCESS;
1095     else
1096         return HDF_FAILURE;
1097 }
ReleaseCaptureSource(struct AudioManager * manager,struct AudioAdapter * & adapter,struct AudioCapture * & capture)1098 int32_t ReleaseCaptureSource(struct AudioManager *manager, struct AudioAdapter *&adapter,
1099     struct AudioCapture *&capture)
1100 {
1101     if (manager == nullptr || adapter == nullptr || capture == nullptr ||
1102         adapter->DestroyCapture == nullptr || manager->UnloadAdapter == nullptr) {
1103         return HDF_FAILURE;
1104     }
1105     int32_t ret = adapter->DestroyCapture(adapter, capture);
1106     if (ret != HDF_SUCCESS) {
1107         return ret;
1108     }
1109     capture = nullptr;
1110     manager->UnloadAdapter(manager, adapter);
1111     adapter = nullptr;
1112     return HDF_SUCCESS;
1113 }
ReleaseRenderSource(struct AudioManager * manager,struct AudioAdapter * & adapter,struct AudioRender * & render)1114 int32_t ReleaseRenderSource(struct AudioManager *manager, struct AudioAdapter *&adapter,
1115     struct AudioRender *&render)
1116 {
1117     if (manager == nullptr || adapter == nullptr || render == nullptr ||
1118         adapter->DestroyRender == nullptr || manager->UnloadAdapter == nullptr) {
1119         return HDF_FAILURE;
1120     }
1121     int32_t ret = adapter->DestroyRender(adapter, render);
1122     if (ret != HDF_SUCCESS) {
1123         return ret;
1124     }
1125     render = nullptr;
1126     manager->UnloadAdapter(manager, adapter);
1127     adapter = nullptr;
1128     return HDF_SUCCESS;
1129 }
1130 }
1131 }
1132