• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2023-2024 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include <cstdio>
17 #include <cstring>
18 #include <cstdlib>
19 #include <unistd.h>
20 #include <cerrno>
21 #include <fcntl.h>
22 #include <csignal>
23 #include <sys/stat.h>
24 
25 #include <iostream>
26 #include <string>
27 
28 #include <securec.h>
29 #include "unistd.h"
30 #include "distributedaudiotest.h"
31 
32 using namespace OHOS::DistributedHardware;
33 
34 using OHOS::HDI::DistributedAudio::Audio::V1_0::IAudioAdapter;
35 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioAdapterDescriptor;
36 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioFormat;
37 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioPort;
38 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioPortDirection;
39 using OHOS::HDI::DistributedAudio::Audio::V1_0::IAudioManager;
40 using OHOS::HDI::DistributedAudio::Audio::V1_0::IAudioRender;
41 using OHOS::HDI::DistributedAudio::Audio::V1_0::IAudioCapture;
42 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioSampleAttributes;
43 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioDeviceDescriptor;
44 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioCategory;
45 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioRouteNode;
46 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioExtParamKey;
47 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioRoute;
48 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioSceneDescriptor;
49 using OHOS::HDI::DistributedAudio::Audio::V1_0::IAudioCallback;
50 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioPortPin;
51 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioPortType;
52 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioPortRole;
53 using OHOS::HDI::DistributedAudio::Audio::V1_0::AudioCallbackType;
54 int32_t g_volume = 5;
55 static int32_t ParamEventCallback(AudioExtParamKey key, const char *condition, const char *value, void *reserved,
56     void *cookie);
57 class AudioParamCallbackImpl final : public IAudioCallback {
58 public:
AudioParamCallbackImpl()59     AudioParamCallbackImpl() {}
~AudioParamCallbackImpl()60     ~AudioParamCallbackImpl() override {}
61     int32_t RenderCallback(AudioCallbackType type, int8_t &reserved, int8_t &cookie) override;
62     int32_t ParamCallback(AudioExtParamKey key, const std::string &condition, const std::string &value,
63         int8_t &reserved, int8_t cookie) override;
64 };
65 
RenderCallback(AudioCallbackType type,int8_t & reserved,int8_t & cookie)66 int32_t AudioParamCallbackImpl::RenderCallback(AudioCallbackType type, int8_t &reserved, int8_t &cookie)
67 {
68     (void) type;
69     (void) reserved;
70     (void) cookie;
71     return DH_SUCCESS;
72 }
73 
ParamCallback(AudioExtParamKey key,const std::string & condition,const std::string & value,int8_t & reserved,int8_t cookie)74 int32_t AudioParamCallbackImpl::ParamCallback(AudioExtParamKey key, const std::string &condition,
75     const std::string &value, int8_t &reserved, int8_t cookie)
76 {
77     (void) cookie;
78     void *cookies = nullptr;
79     ParamEventCallback(static_cast<::AudioExtParamKey>(key), condition.c_str(),
80         value.c_str(), static_cast<void *>(&reserved), cookies);
81     return DH_SUCCESS;
82 }
83 
84 const int32_t CMD_FIND = 9;
85 const int32_t CMD_OPEN_SPK = 1;
86 const int32_t CMD_CLOSE_SPK = 2;
87 const int32_t CMD_START_SPK = 3;
88 const int32_t CMD_STOP_SPK = 4;
89 const int32_t CMD_OPEN_MIC = 5;
90 const int32_t CMD_CLOSE_MIC = 6;
91 const int32_t CMD_START_MIC = 7;
92 const int32_t CMD_STOP_MIC = 8;
93 const int32_t CMD_SET_VOL = 11;
94 const int32_t CMD_GET_VOL = 12;
95 
96 const char DEV_TYPE_SPK = '1';
97 const char DEV_TYPE_MIC = '2';
98 const char SPK_FILE_PATH[128] = "/data/test.wav";
99 const char MIC_FILE_PATH[128] = "/data/mic.pcm";
100 constexpr int32_t TYPE_OFFSET = 12;
101 constexpr int32_t AUDIO_SAMPLE_RATE = 48000;
102 constexpr int32_t VOLUME_MIN = 0;
103 constexpr int32_t VOLUME_MAX = 15;
104 constexpr int32_t RENDER_FRAME_SIZE = 3840;
105 constexpr int32_t RENDER_INTER_LEAVED = 1;
106 constexpr int32_t RENDER_STREAM_ID = 0;
107 constexpr int32_t RENDER_CHANNEL_MASK = 2;
108 constexpr int32_t CAPTURE_INTER_LEAVED = 1;
109 constexpr int32_t CAPTURE_STREAM_ID = 2;
110 constexpr int32_t CAPTURE_CHANNEL_MASK = 2;
111 constexpr int64_t AUDIO_FRAME_TIME_INTERFAL_DEFAULT = 21333;
112 
113 static OHOS::sptr<IAudioManager> g_manager = nullptr;
114 static OHOS::sptr<IAudioAdapter> g_adapter = nullptr;
115 static OHOS::sptr<IAudioRender> g_render = nullptr;
116 static OHOS::sptr<IAudioCapture> g_capture = nullptr;
117 static std::vector<AudioAdapterDescriptor> g_devices;
118 static OHOS::sptr<IAudioCallback> g_callbackStub = nullptr;
119 static std::string g_devId = "";
120 
121 static constexpr const char* PLAY_THREAD = "playThread";
122 static constexpr const char* CAPTURE_THREAD = "captureThread";
123 
124 uint32_t g_renderId = 0;
125 uint32_t g_captureId = 0;
126 int32_t g_frameNum = 0;
127 int32_t g_frameIndex = 0;
128 int32_t g_micFrameNum = 0;
129 bool g_isInitRenderData = false;
130 static std::vector<uint8_t*> renderData;
131 
132 static DeviceStatus g_spkStatus = DeviceStatus::DEVICE_IDLE;
133 static DeviceStatus g_micStatus = DeviceStatus::DEVICE_IDLE;
134 
135 static std::thread g_playingThread;
136 static std::thread g_capingThread;
137 FILE *g_micFile = nullptr;
138 
GetNowTimeUs()139 static int64_t GetNowTimeUs()
140 {
141     std::chrono::microseconds nowUs =
142         std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::system_clock::now().time_since_epoch());
143     return nowUs.count();
144 }
145 
InitTestDemo()146 int32_t InitTestDemo()
147 {
148     std::cout << "**********************************************************************************" << std::endl;
149     DHLOGI("**********************************************************************************");
150     std::cout << "Distributed Audio Test Demo Bin v1.3." << std::endl;
151     std::cout << "**********************************************************************************" << std::endl;
152     std::cout << std::endl;
153     std::cout << "Init distributed audio hdf service." << std::endl;
154     g_manager = IAudioManager::Get("daudio_primary_service", false);
155     if (g_manager == nullptr) {
156         std::cout << "Distributed audio manager is null, Please Check network!" << std::endl;
157         return ERR_DH_AUDIO_FAILED;
158     }
159     std::cout << "Load audio manager success." << std::endl;
160     FindAudioDevice();
161     if (g_devId.empty()) {
162         std::cout << "Cannot find distributed device. Please input 9 to query distribtued device." << std::endl;
163     } else {
164         std::cout << "Find one distributed device: " << g_devId << std::endl;
165     }
166     return DH_SUCCESS;
167 }
168 
FindAudioDevice()169 std::string FindAudioDevice()
170 {
171     if (g_manager == nullptr) {
172         std::cout << "Audio manager is null, Please Check network!" << std::endl;
173         return "false";
174     }
175     int32_t ret = g_manager->GetAllAdapters(g_devices);
176     if (ret != DH_SUCCESS) {
177         std::cout << "Get audio devices failed!" << std::endl;
178         return "false";
179     }
180     for (uint32_t index = 0; index < g_devices.size(); index++) {
181         const AudioAdapterDescriptor desc = g_devices[index];
182         if (index == 0) {
183             g_devId = desc.adapterName;
184             break;
185         }
186     }
187     return "true";
188 }
189 
HandleDevError(const char * condition,const char * value)190 static void HandleDevError(const char *condition, const char *value)
191 {
192     if (condition[TYPE_OFFSET] == DEV_TYPE_SPK && g_spkStatus != DeviceStatus::DEVICE_IDLE) {
193         CloseSpk();
194     }
195 
196     if (condition[TYPE_OFFSET] == DEV_TYPE_MIC && g_micStatus == DeviceStatus::DEVICE_IDLE) {
197         CloseMic();
198     }
199 
200     std::cout << "Receive abnormal event, Demo quit." << std::endl;
201 }
202 
ParamEventCallback(AudioExtParamKey key,const char * condition,const char * value,void * reserved,void * cookie)203 static int32_t ParamEventCallback(AudioExtParamKey key, const char *condition, const char *value, void *reserved,
204     void *cookie)
205 {
206     std::string val(value);
207     std::string con(condition);
208     std::cout << std::endl;
209     std::cout << "**********************************************************************************" << std::endl;
210     std::cout << "Event recived: " << key << std::endl;
211     std::cout << "Condition: " << con << std::endl;
212     std::cout << "Value: " << val << std::endl;
213     std::cout << "**********************************************************************************" << std::endl;
214     std::cout << std::endl;
215 
216     if (key == AudioExtParamKey::AUDIO_EXT_PARAM_KEY_STATUS && con.rfind("ERR_EVENT", 0) == 0) {
217         HandleDevError(condition, value);
218     }
219     return DH_SUCCESS;
220 }
221 
LoadSpkDev(const std::string & devId)222 static int32_t LoadSpkDev(const std::string &devId)
223 {
224     struct AudioAdapterDescriptor dev;
225     for (uint32_t index = 0; index < g_devices.size(); index++) {
226         struct AudioAdapterDescriptor desc = g_devices[index];
227         if (desc.adapterName == devId) {
228             dev = desc;
229             break;
230         }
231     }
232     if (dev.adapterName.data() == nullptr) {
233         std::cout << "Input device id is wrong." << std::endl;
234         FindAudioDevice();
235         return ERR_DH_AUDIO_FAILED;
236     }
237     if (g_manager == nullptr) {
238         return ERR_DH_AUDIO_FAILED;
239     }
240     if (g_adapter == nullptr) {
241         int32_t ret = g_manager->LoadAdapter(dev, g_adapter);
242         if (ret != DH_SUCCESS || g_adapter == nullptr) {
243             std::cout << "Load audio device failed, ret: " << ret << std::endl;
244             return ERR_DH_AUDIO_FAILED;
245         }
246     }
247     return DH_SUCCESS;
248 }
249 
OpenSpk(std::string devId)250 std::string OpenSpk(std::string devId)
251 {
252     if (g_spkStatus != DeviceStatus::DEVICE_IDLE) {
253         std::cout << "Speaker device is already opened." << std::endl;
254         return "true";
255     }
256     if (LoadSpkDev(devId) != DH_SUCCESS) {
257         std::cout << "Load spk failed" << std::endl;
258         return "false";
259     }
260 
261     g_callbackStub = new AudioParamCallbackImpl();
262     int32_t ret = g_adapter->RegExtraParamObserver(g_callbackStub, 0);
263     if (ret != DH_SUCCESS) {
264         std::cout << "Register observer failed, ret: " << ret << std::endl;
265         return "false";
266     }
267 
268     struct AudioDeviceDescriptor renderDesc;
269     renderDesc.pins = AudioPortPin::PIN_OUT_SPEAKER;
270     renderDesc.desc = "";
271     AudioSampleAttributes g_rattrs = {};
272     g_rattrs.type = AudioCategory::AUDIO_IN_MEDIA;
273     g_rattrs.interleaved = RENDER_INTER_LEAVED;
274     g_rattrs.streamId = RENDER_STREAM_ID;
275     g_rattrs.channelCount = RENDER_CHANNEL_MASK;
276     g_rattrs.sampleRate = AUDIO_SAMPLE_RATE;
277     g_rattrs.format = AudioFormat::AUDIO_FORMAT_TYPE_PCM_16_BIT;
278     ret = g_adapter->CreateRender(renderDesc, g_rattrs, g_render, g_renderId);
279     if (ret != DH_SUCCESS || g_render == nullptr) {
280         std::cout << "Open SPK device failed, ret: " << ret << std::endl;
281         return "false";
282     }
283     g_spkStatus = DeviceStatus::DEVICE_OPEN;
284     std::cout << "Open SPK device success." << std::endl;
285     return "true";
286 }
287 
WriteStreamWait(const int64_t & startTime)288 static void WriteStreamWait(const int64_t &startTime)
289 {
290     int64_t endTime = GetNowTimeUs();
291     int64_t passTime = endTime - startTime;
292 
293     if (passTime > AUDIO_FRAME_TIME_INTERFAL_DEFAULT) {
294         return;
295     }
296     int64_t remainTime = AUDIO_FRAME_TIME_INTERFAL_DEFAULT - passTime;
297     std::this_thread::sleep_for(std::chrono::microseconds(remainTime));
298 }
299 
Play()300 static void Play()
301 {
302     if (g_render == nullptr) {
303         std::cout << "SPK device is null." << std::endl;
304         return;
305     }
306     if (pthread_setname_np(pthread_self(), PLAY_THREAD) != DH_SUCCESS) {
307         std::cout << "Play thread setname failed." << std::endl;
308     }
309     std::cout << "Playing thread started." << std::endl;
310     g_render->Start();
311     g_spkStatus = DeviceStatus::DEVICE_START;
312 
313     uint64_t size = 0;
314     while (g_spkStatus == DeviceStatus::DEVICE_START) {
315         int64_t startTime = GetNowTimeUs();
316 
317         std::vector<int8_t> frameHal(RENDER_FRAME_SIZE);
318         int32_t ret = memcpy_s(frameHal.data(), RENDER_FRAME_SIZE, renderData[g_frameIndex], RENDER_FRAME_SIZE);
319         if (ret != EOK) {
320             DHLOGE("Copy render frame failed, error code %{public}d.", ret);
321             return;
322         }
323         ret = g_render->RenderFrame(frameHal, size);
324         if (ret != DH_SUCCESS) {
325             std::cout<<"RenderFrame failed, index: "<< g_frameIndex << ", ret:  " << ret << std::endl;
326         }
327         g_frameIndex++;
328         if (g_frameNum != 0 && g_frameIndex == g_frameNum) {
329             g_frameIndex = 0;
330         }
331         WriteStreamWait(startTime);
332     }
333     std::cout << "Playing thread stopped." << std::endl;
334 }
335 
StartRender()336 std::string StartRender()
337 {
338     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
339         std::cout << "Speaker device is not opened, start render failed." << std::endl;
340         return "false";
341     }
342 
343     if (g_spkStatus == DeviceStatus::DEVICE_OPEN) {
344         WavHdr wavHeader;
345         size_t headerSize = sizeof(WavHdr);
346         if (!g_isInitRenderData) {
347             struct stat statbuf;
348             stat(SPK_FILE_PATH, &statbuf);
349             int32_t size = statbuf.st_size;
350             g_frameNum = (size - static_cast<int32_t>(headerSize)) / RENDER_FRAME_SIZE;
351             std::cout << "Audio file frame num: " << g_frameNum << std::endl;
352             for (int32_t j = 0; j < g_frameNum; j++) {
353                 uint8_t *frame = new uint8_t[RENDER_FRAME_SIZE]();
354                 renderData.push_back(frame);
355             }
356             g_isInitRenderData = true;
357         }
358         FILE *wavFile = fopen(SPK_FILE_PATH, "rb");
359 
360         if (wavFile == nullptr) {
361             DHLOGE("open spk file path failed!");
362             std::cout << "open spk file path failed!" << std::endl;
363             return "false";
364         }
365 
366         fread(&wavHeader, 1, headerSize, wavFile);
367         for (int32_t i = 0; i < g_frameNum; i++) {
368             fread(renderData[i], 1, RENDER_FRAME_SIZE, wavFile);
369         }
370         fclose(wavFile);
371         g_frameIndex = 0;
372         g_playingThread = std::thread(Play);
373         return "true";
374     }
375     if (g_spkStatus == DeviceStatus::DEVICE_START) {
376         std::cout << "Speaker device is started." << std::endl;
377         return "true";
378     }
379     if (g_spkStatus == DeviceStatus::DEVICE_STOP) {
380         g_playingThread = std::thread(Play);
381     }
382     return "true";
383 }
384 
StopRender()385 std::string StopRender()
386 {
387     if (g_render == nullptr) {
388         std::cout << "SPK device is null." << std::endl;
389         return "false";
390     }
391 
392     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
393         std::cout << "Speaker device is not opened." << std::endl;
394         return "false";
395     }
396 
397     if (g_spkStatus == DeviceStatus::DEVICE_OPEN) {
398         std::cout << "Speaker device is not started." << std::endl;
399         return "false";
400     }
401 
402     if (g_spkStatus == DeviceStatus::DEVICE_STOP) {
403         std::cout << "Speaker device is already stoped." << std::endl;
404         return "true";
405     }
406 
407     g_spkStatus = DeviceStatus::DEVICE_STOP;
408     if (g_playingThread.joinable()) {
409         g_playingThread.join();
410     }
411     g_render->Stop();
412     return "true";
413 }
414 
CloseSpk()415 std::string CloseSpk()
416 {
417     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
418         std::cout << "Speaker device is not opened." << std::endl;
419         return "false";
420     }
421 
422     if (g_spkStatus == DeviceStatus::DEVICE_START) {
423         StopRender();
424     }
425 
426     int32_t ret = g_adapter->DestroyRender(g_renderId);
427     if (ret != DH_SUCCESS) {
428         std::cout << "Close speaker failed" << std::endl;
429         return "false";
430     }
431     if (g_micStatus == DeviceStatus::DEVICE_IDLE) {
432         g_manager->UnloadAdapter(g_devId);
433         g_adapter = nullptr;
434     }
435     g_spkStatus = DeviceStatus::DEVICE_IDLE;
436 
437     if (g_isInitRenderData) {
438         for (auto &p : renderData) {
439             delete[] p;
440         }
441         renderData.clear();
442         g_isInitRenderData = false;
443     }
444     std::cout << "Close SPK device success." << std::endl;
445     return "true";
446 }
447 
LoadMicDev(const std::string & devId)448 static int32_t LoadMicDev(const std::string &devId)
449 {
450     struct AudioAdapterDescriptor dev;
451     for (uint32_t index = 0; index < g_devices.size(); index++) {
452         struct AudioAdapterDescriptor desc = g_devices[index];
453         if (desc.adapterName == devId) {
454             dev = desc;
455             break;
456         }
457     }
458     if (dev.adapterName.data() == nullptr) {
459         std::cout << "Input device id is wrong." << std::endl;
460         FindAudioDevice();
461         return ERR_DH_AUDIO_FAILED;
462     }
463     if (g_manager == nullptr) {
464         return ERR_DH_AUDIO_FAILED;
465     }
466     if (g_adapter == nullptr) {
467         int32_t ret = g_manager->LoadAdapter(dev, g_adapter);
468         if (ret != DH_SUCCESS || g_adapter == nullptr) {
469             std::cout << "Load audio device failed, ret: " << ret << std::endl;
470             return ERR_DH_AUDIO_FAILED;
471         }
472     }
473     return DH_SUCCESS;
474 }
475 
OpenMic(std::string devId)476 std::string OpenMic(std::string devId)
477 {
478     if (g_micStatus != DeviceStatus::DEVICE_IDLE) {
479         std::cout << "Mic device is already opened." << std::endl;
480         return "true";
481     }
482     if (LoadMicDev(devId) != DH_SUCCESS) {
483         std::cout << "Load audio device failed." << std::endl;
484         return "false";
485     }
486 
487     AudioDeviceDescriptor captureDesc;
488     captureDesc.pins = AudioPortPin::PIN_IN_MIC;
489     captureDesc.desc = "";
490     AudioSampleAttributes captureAttr;
491     captureAttr.type = AudioCategory::AUDIO_IN_MEDIA;
492     captureAttr.interleaved = CAPTURE_INTER_LEAVED;
493     captureAttr.streamId = CAPTURE_STREAM_ID;
494     captureAttr.channelCount = CAPTURE_CHANNEL_MASK;
495     captureAttr.sampleRate = AUDIO_SAMPLE_RATE;
496     captureAttr.format = AudioFormat::AUDIO_FORMAT_TYPE_PCM_16_BIT;
497     int32_t ret = g_adapter->CreateCapture(captureDesc, captureAttr, g_capture, g_captureId);
498     if (ret != DH_SUCCESS || g_capture == nullptr) {
499         std::cout << "Open MIC device failed." << std::endl;
500         return "false";
501     }
502     g_micStatus = DeviceStatus::DEVICE_OPEN;
503     std::cout << "Open MIC device success." << std::endl;
504     return "true";
505 }
506 
ReadStreamWait(const int64_t & startTime)507 static void ReadStreamWait(const int64_t &startTime)
508 {
509     int64_t endTime = GetNowTimeUs();
510     int32_t passTime = endTime - startTime;
511 
512     if (passTime > AUDIO_FRAME_TIME_INTERFAL_DEFAULT) {
513         return;
514     }
515     int64_t remainTime = AUDIO_FRAME_TIME_INTERFAL_DEFAULT - passTime;
516     std::this_thread::sleep_for(std::chrono::microseconds(remainTime));
517 }
518 
Capture()519 static void Capture()
520 {
521     if (g_capture == nullptr) {
522         std::cout << "MIC device is null." << std::endl;
523         return;
524     }
525     if (pthread_setname_np(pthread_self(), CAPTURE_THREAD) != DH_SUCCESS) {
526         std::cout << "Capture thread setname failed." << std::endl;
527     }
528     std::cout << "Capturing thread started." << std::endl;
529     g_capture->Start();
530     g_micStatus = DeviceStatus::DEVICE_START;
531 
532     uint64_t size = 0;
533     while (g_micStatus == DeviceStatus::DEVICE_START) {
534         std::vector<int8_t> data(RENDER_FRAME_SIZE);
535         int64_t startTime = GetNowTimeUs();
536         int32_t ret = g_capture->CaptureFrame(data, size);
537         if (ret != DH_SUCCESS) {
538             std::cout << "CaptureFrame failed, ret: " << ret << std::endl;
539             return;
540         }
541         size_t writeCnt = fwrite(data.data(), 1, RENDER_FRAME_SIZE, g_micFile);
542         if (static_cast<int32_t>(writeCnt) != RENDER_FRAME_SIZE) {
543             std::cout << "fwrite data failed." << std::endl;
544         }
545         g_micFrameNum++;
546         ReadStreamWait(startTime);
547     }
548     std::cout << "Capturing thread stopped." << std::endl;
549 }
550 
StartCapture()551 std::string StartCapture()
552 {
553     if (g_micStatus == DeviceStatus::DEVICE_IDLE) {
554         std::cout << "Mic device is not opened, start capture failed." << std::endl;
555         return "false";
556     }
557 
558     if (g_micStatus == DeviceStatus::DEVICE_OPEN) {
559         g_micFile = fopen(MIC_FILE_PATH, "ab+");
560         if (g_micFile == nullptr) {
561             std::cout << "Open pcm file failed." << std::endl;
562             return "false";
563         }
564         g_capingThread = std::thread(Capture);
565         return "true";
566     }
567 
568     if (g_micStatus == DeviceStatus::DEVICE_START) {
569         std::cout << "Mic device is already started." << std::endl;
570         return "true";
571     }
572 
573     if (g_micStatus == DeviceStatus::DEVICE_STOP) {
574         g_capingThread = std::thread(Capture);
575     }
576     return "true";
577 }
578 
StopCapture()579 std::string StopCapture()
580 {
581     if (g_capture == nullptr) {
582         std::cout << "MIC device is null." << std::endl;
583         return "false";
584     }
585     if (g_micStatus == DeviceStatus::DEVICE_IDLE) {
586         std::cout << "Mic device is not opened." << std::endl;
587         return "false";
588     }
589     if (g_micStatus == DeviceStatus::DEVICE_OPEN) {
590         std::cout << "Mic device is not started." << std::endl;
591         return "false";
592     }
593     if (g_micStatus == DeviceStatus::DEVICE_STOP) {
594         std::cout << "Mic device is already started." << std::endl;
595         return "false";
596     }
597     g_micStatus = DeviceStatus::DEVICE_STOP;
598     if (g_capingThread.joinable()) {
599         g_capingThread.join();
600     }
601     g_capture->Stop();
602     return "true";
603 }
604 
CloseMic()605 std::string CloseMic()
606 {
607     if (g_micStatus == DeviceStatus::DEVICE_IDLE) {
608         std::cout << "Mic device is not opened." << std::endl;
609         return "false";
610     }
611 
612     if (g_micStatus == DeviceStatus::DEVICE_START) {
613         StopCapture();
614     }
615 
616     int32_t ret = g_adapter->DestroyCapture(g_captureId);
617     if (ret != DH_SUCCESS) {
618         std::cout << "Close mic failed." << std::endl;
619         return "false";
620     }
621     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
622         g_manager->UnloadAdapter(g_devId);
623         g_adapter = nullptr;
624     }
625     if (g_micFile != nullptr) {
626         fclose(g_micFile);
627         g_micFile = nullptr;
628     }
629     g_micStatus = DeviceStatus::DEVICE_IDLE;
630     std::cout << "Close MIC device success." << std::endl;
631     return "true";
632 }
633 
SetVolume(int vol)634 std::string SetVolume(int vol)
635 {
636     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
637         std::cout << "Speaker is not opened, can not set volume." << std::endl;
638         return "false";
639     }
640     std::cout << "Please input volum to set [0,15]." << std::endl;
641     if (vol < VOLUME_MIN || vol > VOLUME_MAX) {
642         std::cout << "Volume is invalid." << std::endl;
643         return "false";
644     }
645     std::cout << "Set volume: " << vol << std::endl;
646     AudioExtParamKey key = AudioExtParamKey::AUDIO_EXT_PARAM_KEY_VOLUME;
647     std::string condition = "EVENT_TYPE=1;VOLUME_GROUP_ID=1;AUDIO_VOLUME_TYPE=1;";
648     std::string volStr = std::to_string(vol);
649     int32_t ret = g_adapter->SetExtraParams(key, condition, volStr);
650     if (ret != DH_SUCCESS) {
651         std::cout << "Set volume failed" << std::endl;
652         return "false";
653     }
654     return "true";
655 }
656 
GetVolume()657 std::string GetVolume()
658 {
659     if (g_spkStatus == DeviceStatus::DEVICE_IDLE) {
660         std::cout << "Speaker is not opened, can not get volume." << std::endl;
661         return "false";
662     }
663     AudioExtParamKey key = AudioExtParamKey::AUDIO_EXT_PARAM_KEY_VOLUME;
664     std::string condition = "EVENT_TYPE=1;VOLUME_GROUP_ID=1;AUDIO_VOLUME_TYPE=1;";
665     std::string vol;
666     int32_t ret = g_adapter->GetExtraParams(key, condition.c_str(), vol);
667     if (ret != DH_SUCCESS) {
668         std::cout << "Get Volume failed." << std::endl;
669         return "false";
670     }
671     std::cout << "Get volume success. volume: " << vol <<std::endl;
672     return "true";
673 }
674 
HandleAudioEvent(int32_t cmd)675 std::string HandleAudioEvent(int32_t cmd)
676 {
677     std::string res = "";
678     if (cmd == CMD_FIND) {
679         res = FindAudioDevice();
680     }
681     if (cmd == CMD_OPEN_SPK) {
682         res = OpenSpk(g_devId);
683     }
684     if (cmd == CMD_START_SPK) {
685         res = StartRender();
686     }
687     if (cmd == CMD_STOP_SPK) {
688         res = StopRender();
689     }
690     if (cmd == CMD_CLOSE_SPK) {
691         res = CloseSpk();
692     }
693     if (cmd == CMD_OPEN_MIC) {
694         res = OpenMic(g_devId);
695     }
696     if (cmd == CMD_START_MIC) {
697         res = StartCapture();
698     }
699     if (cmd == CMD_STOP_MIC) {
700         res = StopCapture();
701     }
702     if (cmd == CMD_CLOSE_MIC) {
703         res = CloseMic();
704     }
705     if (cmd == CMD_SET_VOL) {
706         res = SetVolume(g_volume);
707     }
708     if (cmd == CMD_GET_VOL) {
709         res = GetVolume();
710     }
711     return res;
712 }