1 /*
2 * Copyright (c) 2022 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 "alsa_lib_capture.h"
17 #include "audio_common.h"
18 #include "osal_mem.h"
19 #include "securec.h"
20
21 #define HDF_LOG_TAG HDF_AUDIO_HAL_LIB
22
23 #define AUDIO_TIMESTAMP_FREQ 8 /* Hz */
24 #define AUDIO_SAMPLE_FREQ 48000
25 #define AUDIO_PERIOD ((AUDIO_SAMPLE_FREQ) / (AUDIO_TIMESTAMP_FREQ))
26 #define AUDIO_PCM_WAIT 100
27 #define AUDIO_RESUME_POLL (10 * (AUDIO_PCM_WAIT)) // 1s
28 #define ALSA_CAP_BUFFER_SIZE (2 * 2 * 6000) // format(S16LE) * channels(2) * period.
29
30 static unsigned int g_bufferTime = 500000; /* (0.5s): ring buffer length in us */
31 static unsigned int g_periodTime = 100000; /* (0.1s): period time in us */
32 static snd_pcm_sframes_t g_bufferSize = 0;
33 static snd_pcm_sframes_t g_periodSize = 0;
34 static int g_resample = 1; /* enable alsa-lib resampling */
35 static bool g_periodEvent = false; /* produce poll event after each period */
36 static int g_canPause = 0; /* 0 Hardware doesn't support pause, 1 Hardware supports pause */
37
AudioSetMixerCapVolume(snd_mixer_elem_t * pcmElemen,long vol)38 static int32_t AudioSetMixerCapVolume(snd_mixer_elem_t *pcmElemen, long vol)
39 {
40 int32_t ret;
41
42 if (pcmElemen == NULL) {
43 AUDIO_FUNC_LOGE("parameter is NULL!");
44 return HDF_FAILURE;
45 }
46
47 /* Judge whether it is mono or stereo */
48 ret = snd_mixer_selem_is_capture_mono(pcmElemen);
49 if (ret == 1) { // mono
50 ret = snd_mixer_selem_set_capture_volume(pcmElemen, SND_MIXER_SCHN_MONO, vol);
51 if (ret < 0) {
52 AUDIO_FUNC_LOGE("Failed to set volume: %{public}s.", snd_strerror(ret));
53 return HDF_FAILURE;
54 }
55 } else { // ret == 0: is not mono. (stereo)
56 ret = snd_mixer_selem_set_capture_volume_all(pcmElemen, vol);
57 if (ret < 0) {
58 AUDIO_FUNC_LOGE("Failed to set all channel volume: %{public}s.", snd_strerror(ret));
59 return HDF_FAILURE;
60 }
61 }
62
63 return HDF_SUCCESS;
64 }
65
AudioCaptureSetPauseState(snd_pcm_t * pcm,int32_t pause)66 static int32_t AudioCaptureSetPauseState(snd_pcm_t *pcm, int32_t pause)
67 {
68 int32_t ret;
69
70 if (pcm == NULL) {
71 AUDIO_FUNC_LOGE("Param is NULL!");
72 return HDF_FAILURE;
73 }
74
75 if (pause == AUDIO_ALSALIB_IOCTRL_RESUME) {
76 ret = snd_pcm_prepare(pcm);
77 if (ret < 0) {
78 AUDIO_FUNC_LOGE("snd_pcm_prepare fail: %{public}s", snd_strerror(ret));
79 return HDF_FAILURE;
80 }
81 ret = snd_pcm_start(pcm);
82 if (ret < 0) {
83 AUDIO_FUNC_LOGE("snd_pcm_start fail. %{public}s", snd_strerror(ret));
84 return HDF_FAILURE;
85 }
86 } else if (pause == AUDIO_ALSALIB_IOCTRL_PAUSE) {
87 ret = snd_pcm_drop(pcm);
88 if (ret < 0) {
89 AUDIO_FUNC_LOGE("Pause fail: %{public}s", snd_strerror(ret));
90 return HDF_FAILURE;
91 }
92 } else {
93 /* Nothing to do! */
94 }
95
96 return HDF_SUCCESS;
97 }
98
AudioCtlCaptureSetPauseStu(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)99 int32_t AudioCtlCaptureSetPauseStu(
100 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
101 {
102 int32_t ret;
103 int32_t pause;
104 struct AudioCardInfo *cardIns;
105
106 (void)cmdId;
107 if (handle == NULL || handleData == NULL) {
108 AUDIO_FUNC_LOGE("Param is NULL!");
109 return HDF_FAILURE;
110 }
111
112 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
113 cardIns = GetCardIns(adapterName);
114 if (cardIns == NULL) {
115 AUDIO_FUNC_LOGE("cardIns or capturePcmHandle is NULL!");
116 return HDF_FAILURE;
117 }
118
119 pause = handleData->captureMode.ctlParam.pause ? AUDIO_ALSALIB_IOCTRL_PAUSE : AUDIO_ALSALIB_IOCTRL_RESUME;
120 ret = AudioCaptureSetPauseState(cardIns->capturePcmHandle, pause);
121 if (ret != HDF_SUCCESS) {
122 AUDIO_FUNC_LOGE("set pause error!");
123 return HDF_FAILURE;
124 }
125
126 return HDF_SUCCESS;
127 }
128
AudioCtlCaptureGetVolume(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)129 int32_t AudioCtlCaptureGetVolume(
130 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
131 {
132 int32_t ret;
133 long volEverage;
134 long volLeft = 0;
135 long volRight = 0;
136 struct AudioCardInfo *cardIns;
137
138 (void)cmdId;
139 if (handle == NULL || handleData == NULL) {
140 AUDIO_FUNC_LOGE("AudioCtlCaptureSetVolume parameter is NULL!");
141 return HDF_FAILURE;
142 }
143
144 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
145 cardIns = GetCardIns(adapterName);
146 if (cardIns == NULL) {
147 AUDIO_FUNC_LOGE("Unable to obtain correct sound card information!");
148 return HDF_FAILURE;
149 }
150
151 if (strncmp(adapterName, USB, strlen(USB)) == 0) {
152 handleData->captureMode.ctlParam.volume = MAX_VOLUME;
153 return HDF_SUCCESS;
154 }
155
156 ret = snd_mixer_handle_events(cardIns->mixer);
157 if (ret < 0) {
158 AUDIO_FUNC_LOGE("snd_mixer_handle_events fail: %{public}s.", snd_strerror(ret));
159 return HDF_FAILURE;
160 }
161
162 /* Read the two channel volume */
163 ret = snd_mixer_selem_get_capture_volume(cardIns->ctrlLeftVolume, SND_MIXER_SCHN_FRONT_LEFT, &volLeft);
164 if (ret < 0) {
165 AUDIO_FUNC_LOGE("Get left channel volume fail: %{public}s.", snd_strerror(ret));
166 }
167 ret = snd_mixer_selem_get_capture_volume(cardIns->ctrlLeftVolume, SND_MIXER_SCHN_FRONT_RIGHT, &volRight);
168 if (ret < 0) {
169 AUDIO_FUNC_LOGE("Get right channel volume fail: %{public}s.", snd_strerror(ret));
170 }
171 volEverage = (volLeft + volRight) >> 1;
172 handleData->captureMode.ctlParam.volume = (float)(volEverage);
173
174 return HDF_SUCCESS;
175 }
176
AudioCtlCaptureSetVolume(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)177 int32_t AudioCtlCaptureSetVolume(
178 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
179 {
180 int32_t ret;
181 int32_t vol;
182 struct AudioCardInfo *cardIns;
183
184 (void)cmdId;
185 if (handle == NULL || handleData == NULL) {
186 AUDIO_FUNC_LOGE("parameter is NULL!");
187 return HDF_FAILURE;
188 }
189
190 vol = (int32_t)handleData->captureMode.ctlParam.volume;
191 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
192 cardIns = GetCardIns(adapterName);
193 if (cardIns == NULL) {
194 AUDIO_FUNC_LOGE("cardIns is NULL!");
195 return HDF_FAILURE;
196 }
197
198 if (strncmp(adapterName, USB, strlen(USB)) == 0) {
199 /* The external Settings. */
200 return HDF_SUCCESS;
201 }
202
203 ret = AudioSetMixerCapVolume(cardIns->ctrlLeftVolume, vol);
204 if (ret != HDF_SUCCESS) {
205 AUDIO_FUNC_LOGE("AudioSetMixerVolume left fail!");
206 return ret;
207 }
208
209 ret = AudioSetMixerCapVolume(cardIns->ctrlRightVolume, vol);
210 if (ret != HDF_SUCCESS) {
211 AUDIO_FUNC_LOGE("AudioSetMixerVolume right fail!");
212 return ret;
213 }
214
215 return HDF_SUCCESS;
216 }
217
AudioCtlCaptureSetMuteStu(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)218 int32_t AudioCtlCaptureSetMuteStu(
219 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
220 {
221 int32_t ret;
222 bool muteState;
223
224 (void)cmdId;
225 if (handle == NULL || handleData == NULL) {
226 AUDIO_FUNC_LOGE("param is NULL!");
227 return HDF_FAILURE;
228 }
229
230 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
231 struct AudioCardInfo *cardIns = GetCardIns(adapterName);
232 if (cardIns == NULL) {
233 AUDIO_FUNC_LOGE("cardIns is empty pointer!!!");
234 return HDF_FAILURE;
235 }
236
237 muteState = (bool)cardIns->captureMuteValue;
238 if (muteState == false) {
239 ret =
240 AudioMixerSetCtrlMode(cardIns, adapterName, "Digital Capture mute", SND_CAP_MIC_PATH, SND_IN_CARD_MIC_OFF);
241 } else {
242 ret =
243 AudioMixerSetCtrlMode(cardIns, adapterName, "Digital Capture mute", SND_CAP_MIC_PATH, SND_IN_CARD_MAIN_MIC);
244 }
245 if (ret != HDF_SUCCESS) {
246 AUDIO_FUNC_LOGE("AudioMixerSetCtrlMode failed!");
247 return ret;
248 }
249 cardIns->captureMuteValue = (int32_t)handleData->captureMode.ctlParam.mute;
250
251 return HDF_SUCCESS;
252 }
253
AudioCtlCaptureGetMuteStu(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)254 int32_t AudioCtlCaptureGetMuteStu(
255 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
256 {
257 struct AudioCardInfo *cardInstance;
258
259 (void)cmdId;
260 if (handle == NULL || handleData == NULL) {
261 AUDIO_FUNC_LOGE("param is NULL!");
262 return HDF_FAILURE;
263 }
264
265 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
266 cardInstance = GetCardIns(adapterName);
267 if (cardInstance == NULL) {
268 AUDIO_FUNC_LOGE("cardInsance is null pointer!!");
269 return HDF_FAILURE;
270 }
271
272 if (strncmp(adapterName, USB, strlen(USB)) == 0) {
273 /* The external Settings. */
274 return HDF_SUCCESS;
275 }
276 handleData->captureMode.ctlParam.mute = (bool)cardInstance->captureMuteValue;
277
278 return HDF_SUCCESS;
279 }
280
AudioCtlCaptureSetGainStu(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)281 int32_t AudioCtlCaptureSetGainStu(
282 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
283 {
284 (void)cmdId;
285 if (handle == NULL || handleData == NULL) {
286 AUDIO_FUNC_LOGE("param is NULL!");
287 return HDF_FAILURE;
288 }
289
290 return HDF_SUCCESS;
291 }
292
AudioCtlCaptureGetGainStu(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)293 int32_t AudioCtlCaptureGetGainStu(
294 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
295 {
296 (void)cmdId;
297 if (handle == NULL || handleData == NULL) {
298 AUDIO_FUNC_LOGE("param is NULL!");
299 return HDF_FAILURE;
300 }
301
302 return HDF_SUCCESS;
303 }
304
AudioCtlCaptureSceneSelect(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)305 int32_t AudioCtlCaptureSceneSelect(
306 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
307 {
308 int32_t deviceNum;
309
310 (void)cmdId;
311 if (handle == NULL || handleData == NULL) {
312 AUDIO_FUNC_LOGE("param is NULL!");
313 return HDF_FAILURE;
314 }
315
316 deviceNum = handleData->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum;
317 if (deviceNum < AUDIO_MIN_CARD_NUM) {
318 AUDIO_FUNC_LOGE("Not find device!");
319 return HDF_FAILURE;
320 }
321
322 return HDF_SUCCESS;
323 }
324
AudioCtlCaptureGetGainThreshold(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)325 int32_t AudioCtlCaptureGetGainThreshold(
326 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
327 {
328 (void)cmdId;
329 if (handle == NULL || handleData == NULL) {
330 AUDIO_FUNC_LOGE("param is NULL!");
331 return HDF_FAILURE;
332 }
333
334 return HDF_SUCCESS;
335 }
336
AudioCtlCaptureGetVolThreshold(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)337 int32_t AudioCtlCaptureGetVolThreshold(
338 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
339 {
340 int32_t ret;
341 long volMax = MIN_VOLUME;
342 long volMin = MIN_VOLUME;
343
344 (void)cmdId;
345 if (handle == NULL || handleData == NULL) {
346 AUDIO_FUNC_LOGE("Param is NULL!");
347 return HDF_FAILURE;
348 }
349
350 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
351 struct AudioCardInfo *cardIns = GetCardIns(adapterName);
352 if (cardIns == NULL) {
353 AUDIO_FUNC_LOGE("cardIns is NULL!!!");
354 return HDF_FAILURE;
355 }
356
357 if (strncmp(adapterName, USB, strlen(USB)) == 0) {
358 handleData->captureMode.ctlParam.volThreshold.volMax = MAX_VOLUME;
359 handleData->captureMode.ctlParam.volThreshold.volMin = MIN_VOLUME;
360 return HDF_SUCCESS;
361 }
362
363 ret = snd_mixer_selem_get_capture_volume_range(cardIns->ctrlLeftVolume, &volMin, &volMax);
364 if (ret < 0) {
365 AUDIO_FUNC_LOGE("Get capture volume range fail: %{public}s.", snd_strerror(ret));
366 return HDF_FAILURE;
367 }
368 handleData->captureMode.ctlParam.volThreshold.volMax = (int)volMax;
369 handleData->captureMode.ctlParam.volThreshold.volMin = (int)volMin;
370
371 return HDF_SUCCESS;
372 }
373
AudioInterfaceLibCtlCapture(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)374 int32_t AudioInterfaceLibCtlCapture(
375 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
376 {
377 int32_t ret;
378
379 if (handle == NULL || handleData == NULL) {
380 AUDIO_FUNC_LOGE("param is NULL!");
381 return HDF_FAILURE;
382 }
383
384 switch (cmdId) {
385 /* setPara: */
386 case AUDIODRV_CTL_IOCTL_ELEM_WRITE_CAPTURE:
387 ret = AudioCtlCaptureSetVolume(handle, cmdId, handleData);
388 break;
389 case AUDIODRV_CTL_IOCTL_MUTE_WRITE_CAPTURE:
390 ret = AudioCtlCaptureSetMuteStu(handle, cmdId, handleData);
391 break;
392 case AUDIODRV_CTL_IOCTL_MUTE_READ_CAPTURE:
393 ret = AudioCtlCaptureGetMuteStu(handle, cmdId, handleData);
394 break;
395 /* getPara: */
396 case AUDIODRV_CTL_IOCTL_ELEM_READ_CAPTURE:
397 ret = AudioCtlCaptureGetVolume(handle, cmdId, handleData);
398 break;
399 case AUDIODRV_CTL_IOCTL_GAIN_WRITE_CAPTURE:
400 ret = AudioCtlCaptureSetGainStu(handle, cmdId, handleData);
401 break;
402 case AUDIODRV_CTL_IOCTL_GAIN_READ_CAPTURE:
403 ret = AudioCtlCaptureGetGainStu(handle, cmdId, handleData);
404 break;
405 case AUDIODRV_CTL_IOCTL_SCENESELECT_CAPTURE:
406 ret = AudioCtlCaptureSceneSelect(handle, cmdId, handleData);
407 break;
408 case AUDIODRV_CTL_IOCTL_GAINTHRESHOLD_CAPTURE:
409 ret = AudioCtlCaptureGetGainThreshold(handle, cmdId, handleData);
410 break;
411 case AUDIODRV_CTL_IOCTL_VOL_THRESHOLD_CAPTURE:
412 ret = AudioCtlCaptureGetVolThreshold(handle, cmdId, handleData);
413 break;
414 default:
415 AUDIO_FUNC_LOGE("Ctl Mode not support!");
416 ret = HDF_FAILURE;
417 break;
418 }
419
420 return ret;
421 }
422
GetCapHwParams(struct AudioCardInfo * cardIns,const struct AudioHwCaptureParam * handleData)423 static int32_t GetCapHwParams(struct AudioCardInfo *cardIns, const struct AudioHwCaptureParam *handleData)
424 {
425 if (cardIns == NULL || handleData == NULL) {
426 AUDIO_FUNC_LOGE("Parameter is NULL!");
427 return HDF_FAILURE;
428 }
429
430 cardIns->hwCaptureParams.streamType = AUDIO_CAPTURE_STREAM;
431 cardIns->hwCaptureParams.channels = handleData->frameCaptureMode.attrs.channelCount;
432 cardIns->hwCaptureParams.rate = handleData->frameCaptureMode.attrs.sampleRate;
433 cardIns->hwCaptureParams.periodSize = handleData->frameCaptureMode.periodSize;
434 cardIns->hwCaptureParams.periodCount = handleData->frameCaptureMode.periodCount;
435 cardIns->hwCaptureParams.format = handleData->frameCaptureMode.attrs.format;
436 cardIns->hwCaptureParams.period = handleData->frameCaptureMode.attrs.period;
437 cardIns->hwCaptureParams.frameSize = handleData->frameCaptureMode.attrs.frameSize;
438 cardIns->hwCaptureParams.isBigEndian = handleData->frameCaptureMode.attrs.isBigEndian;
439 cardIns->hwCaptureParams.isSignedData = handleData->frameCaptureMode.attrs.isSignedData;
440 cardIns->hwCaptureParams.startThreshold = handleData->frameCaptureMode.attrs.startThreshold;
441 cardIns->hwCaptureParams.stopThreshold = handleData->frameCaptureMode.attrs.stopThreshold;
442 cardIns->hwCaptureParams.silenceThreshold = handleData->frameCaptureMode.attrs.silenceThreshold;
443
444 return HDF_SUCCESS;
445 }
446
SetHWParamsSub(snd_pcm_t * handle,snd_pcm_hw_params_t * params,struct AudioPcmHwParams hwCapParams,snd_pcm_access_t access)447 static int32_t SetHWParamsSub(
448 snd_pcm_t *handle, snd_pcm_hw_params_t *params, struct AudioPcmHwParams hwCapParams, snd_pcm_access_t access)
449 {
450 int32_t ret;
451 snd_pcm_format_t pcmFormat;
452
453 if (handle == NULL || params == NULL) {
454 AUDIO_FUNC_LOGE("SetHWParamsSub parameter is null!");
455 return HDF_FAILURE;
456 }
457
458 ret = snd_pcm_hw_params_set_rate_resample(handle, params, g_resample);
459 if (ret < 0) {
460 AUDIO_FUNC_LOGE("Resampling setup failed for capture: %{public}s", snd_strerror(ret));
461 return HDF_FAILURE;
462 }
463
464 /* set the interleaved read/write format */
465 ret = snd_pcm_hw_params_set_access(handle, params, access);
466 if (ret < 0) {
467 AUDIO_FUNC_LOGE("Access type not available for capture: %{public}s", snd_strerror(ret));
468 return HDF_FAILURE;
469 }
470 ret = CheckParaFormat(hwCapParams, &pcmFormat);
471 if (ret != HDF_SUCCESS) {
472 AUDIO_FUNC_LOGE("CheckParaFormat error.");
473 return ret;
474 }
475 /* set the sample format */
476 ret = snd_pcm_hw_params_set_format(handle, params, pcmFormat);
477 if (ret < 0) {
478 AUDIO_FUNC_LOGE("Sample format not available for capture: %{public}s", snd_strerror(ret));
479 return HDF_FAILURE;
480 }
481
482 /* set the count of channels */
483 ret = snd_pcm_hw_params_set_channels(handle, params, hwCapParams.channels);
484 if (ret < 0) {
485 AUDIO_FUNC_LOGE("Channels count (%{public}u) not available for capture: %{public}s", hwCapParams.channels,
486 snd_strerror(ret));
487 return HDF_FAILURE;
488 }
489
490 return HDF_SUCCESS;
491 }
492
SetHWRate(snd_pcm_t * handle,snd_pcm_hw_params_t * params,uint32_t * rate)493 static int32_t SetHWRate(snd_pcm_t *handle, snd_pcm_hw_params_t *params, uint32_t *rate)
494 {
495 int32_t ret;
496 uint32_t rRate;
497 int32_t dir = 0; /* dir Value range (-1,0,1) */
498
499 if (handle == NULL || params == NULL || rate == NULL) {
500 AUDIO_FUNC_LOGE("SetHWParams parameter is null!");
501 return HDF_FAILURE;
502 }
503
504 /* set the stream rate */
505 rRate = *rate;
506 ret = snd_pcm_hw_params_set_rate_near(handle, params, &rRate, &dir);
507 if (ret < 0) {
508 AUDIO_FUNC_LOGE("Rate %{public}uHz not available for capture: %{public}s", *rate, snd_strerror(ret));
509 return HDF_FAILURE;
510 }
511
512 if (rRate != *rate) {
513 ret = snd_pcm_hw_params_set_rate_near(handle, params, &rRate, &dir);
514 if (ret < 0) {
515 AUDIO_FUNC_LOGE("Rate %{public}uHz not available for capture: %{public}s", *rate, snd_strerror(ret));
516 return HDF_FAILURE;
517 }
518 }
519 /* Update to hardware supported rate */
520 *rate = rRate;
521
522 g_canPause = snd_pcm_hw_params_can_pause(params);
523
524 return HDF_SUCCESS;
525 }
526
SetHWBuffer(snd_pcm_t * handle,snd_pcm_hw_params_t * params)527 static int32_t SetHWBuffer(snd_pcm_t *handle, snd_pcm_hw_params_t *params)
528 {
529 int32_t ret;
530 int32_t dir = 0; /* dir Value range (-1,0,1) */
531 snd_pcm_uframes_t size = 0;
532
533 if (handle == NULL || params == NULL) {
534 AUDIO_FUNC_LOGE("SetHWParams parameter is null!");
535 return HDF_FAILURE;
536 }
537
538 ret = snd_pcm_hw_params_set_buffer_time_near(handle, params, &g_bufferTime, &dir);
539 if (ret < 0) {
540 AUDIO_FUNC_LOGE(
541 "Unable to set buffer time %{public}u for capture: %{public}s", g_bufferTime, snd_strerror(ret));
542 return HDF_FAILURE;
543 }
544
545 ret = snd_pcm_hw_params_get_buffer_size(params, &size);
546 if (ret < 0) {
547 AUDIO_FUNC_LOGE("Unable to get buffer size for capture: %{public}s", snd_strerror(ret));
548 return HDF_FAILURE;
549 }
550 g_bufferSize = size;
551
552 return HDF_SUCCESS;
553 }
554
SetHWPeriod(snd_pcm_t * handle,snd_pcm_hw_params_t * params)555 static int32_t SetHWPeriod(snd_pcm_t *handle, snd_pcm_hw_params_t *params)
556 {
557 int32_t ret;
558 int32_t dir = 0; /* dir Value range (-1,0,1) */
559 snd_pcm_uframes_t size = 0;
560
561 if (handle == NULL || params == NULL) {
562 AUDIO_FUNC_LOGE("SetHWParams parameter is null!");
563 return HDF_FAILURE;
564 }
565
566 ret = snd_pcm_hw_params_set_period_time_near(handle, params, &g_periodTime, &dir);
567 if (ret < 0) {
568 AUDIO_FUNC_LOGE(
569 "Unable to set period time %{public}u for capture: %{public}s", g_periodTime, snd_strerror(ret));
570 return HDF_FAILURE;
571 }
572
573 ret = snd_pcm_hw_params_get_period_size(params, &size, &dir);
574 if (ret < 0) {
575 AUDIO_FUNC_LOGE("Unable to get period size for capture: %{public}s", snd_strerror(ret));
576 return HDF_FAILURE;
577 }
578 g_periodSize = size;
579
580 return HDF_SUCCESS;
581 }
582
SetHWParams(snd_pcm_t * handle,snd_pcm_hw_params_t * params,struct AudioPcmHwParams hwCapParams,snd_pcm_access_t access)583 static int32_t SetHWParams(
584 snd_pcm_t *handle, snd_pcm_hw_params_t *params, struct AudioPcmHwParams hwCapParams, snd_pcm_access_t access)
585 {
586 int32_t ret;
587
588 if (handle == NULL || params == NULL) {
589 AUDIO_FUNC_LOGE("SetHWParams parameter is null!");
590 return HDF_FAILURE;
591 }
592
593 ret = snd_pcm_hw_params_any(handle, params); // choose all parameters
594 if (ret < 0) {
595 AUDIO_FUNC_LOGE(
596 "Broken configuration for capture: no configurations available: %{public}s.", snd_strerror(ret));
597 return HDF_FAILURE;
598 }
599
600 ret = SetHWParamsSub(handle, params, hwCapParams, access);
601 if (ret != HDF_SUCCESS) {
602 AUDIO_FUNC_LOGE("SetHWParamsSub failed!");
603 return ret;
604 }
605
606 ret = SetHWRate(handle, params, &(hwCapParams.rate));
607 if (ret != HDF_SUCCESS) {
608 AUDIO_FUNC_LOGE("SetHWRate failed!");
609 return ret;
610 }
611
612 ret = SetHWBuffer(handle, params);
613 if (ret != HDF_SUCCESS) {
614 AUDIO_FUNC_LOGE("SetHWBuffer failed!");
615 return ret;
616 }
617
618 ret = SetHWPeriod(handle, params);
619 if (ret != HDF_SUCCESS) {
620 AUDIO_FUNC_LOGE("SetHWPeriod failed!");
621 return ret;
622 }
623
624 /* write the parameters to device. */
625 ret = snd_pcm_hw_params(handle, params);
626 if (ret < 0) {
627 AUDIO_FUNC_LOGE("Unable to set hw params for capture: %{public}s", snd_strerror(ret));
628 return HDF_FAILURE;
629 }
630
631 return HDF_SUCCESS;
632 }
633
SetSWParams(snd_pcm_t * handle,snd_pcm_sw_params_t * swparams)634 static int32_t SetSWParams(snd_pcm_t *handle, snd_pcm_sw_params_t *swparams)
635 {
636 int32_t ret;
637
638 if (handle == NULL || swparams == NULL) {
639 AUDIO_FUNC_LOGE("SetHWParams parameter is null!");
640 return HDF_FAILURE;
641 }
642
643 /* get the current swparams */
644 ret = snd_pcm_sw_params_current(handle, swparams);
645 if (ret < 0) {
646 AUDIO_FUNC_LOGE("Unable to determine current swparams for capture: %{public}s.", snd_strerror(ret));
647 return HDF_FAILURE;
648 }
649
650 if (g_periodSize == 0) {
651 AUDIO_FUNC_LOGE("error: g_periodSize cannot be zero!");
652 return HDF_FAILURE;
653 }
654 /* start the transfer when the buffer is almost full: */
655 /* (buffer_size / avail_min) * avail_min */
656 ret = snd_pcm_sw_params_set_start_threshold(handle, swparams, (g_bufferSize / g_periodSize) * g_periodSize);
657 if (ret < 0) {
658 AUDIO_FUNC_LOGE("Unable to set start threshold mode for capture: %{public}s.", snd_strerror(ret));
659 return HDF_FAILURE;
660 }
661
662 /* allow the transfer when at least period_size samples can be processed */
663 /* or disable this mechanism when period event is enabled (aka interrupt like style processing) */
664 ret = snd_pcm_sw_params_set_avail_min(handle, swparams, g_periodEvent ? g_bufferSize : g_periodSize);
665 if (ret < 0) {
666 AUDIO_FUNC_LOGE("Unable to set avail min for capture: %{public}s", snd_strerror(ret));
667 return HDF_FAILURE;
668 }
669
670 /* enable period events when requested */
671 if (g_periodEvent) {
672 ret = snd_pcm_sw_params_set_period_event(handle, swparams, 1);
673 if (ret < 0) {
674 AUDIO_FUNC_LOGE("Unable to set period event: %{public}s", snd_strerror(ret));
675 return HDF_FAILURE;
676 }
677 }
678
679 /* write the parameters to the capture device */
680 ret = snd_pcm_sw_params(handle, swparams);
681 if (ret < 0) {
682 AUDIO_FUNC_LOGE("Unable to set sw params for capture: %{public}s", snd_strerror(ret));
683 return HDF_FAILURE;
684 }
685
686 return HDF_SUCCESS;
687 }
688
AudioOutputCaptureHwParams(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)689 int32_t AudioOutputCaptureHwParams(
690 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
691 {
692 int32_t ret;
693 struct AudioCardInfo *cardIns;
694 snd_pcm_hw_params_t *hwParams = NULL;
695 snd_pcm_sw_params_t *swParams = NULL;
696
697 (void)cmdId;
698 if (handle == NULL || handleData == NULL) {
699 AUDIO_FUNC_LOGE("The parameter is empty");
700 return HDF_FAILURE;
701 }
702
703 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
704 cardIns = GetCardIns(adapterName);
705 if (cardIns == NULL) {
706 AUDIO_FUNC_LOGE("cardIns is NULL!");
707 return HDF_FAILURE;
708 }
709
710 ret = (int32_t)snd_pcm_state(cardIns->capturePcmHandle);
711 if (ret >= SND_PCM_STATE_RUNNING) {
712 AUDIO_FUNC_LOGE("Unable to set parameters during capture!");
713 return HDF_FAILURE;
714 }
715
716 ret = GetCapHwParams(cardIns, handleData);
717 if (ret != HDF_SUCCESS) {
718 AUDIO_FUNC_LOGE("GetCapHwParams error.");
719 return ret;
720 }
721
722 snd_pcm_hw_params_alloca(&hwParams);
723 snd_pcm_sw_params_alloca(&swParams);
724 ret = SetHWParams(cardIns->capturePcmHandle, hwParams, cardIns->hwCaptureParams, SND_PCM_ACCESS_RW_INTERLEAVED);
725 if (ret != HDF_SUCCESS) {
726 AUDIO_FUNC_LOGE("Setting of hwparams failed: %{public}d.", ret);
727 return ret;
728 }
729 ret = SetSWParams(cardIns->capturePcmHandle, swParams);
730 if (ret != HDF_SUCCESS) {
731 AUDIO_FUNC_LOGE("Setting of swparams failed: %{public}d.", ret);
732 return ret;
733 }
734
735 return HDF_SUCCESS;
736 }
737
InitMixerCtrlCapVolumeRange(const char * adapterName,struct AudioCardInfo * cardIns)738 static int32_t InitMixerCtrlCapVolumeRange(const char *adapterName, struct AudioCardInfo *cardIns)
739 {
740 int32_t ret;
741
742 if (cardIns == NULL || adapterName == NULL) {
743 AUDIO_FUNC_LOGE("The parameter is NULL");
744 return HDF_FAILURE;
745 }
746
747 if (strncmp(adapterName, USB, strlen(USB)) == 0) {
748 /* The external Settings. */
749 return HDF_SUCCESS;
750 }
751
752 if (cardIns->ctrlLeftVolume != NULL) {
753 ret = snd_mixer_selem_set_capture_volume_range(cardIns->ctrlLeftVolume, MIN_VOLUME, MAX_VOLUME);
754 if (ret < 0) {
755 AUDIO_FUNC_LOGE("Failed to set capture left volume range: %{public}s.", snd_strerror(ret));
756 return HDF_FAILURE;
757 }
758 }
759
760 if (cardIns->ctrlRightVolume != NULL) {
761 ret = snd_mixer_selem_set_capture_volume_range(cardIns->ctrlRightVolume, MIN_VOLUME, MAX_VOLUME);
762 if (ret < 0) {
763 AUDIO_FUNC_LOGE("Failed to set capture right volume range: %{public}s.", snd_strerror(ret));
764 return HDF_FAILURE;
765 }
766 }
767
768 return HDF_SUCCESS;
769 }
770
InitMixerCtlElement(const char * adapterName,struct AudioCardInfo * cardIns,snd_mixer_t * mixer)771 static int32_t InitMixerCtlElement(const char *adapterName, struct AudioCardInfo *cardIns, snd_mixer_t *mixer)
772 {
773 int32_t ret;
774
775 if (adapterName == NULL || cardIns == NULL || mixer == NULL) {
776 AUDIO_FUNC_LOGE("The parameter is empty.");
777 return HDF_FAILURE;
778 }
779
780 snd_mixer_elem_t *pcmElement = snd_mixer_first_elem(mixer);
781 if (strncmp(adapterName, PRIMARY, strlen(PRIMARY)) == 0) {
782 ret = GetPriMixerCtlElement(cardIns, pcmElement);
783 if (ret != HDF_SUCCESS) {
784 AUDIO_FUNC_LOGE("Capture GetPriMixerCtlElement failed.");
785 return ret;
786 }
787 } else if (strncmp(adapterName, USB, strlen(USB)) == 0) {
788 cardIns->ctrlLeftVolume = AudioUsbFindElement(mixer);
789 } else {
790 AUDIO_FUNC_LOGE("The selected sound card not supported, please check!");
791 return HDF_FAILURE;
792 }
793
794 ret = InitMixerCtrlCapVolumeRange(adapterName, cardIns);
795 if (ret != HDF_SUCCESS) {
796 AUDIO_FUNC_LOGE("InitMixerCtrlCapVolumeRange fail!");
797 return ret;
798 }
799
800 ret = AudioMixerSetCtrlMode(cardIns, adapterName, "Capture MIC Path", SND_CAP_MIC_PATH, SND_IN_CARD_MAIN_MIC);
801 if (ret != HDF_SUCCESS) {
802 AUDIO_FUNC_LOGE("AudioMixerSetCtrlMode failed!");
803 return ret;
804 }
805
806 return HDF_SUCCESS;
807 }
808
809 /*
810 * brief: Opens a capture PCM
811 * param mode Open mode (see #SND_PCM_NONBLOCK, #SND_PCM_ASYNC)
812 */
AudioOutputCaptureOpen(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)813 int32_t AudioOutputCaptureOpen(
814 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
815 {
816 int32_t ret;
817 struct AudioCardInfo *cardIns;
818
819 (void)cmdId;
820 if (handle == NULL || handleData == NULL) {
821 AUDIO_FUNC_LOGE("Function parameter is NULL!");
822 return HDF_FAILURE;
823 }
824
825 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
826 cardIns = AudioGetCardInfo(adapterName, SND_PCM_STREAM_CAPTURE);
827 if (cardIns == NULL) {
828 AUDIO_FUNC_LOGE("AudioCaptureGetCardIns failed.");
829 return HDF_FAILURE;
830 }
831
832 if (cardIns->capturePcmHandle != NULL) {
833 AUDIO_FUNC_LOGE("Resource busy!!");
834 return HDF_ERR_DEVICE_BUSY;
835 }
836 ret = snd_pcm_open(&cardIns->capturePcmHandle, cardIns->devName, SND_PCM_STREAM_CAPTURE, SND_PCM_NONBLOCK);
837 if (ret < 0) {
838 AUDIO_FUNC_LOGE("Capture open device error: %{public}s.", snd_strerror(ret));
839 CheckCardStatus(cardIns);
840 (void)DestroyCardList();
841 return HDF_FAILURE;
842 }
843
844 InitSound(&cardIns->mixer, cardIns->ctrlName);
845 ret = InitMixerCtlElement(adapterName, cardIns, cardIns->mixer);
846 if (ret != HDF_SUCCESS) {
847 AUDIO_FUNC_LOGE("capture InitMixerCtlElement failed!");
848 (void)CloseMixerHandle(cardIns->mixer);
849 CheckCardStatus(cardIns);
850 (void)DestroyCardList();
851 return ret;
852 }
853
854 return HDF_SUCCESS;
855 }
856
AudioCaptureResetParams(snd_pcm_t * handle,struct AudioPcmHwParams audioHwParams,snd_pcm_access_t access)857 int32_t AudioCaptureResetParams(snd_pcm_t *handle, struct AudioPcmHwParams audioHwParams, snd_pcm_access_t access)
858 {
859 int32_t ret;
860 snd_pcm_hw_params_t *hwParams = NULL;
861 snd_pcm_sw_params_t *swParams = NULL;
862
863 if (handle == NULL) {
864 AUDIO_FUNC_LOGE("handle is NULL!");
865 return HDF_FAILURE;
866 }
867
868 snd_pcm_hw_params_alloca(&hwParams);
869 snd_pcm_sw_params_alloca(&swParams);
870 ret = SetHWParams(handle, hwParams, audioHwParams, access);
871 if (ret != HDF_SUCCESS) {
872 AUDIO_FUNC_LOGE("Setting of hwparams failed: %{public}d.", ret);
873 return ret;
874 }
875
876 ret = SetSWParams(handle, swParams);
877 if (ret != HDF_SUCCESS) {
878 AUDIO_FUNC_LOGE("Setting of swparams failed: %{public}d.", ret);
879 return ret;
880 }
881
882 return HDF_SUCCESS;
883 }
884
CaptureDataCopy(struct AudioHwCaptureParam * handleData,char * buffer,uint64_t frames)885 static int32_t CaptureDataCopy(struct AudioHwCaptureParam *handleData, char *buffer, uint64_t frames)
886 {
887 int32_t ret;
888 uint32_t channels;
889 uint32_t format;
890 uint64_t recvDataSize;
891
892 if (handleData == NULL || buffer == NULL || frames == 0) {
893 AUDIO_FUNC_LOGE("Param is NULL!");
894 return HDF_FAILURE;
895 }
896
897 if (handleData->frameCaptureMode.buffer == NULL) {
898 AUDIO_FUNC_LOGE("frameCaptureMode.buffer is NULL!");
899 return HDF_FAILURE;
900 }
901 channels = handleData->frameCaptureMode.attrs.channelCount;
902 format = (uint32_t)handleData->frameCaptureMode.attrs.format;
903 recvDataSize = (uint64_t)(frames * channels * format);
904 ret = memcpy_s(handleData->frameCaptureMode.buffer, FRAME_DATA, buffer, recvDataSize);
905 if (ret != EOK) {
906 AUDIO_FUNC_LOGE("memcpy frame data failed!");
907 return HDF_FAILURE;
908 }
909 handleData->frameCaptureMode.bufferSize = recvDataSize;
910 handleData->frameCaptureMode.bufferFrameSize = frames;
911
912 return HDF_SUCCESS;
913 }
914
CheckCapFrameBufferSize(struct AudioHwCaptureParam * handleData,snd_pcm_uframes_t * periodSize)915 static int32_t CheckCapFrameBufferSize(struct AudioHwCaptureParam *handleData, snd_pcm_uframes_t *periodSize)
916 {
917 uint32_t capFrameSize;
918 uint64_t capReqBufferSize;
919
920 if (handleData == NULL || periodSize == NULL) {
921 AUDIO_FUNC_LOGE("Param is NULL!");
922 return HDF_FAILURE;
923 }
924
925 capFrameSize = handleData->frameCaptureMode.attrs.channelCount * handleData->frameCaptureMode.attrs.format;
926 if (capFrameSize == 0) {
927 AUDIO_FUNC_LOGE("capFrameSize is zero.");
928 return HDF_FAILURE;
929 }
930 capReqBufferSize = capFrameSize * (*periodSize);
931 if (capReqBufferSize > FRAME_DATA) {
932 *periodSize = FRAME_DATA / capFrameSize;
933 }
934
935 return HDF_SUCCESS;
936 }
937
CheckPcmStatus(snd_pcm_t * capturePcmHandle)938 static int32_t CheckPcmStatus(snd_pcm_t *capturePcmHandle)
939 {
940 int32_t ret;
941
942 if (capturePcmHandle == NULL) {
943 AUDIO_FUNC_LOGE("Param is NULL.");
944 return HDF_FAILURE;
945 }
946
947 ret = snd_pcm_wait(capturePcmHandle, -1); /* -1 for timeout, Waiting forever */
948 if (ret < 0) {
949 AUDIO_FUNC_LOGE("snd_pcm_wait failed: %{public}s.", snd_strerror(ret));
950 return HDF_FAILURE;
951 }
952
953 if (snd_pcm_state(capturePcmHandle) == SND_PCM_STATE_SETUP) {
954 ret = snd_pcm_prepare(capturePcmHandle);
955 if (ret < 0) {
956 AUDIO_FUNC_LOGE("snd_pcm_prepare fail: %{public}s", snd_strerror(ret));
957 return HDF_FAILURE;
958 }
959 }
960
961 return HDF_SUCCESS;
962 }
963
AudioCaptureReadFrameSub(snd_pcm_t * pcm,uint64_t * frameCnt,char * dataBuf,snd_pcm_uframes_t bufSize)964 static int32_t AudioCaptureReadFrameSub(snd_pcm_t *pcm, uint64_t *frameCnt, char *dataBuf, snd_pcm_uframes_t bufSize)
965 {
966 int32_t ret;
967 long frames;
968 int32_t tryNum = AUDIO_ALSALIB_RETYR;
969
970 if (pcm == NULL || frameCnt == NULL || dataBuf == NULL || bufSize == 0) {
971 AUDIO_FUNC_LOGE("The parameter is error.");
972 return HDF_FAILURE;
973 }
974
975 do {
976 /* Read interleaved frames to a PCM. */
977 frames = snd_pcm_readi(pcm, dataBuf, bufSize);
978 if (frames > 0) {
979 *frameCnt = (uint64_t)frames;
980 return HDF_SUCCESS;
981 }
982
983 if (frames == -EBADFD) {
984 AUDIO_FUNC_LOGE("capture PCM is not in the right state: %{public}s", snd_strerror(frames));
985 ret = snd_pcm_prepare(pcm);
986 if (ret < 0) {
987 AUDIO_FUNC_LOGE("capture snd_pcm_prepare fail: %{public}s", snd_strerror(ret));
988 return HDF_FAILURE;
989 }
990 } else {
991 /* -ESTRPIPE: a suspend event occurred,
992 * stream is suspended and waiting for an application recovery.
993 * -EPIPE: an underrun occurred.
994 */
995 ret = snd_pcm_recover(pcm, frames, 0); // 0 for open capture recover log.
996 if (ret < 0) {
997 AUDIO_FUNC_LOGE("snd_pcm_readi failed: %{public}s", snd_strerror(ret));
998 return HDF_FAILURE;
999 }
1000 }
1001 ret = snd_pcm_start(pcm);
1002 if (ret < 0) {
1003 AUDIO_FUNC_LOGE("snd_pcm_start fail. %{public}s", snd_strerror(ret));
1004 return HDF_FAILURE;
1005 }
1006 tryNum--;
1007 } while (tryNum > 0);
1008
1009 return HDF_SUCCESS;
1010 }
1011
AudioCaptureReadFrame(struct AudioHwCaptureParam * handleData,struct AudioCardInfo * cardIns,snd_pcm_uframes_t periodSize)1012 static int32_t AudioCaptureReadFrame(
1013 struct AudioHwCaptureParam *handleData, struct AudioCardInfo *cardIns, snd_pcm_uframes_t periodSize)
1014 {
1015 int32_t ret;
1016 uint64_t frames = 0;
1017 char *buffer = NULL;
1018
1019 if (handleData == NULL || cardIns == NULL) {
1020 AUDIO_FUNC_LOGE("Param is NULL!");
1021 return HDF_FAILURE;
1022 }
1023
1024 buffer = OsalMemCalloc(ALSA_CAP_BUFFER_SIZE);
1025 if (buffer == NULL) {
1026 AUDIO_FUNC_LOGE("Failed to Calloc buffer");
1027 return HDF_FAILURE;
1028 }
1029
1030 ret = CheckCapFrameBufferSize(handleData, &periodSize);
1031 if (ret != HDF_SUCCESS) {
1032 AUDIO_FUNC_LOGE("CheckCapFrameBufferSize failed.");
1033 AudioMemFree((void **)&buffer);
1034 return ret;
1035 }
1036
1037 ret = CheckPcmStatus(cardIns->capturePcmHandle);
1038 if (ret != HDF_SUCCESS) {
1039 AUDIO_FUNC_LOGE("CheckPcmStatus failed.");
1040 AudioMemFree((void **)&buffer);
1041 return ret;
1042 }
1043
1044 ret = AudioCaptureReadFrameSub(cardIns->capturePcmHandle, &frames, buffer, periodSize);
1045 if (ret != HDF_SUCCESS) {
1046 AUDIO_FUNC_LOGE("AudioCaptureReadFrameSub is error!");
1047 AudioMemFree((void **)&buffer);
1048 return ret;
1049 }
1050
1051 ret = CaptureDataCopy(handleData, buffer, frames);
1052 if (ret != HDF_SUCCESS) {
1053 AUDIO_FUNC_LOGE("Failed to copy data. It may be paused. Check the status!");
1054 AudioMemFree((void **)&buffer);
1055 return ret;
1056 }
1057 AudioMemFree((void **)&buffer);
1058
1059 return HDF_SUCCESS;
1060 }
1061
AudioOutputCaptureRead(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)1062 int32_t AudioOutputCaptureRead(const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
1063 {
1064 int32_t ret;
1065 snd_pcm_uframes_t bufferSize = 0;
1066 snd_pcm_uframes_t periodSize = 0;
1067
1068 (void)cmdId;
1069 if (handle == NULL || handleData == NULL) {
1070 AUDIO_FUNC_LOGE("Param is NULL!");
1071 return HDF_FAILURE;
1072 }
1073
1074 const char *sndCardName = handleData->captureMode.hwInfo.adapterName;
1075 struct AudioCardInfo *cardIns = GetCardIns(sndCardName);
1076 if (cardIns == NULL) {
1077 AUDIO_FUNC_LOGE("cardIns is NULL!");
1078 return HDF_FAILURE;
1079 }
1080
1081 ret = snd_pcm_get_params(cardIns->capturePcmHandle, &bufferSize, &periodSize);
1082 if (ret < 0) {
1083 AUDIO_FUNC_LOGE("Get capture params error: %{public}s.", snd_strerror(ret));
1084 return HDF_FAILURE;
1085 }
1086
1087 if (!cardIns->captureMmapFlag) {
1088 ret =
1089 AudioCaptureResetParams(cardIns->capturePcmHandle, cardIns->hwCaptureParams, SND_PCM_ACCESS_RW_INTERLEAVED);
1090 if (ret != HDF_SUCCESS) {
1091 AUDIO_FUNC_LOGE("AudioSetParamsMmap failed!");
1092 return ret;
1093 }
1094 ret = snd_pcm_start(cardIns->capturePcmHandle);
1095 if (ret < 0) {
1096 AUDIO_FUNC_LOGE("snd_pcm_start fail. %{public}s", snd_strerror(ret));
1097 return HDF_FAILURE;
1098 }
1099 cardIns->captureMmapFlag = true;
1100 }
1101
1102 ret = AudioCaptureReadFrame(handleData, cardIns, periodSize);
1103 if (ret != HDF_SUCCESS) {
1104 AUDIO_FUNC_LOGE("AudioOutputCaptureRead failed");
1105 return ret;
1106 }
1107
1108 return HDF_SUCCESS;
1109 }
1110
AudioOutputCaptureStart(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)1111 int32_t AudioOutputCaptureStart(
1112 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
1113 {
1114 (void)cmdId;
1115 if (handle == NULL || handleData == NULL) {
1116 AUDIO_FUNC_LOGE("Param is NULL!");
1117 return HDF_FAILURE;
1118 }
1119
1120 return HDF_SUCCESS;
1121 }
1122
AudioOutputCapturePrepare(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)1123 int32_t AudioOutputCapturePrepare(
1124 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
1125 {
1126 int32_t ret;
1127 struct AudioCardInfo *cardIns;
1128
1129 (void)cmdId;
1130 if (handle == NULL || handleData == NULL) {
1131 AUDIO_FUNC_LOGE("Invalid parameters!!!");
1132 return HDF_FAILURE;
1133 }
1134
1135 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
1136 cardIns = GetCardIns(adapterName);
1137 if (cardIns == NULL) {
1138 AUDIO_FUNC_LOGE("Get cardIns is failed!!!");
1139 return HDF_FAILURE;
1140 }
1141
1142 ret = snd_pcm_prepare(cardIns->capturePcmHandle);
1143 if (ret < 0) {
1144 AUDIO_FUNC_LOGE("snd_pcm_prepare fail! %{public}s.", snd_strerror(ret));
1145 return HDF_FAILURE;
1146 }
1147
1148 return HDF_SUCCESS;
1149 }
1150
AudioOutputCaptureClose(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)1151 int32_t AudioOutputCaptureClose(
1152 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
1153 {
1154 int32_t ret;
1155 struct AudioCardInfo *cardIns;
1156
1157 (void)cmdId;
1158 if (handle == NULL || handleData == NULL) {
1159 AUDIO_FUNC_LOGE("Parameter is NULL!");
1160 return HDF_FAILURE;
1161 }
1162
1163 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
1164 cardIns = GetCardIns(adapterName);
1165 if (cardIns == NULL) {
1166 AUDIO_FUNC_LOGE("cardIns is NULL!");
1167 return HDF_FAILURE;
1168 }
1169
1170 if (cardIns->capturePcmHandle != NULL) {
1171 (void)snd_pcm_close(cardIns->capturePcmHandle);
1172 cardIns->capturePcmHandle = NULL;
1173 }
1174
1175 if (cardIns->cardStatus > 0) {
1176 cardIns->cardStatus -= 1;
1177 }
1178 if (cardIns->cardStatus == 0) {
1179 if (cardIns->mixer != NULL) {
1180 (void)snd_mixer_close(cardIns->mixer);
1181 cardIns->mixer = NULL;
1182 }
1183 (void)memset_s(cardIns->cardName, MAX_CARD_NAME_LEN + 1, 0, MAX_CARD_NAME_LEN + 1);
1184 ret = DestroyCardList();
1185 if (ret != HDF_SUCCESS) {
1186 AUDIO_FUNC_LOGE("DestroyCardList failed: %{public}d.", ret);
1187 return ret;
1188 }
1189 }
1190
1191 return HDF_SUCCESS;
1192 }
1193
1194 // Stop capture first, and then close the resource
AudioOutputCaptureStop(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)1195 int32_t AudioOutputCaptureStop(
1196 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
1197 {
1198 int32_t ret;
1199 struct AudioCardInfo *cardIns;
1200
1201 (void)cmdId;
1202 if (handle == NULL || handleData == NULL) {
1203 AUDIO_FUNC_LOGE("Param is NULL!");
1204 return HDF_FAILURE;
1205 }
1206
1207 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
1208 cardIns = GetCardIns(adapterName);
1209 if (cardIns == NULL) {
1210 AUDIO_FUNC_LOGE("Can't find sound card instance!!!");
1211 return HDF_FAILURE;
1212 }
1213
1214 /* pass the remaining samples, otherwise they're dropped in close */
1215 ret = snd_pcm_drop(cardIns->capturePcmHandle);
1216 if (ret < 0) {
1217 AUDIO_FUNC_LOGE("snd_pcm_drain failed: %{public}s.", snd_strerror(ret));
1218 return HDF_FAILURE;
1219 }
1220
1221 return HDF_SUCCESS;
1222 }
1223
UpdateSetParams(struct AudioCardInfo * cardIns)1224 static int32_t UpdateSetParams(struct AudioCardInfo *cardIns)
1225 {
1226 int32_t ret;
1227
1228 if (cardIns == NULL) {
1229 AUDIO_FUNC_LOGE("param is NULL!");
1230 return HDF_FAILURE;
1231 }
1232
1233 cardIns->captureMmapFlag = false;
1234 ret = AudioCaptureResetParams(cardIns->capturePcmHandle, cardIns->hwCaptureParams, SND_PCM_ACCESS_MMAP_INTERLEAVED);
1235 if (ret != HDF_SUCCESS) {
1236 AUDIO_FUNC_LOGE("AudioSetParamsMmap failed!");
1237 return ret;
1238 }
1239
1240 ret = snd_pcm_start(cardIns->capturePcmHandle);
1241 if (ret < 0) {
1242 AUDIO_FUNC_LOGE("snd_pcm_start fail. %{public}s.", snd_strerror(ret));
1243 return HDF_FAILURE;
1244 }
1245
1246 return HDF_SUCCESS;
1247 }
1248
MmapDescWriteBufferCapture(const struct AudioHwCaptureParam * handleData)1249 static int32_t MmapDescWriteBufferCapture(const struct AudioHwCaptureParam *handleData)
1250 {
1251 int32_t ret;
1252 char *mmapAddr;
1253 uint32_t frameSize;
1254 snd_pcm_sframes_t xfer;
1255 snd_pcm_uframes_t size;
1256 struct AudioCardInfo *cardIns;
1257
1258 if (handleData == NULL) {
1259 AUDIO_FUNC_LOGE("param is NULL!");
1260 return HDF_FAILURE;
1261 }
1262
1263 const char *adapterName = handleData->captureMode.hwInfo.adapterName;
1264 cardIns = GetCardIns(adapterName);
1265 if (cardIns == NULL) {
1266 AUDIO_FUNC_LOGE("cardIns is NULL!");
1267 return HDF_FAILURE;
1268 }
1269
1270 ret = UpdateSetParams(cardIns);
1271 if (ret != HDF_SUCCESS) {
1272 AUDIO_FUNC_LOGE("Update set params failed!");
1273 return ret;
1274 }
1275
1276 mmapAddr = (char *)handleData->frameCaptureMode.mmapBufDesc.memoryAddress;
1277 if (mmapAddr == NULL) {
1278 AUDIO_FUNC_LOGE("mmapAddr is NULL!");
1279 return HDF_FAILURE;
1280 }
1281 size = (snd_pcm_sframes_t)handleData->frameCaptureMode.mmapBufDesc.totalBufferFrames;
1282 frameSize = handleData->frameCaptureMode.attrs.channelCount * handleData->frameCaptureMode.attrs.format;
1283 while (size > 0) {
1284 xfer = snd_pcm_mmap_readi(cardIns->capturePcmHandle, mmapAddr, size);
1285 if (xfer < 0) {
1286 if (xfer == -EAGAIN) {
1287 snd_pcm_wait(cardIns->capturePcmHandle, AUDIO_PCM_WAIT);
1288 continue;
1289 }
1290 AUDIO_FUNC_LOGE("snd_pcm_mmap_readi: %{public}s", snd_strerror(xfer));
1291 return HDF_FAILURE;
1292 }
1293
1294 if (xfer > 0) {
1295 mmapAddr += xfer * frameSize;
1296 size -= xfer;
1297 cardIns->capMmapFrames += xfer;
1298 }
1299 }
1300
1301 return HDF_SUCCESS;
1302 }
1303
AudioOutputCaptureReqMmapBuffer(const struct DevHandleCapture * handle,int cmdId,const struct AudioHwCaptureParam * handleData)1304 int32_t AudioOutputCaptureReqMmapBuffer(
1305 const struct DevHandleCapture *handle, int cmdId, const struct AudioHwCaptureParam *handleData)
1306 {
1307 int32_t ret;
1308
1309 (void)cmdId;
1310 if (handle == NULL || handleData == NULL) {
1311 AUDIO_FUNC_LOGE("param is NULL!");
1312 return HDF_FAILURE;
1313 }
1314
1315 ret = MmapDescWriteBufferCapture(handleData);
1316 if (ret != HDF_SUCCESS) {
1317 AUDIO_FUNC_LOGE("Capture mmap write buffer failed!");
1318 return ret;
1319 }
1320
1321 return HDF_SUCCESS;
1322 }
1323
AudioOutputCaptureGetMmapPosition(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)1324 int32_t AudioOutputCaptureGetMmapPosition(
1325 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
1326 {
1327 struct AudioCardInfo *cardIns;
1328
1329 (void)cmdId;
1330 if (handle == NULL || handleData == NULL) {
1331 AUDIO_FUNC_LOGE("param is NULL!");
1332 return HDF_FAILURE;
1333 }
1334
1335 const char *cardName = handleData->captureMode.hwInfo.adapterName;
1336 cardIns = GetCardIns(cardName);
1337 if (cardIns == NULL) {
1338 AUDIO_FUNC_LOGE("Get cardIns is NULL!");
1339 return HDF_FAILURE;
1340 }
1341 handleData->frameCaptureMode.frames = cardIns->capMmapFrames;
1342
1343 return HDF_SUCCESS;
1344 }
1345
AudioBindServiceCaptureObject(struct DevHandleCapture * const handle,const char * name)1346 static int32_t AudioBindServiceCaptureObject(struct DevHandleCapture * const handle, const char *name)
1347 {
1348 int32_t ret;
1349 char *serviceName;
1350 struct HdfIoService *service;
1351
1352 if (handle == NULL || name == NULL) {
1353 AUDIO_FUNC_LOGE("service name or handle is NULL!");
1354 return HDF_FAILURE;
1355 }
1356
1357 serviceName = (char *)OsalMemCalloc(NAME_LEN);
1358 if (serviceName == NULL) {
1359 AUDIO_FUNC_LOGE("Failed to alloc serviceName");
1360 return HDF_FAILURE;
1361 }
1362
1363 ret = snprintf_s(serviceName, NAME_LEN - 1, SERVIC_NAME_MAX_LEN + 1, "hdf_audio_%s", name);
1364 if (ret < 0) {
1365 AudioMemFree((void **)&serviceName);
1366 return HDF_FAILURE;
1367 }
1368
1369 service = HdfIoServiceBindName(serviceName);
1370 if (service == NULL) {
1371 AUDIO_FUNC_LOGE("Capture: Failed to get service!");
1372 AudioMemFree((void **)&serviceName);
1373 return HDF_FAILURE;
1374 }
1375 AudioMemFree((void **)&serviceName);
1376 handle->object = service;
1377
1378 return HDF_SUCCESS;
1379 }
1380
1381 /* CreatCapture for Bind handle */
AudioBindServiceCapture(const char * name)1382 struct DevHandleCapture *AudioBindServiceCapture(const char *name)
1383 {
1384 int32_t ret;
1385 struct DevHandleCapture *handle = NULL;
1386
1387 if (name == NULL) {
1388 AUDIO_FUNC_LOGE("service name NULL!");
1389 return NULL;
1390 }
1391
1392 handle = (struct DevHandleCapture *)OsalMemCalloc(sizeof(struct DevHandleCapture));
1393 if (handle == NULL) {
1394 AUDIO_FUNC_LOGE("Failed to alloc handle");
1395 return NULL;
1396 }
1397
1398 ret = AudioBindServiceCaptureObject(handle, name);
1399 if (ret != HDF_SUCCESS) {
1400 AUDIO_FUNC_LOGE("AudioBindServiceCaptureObject failed!");
1401 AudioMemFree((void **)&handle);
1402 return NULL;
1403 }
1404
1405 /* Capture: Parsing primary sound card from configuration file */
1406 ret = CardInfoParseFromConfig();
1407 if (ret != HDF_SUCCESS) {
1408 AUDIO_FUNC_LOGE("Capture: parse config file failed!");
1409 AudioMemFree((void **)&handle);
1410 return NULL;
1411 }
1412 AUDIO_FUNC_LOGI("BIND SERVICE SUCCESS!");
1413
1414 return handle;
1415 }
1416
AudioCloseServiceCapture(const struct DevHandleCapture * handle)1417 void AudioCloseServiceCapture(const struct DevHandleCapture *handle)
1418 {
1419 if (handle != NULL) {
1420 if (handle->object == NULL) {
1421 AUDIO_FUNC_LOGE("Capture handle or handle->object is NULL");
1422 }
1423 AudioMemFree((void **)&handle);
1424 }
1425 }
1426
AudioInterfaceLibOutputCapture(const struct DevHandleCapture * handle,int cmdId,struct AudioHwCaptureParam * handleData)1427 int32_t AudioInterfaceLibOutputCapture(
1428 const struct DevHandleCapture *handle, int cmdId, struct AudioHwCaptureParam *handleData)
1429 {
1430 int32_t ret;
1431
1432 if (handle == NULL || handleData == NULL) {
1433 AUDIO_FUNC_LOGE("Parameter is NULL!");
1434 return HDF_FAILURE;
1435 }
1436
1437 switch (cmdId) {
1438 case AUDIO_DRV_PCM_IOCTL_HW_PARAMS:
1439 ret = AudioOutputCaptureHwParams(handle, cmdId, handleData);
1440 break;
1441 case AUDIO_DRV_PCM_IOCTL_READ:
1442 ret = AudioOutputCaptureRead(handle, cmdId, handleData);
1443 break;
1444 case AUDIO_DRV_PCM_IOCTRL_START_CAPTURE:
1445 ret = AudioOutputCaptureStart(handle, cmdId, handleData);
1446 break;
1447 case AUDIO_DRV_PCM_IOCTL_PREPARE_CAPTURE:
1448 ret = AudioOutputCapturePrepare(handle, cmdId, handleData);
1449 break;
1450 case AUDIO_DRV_PCM_IOCTRL_CAPTURE_CLOSE:
1451 ret = AudioOutputCaptureClose(handle, cmdId, handleData);
1452 break;
1453 case AUDIO_DRV_PCM_IOCTRL_CAPTURE_OPEN:
1454 ret = AudioOutputCaptureOpen(handle, cmdId, handleData);
1455 break;
1456 case AUDIO_DRV_PCM_IOCTRL_STOP_CAPTURE:
1457 ret = AudioOutputCaptureStop(handle, cmdId, handleData);
1458 break;
1459 case AUDIODRV_CTL_IOCTL_PAUSE_WRITE_CAPTURE:
1460 ret = AudioCtlCaptureSetPauseStu(handle, cmdId, handleData);
1461 break;
1462 case AUDIO_DRV_PCM_IOCTL_MMAP_BUFFER_CAPTURE:
1463 ret = AudioOutputCaptureReqMmapBuffer(handle, cmdId, handleData);
1464 break;
1465 case AUDIO_DRV_PCM_IOCTL_MMAP_POSITION_CAPTURE:
1466 ret = AudioOutputCaptureGetMmapPosition(handle, cmdId, handleData);
1467 break;
1468 default:
1469 AUDIO_FUNC_LOGE("Output Mode not support!");
1470 ret = HDF_FAILURE;
1471 break;
1472 }
1473
1474 return ret;
1475 }
1476
AudioInterfaceLibModeCapture(const struct DevHandleCapture * handle,struct AudioHwCaptureParam * handleData,int cmdId)1477 int32_t AudioInterfaceLibModeCapture(
1478 const struct DevHandleCapture *handle, struct AudioHwCaptureParam *handleData, int cmdId)
1479 {
1480 AUDIO_FUNC_LOGI();
1481 if (handle == NULL || handleData == NULL) {
1482 AUDIO_FUNC_LOGE("paras is NULL!");
1483 return HDF_FAILURE;
1484 }
1485
1486 switch (cmdId) {
1487 case AUDIO_DRV_PCM_IOCTL_HW_PARAMS:
1488 case AUDIO_DRV_PCM_IOCTL_READ:
1489 case AUDIO_DRV_PCM_IOCTRL_START_CAPTURE:
1490 case AUDIO_DRV_PCM_IOCTRL_STOP_CAPTURE:
1491 case AUDIO_DRV_PCM_IOCTL_PREPARE_CAPTURE:
1492 case AUDIODRV_CTL_IOCTL_PAUSE_WRITE_CAPTURE:
1493 case AUDIO_DRV_PCM_IOCTL_MMAP_BUFFER_CAPTURE:
1494 case AUDIO_DRV_PCM_IOCTL_MMAP_POSITION_CAPTURE:
1495 case AUDIO_DRV_PCM_IOCTRL_CAPTURE_OPEN:
1496 case AUDIO_DRV_PCM_IOCTRL_CAPTURE_CLOSE:
1497 return (AudioInterfaceLibOutputCapture(handle, cmdId, handleData));
1498 case AUDIODRV_CTL_IOCTL_ELEM_WRITE_CAPTURE:
1499 case AUDIODRV_CTL_IOCTL_ELEM_READ_CAPTURE:
1500 case AUDIODRV_CTL_IOCTL_MUTE_WRITE_CAPTURE:
1501 case AUDIODRV_CTL_IOCTL_MUTE_READ_CAPTURE:
1502 case AUDIODRV_CTL_IOCTL_GAIN_WRITE_CAPTURE:
1503 case AUDIODRV_CTL_IOCTL_GAIN_READ_CAPTURE:
1504 case AUDIODRV_CTL_IOCTL_SCENESELECT_CAPTURE:
1505 case AUDIODRV_CTL_IOCTL_GAINTHRESHOLD_CAPTURE:
1506 case AUDIODRV_CTL_IOCTL_VOL_THRESHOLD_CAPTURE:
1507 return (AudioInterfaceLibCtlCapture(handle, cmdId, handleData));
1508 default:
1509 AUDIO_FUNC_LOGE("Mode Error!");
1510 break;
1511 }
1512
1513 return HDF_ERR_NOT_SUPPORT;
1514 }
1515