blob: f1ae71951e9ed953174d61d24c2119b2568790f3 [file] [log] [blame]
Soumya Managolid11d6f02020-05-27 17:25:12 +05301// SPDX-License-Identifier: GPL-2.0-only
2/*
3 * Copyright (c) 2015-2020, The Linux Foundation. All rights reserved.
4 */
5
6#include <linux/of_gpio.h>
7#include <linux/platform_device.h>
8#include <linux/module.h>
9#include <sound/pcm_params.h>
10#include "msm-pcm-routing-v2.h"
11#include <asoc/sdm660-common.h>
12#include <asoc/msm-cdc-pinctrl.h>
13#include "codecs/sdm660_cdc/msm-digital-cdc.h"
14#include "codecs/sdm660_cdc/msm-analog-cdc.h"
15#include "codecs/msm_sdw/msm_sdw.h"
16#include <linux/pm_qos.h>
17
18#define __CHIPSET__ "SDM660 "
19#define MSM_DAILINK_NAME(name) (__CHIPSET__#name)
20
21#define WCD_MBHC_DEF_RLOADS 5
22
23#define WCN_CDC_SLIM_RX_CH_MAX 2
24#define WCN_CDC_SLIM_TX_CH_MAX 3
25
26#define WSA8810_NAME_1 "wsa881x.20170211"
27#define WSA8810_NAME_2 "wsa881x.20170212"
28#define MSM_LL_QOS_VALUE 300 /* time in us to ensure LPM doesn't go in C3/C4 */
29enum {
30 INT0_MI2S = 0,
31 INT1_MI2S,
32 INT2_MI2S,
33 INT3_MI2S,
34 INT4_MI2S,
35 INT5_MI2S,
36 INT6_MI2S,
37 INT_MI2S_MAX,
38};
39
40enum {
41 BT_SLIM7,
42 FM_SLIM8,
43 SLIM_MAX,
44};
45
46static struct afe_clk_set int_mi2s_clk[INT_MI2S_MAX] = {
47 {
48 AFE_API_VERSION_I2S_CONFIG,
49 Q6AFE_LPASS_CLK_ID_INT0_MI2S_IBIT,
50 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
51 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
52 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
53 0,
54 },
55 {
56 AFE_API_VERSION_I2S_CONFIG,
57 Q6AFE_LPASS_CLK_ID_INT1_MI2S_IBIT,
58 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
59 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
60 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
61 0,
62 },
63 {
64 AFE_API_VERSION_I2S_CONFIG,
65 Q6AFE_LPASS_CLK_ID_INT2_MI2S_IBIT,
66 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
67 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
68 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
69 0,
70 },
71 {
72 AFE_API_VERSION_I2S_CONFIG,
73 Q6AFE_LPASS_CLK_ID_INT3_MI2S_IBIT,
74 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
75 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
76 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
77 0,
78 },
79 {
80 AFE_API_VERSION_I2S_CONFIG,
81 Q6AFE_LPASS_CLK_ID_INT4_MI2S_IBIT,
82 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
83 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
84 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
85 0,
86 },
87 {
88 AFE_API_VERSION_I2S_CONFIG,
89 Q6AFE_LPASS_CLK_ID_INT5_MI2S_IBIT,
90 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
91 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
92 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
93 0,
94 },
95 {
96 AFE_API_VERSION_I2S_CONFIG,
97 Q6AFE_LPASS_CLK_ID_INT6_MI2S_IBIT,
98 Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ,
99 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO,
100 Q6AFE_LPASS_CLK_ROOT_DEFAULT,
101 0,
102 },
103};
104
105/* Default configuration of MI2S channels */
106static struct dev_config int_mi2s_cfg[] = {
107 [INT0_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 2},
108 [INT1_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 1},
109 [INT2_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 1},
110 [INT3_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 1},
111 [INT4_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 1},
112 [INT5_MI2S] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 2},
113 [INT6_MI2S] = {SAMPLING_RATE_8KHZ, SNDRV_PCM_FORMAT_S16_LE, 2},
114};
115
116static struct dev_config bt_fm_cfg[] = {
117 [BT_SLIM7] = {SAMPLING_RATE_8KHZ, SNDRV_PCM_FORMAT_S16_LE, 1},
118 [FM_SLIM8] = {SAMPLING_RATE_48KHZ, SNDRV_PCM_FORMAT_S16_LE, 2},
119};
120
121static char const *int_mi2s_rate_text[] = {"KHZ_8", "KHZ_16",
122 "KHZ_32", "KHZ_44P1", "KHZ_48",
123 "KHZ_96", "KHZ_192"};
124static const char *const int_mi2s_ch_text[] = {"One", "Two"};
125static const char *const int_mi2s_tx_ch_text[] = {"One", "Two",
126 "Three", "Four"};
127static char const *bit_format_text[] = {"S16_LE", "S24_LE", "S24_3LE"};
128static const char *const loopback_mclk_text[] = {"DISABLE", "ENABLE"};
129static char const *bt_sample_rate_text[] = {"KHZ_8", "KHZ_16",
130 "KHZ_44P1", "KHZ_48",
131 "KHZ_88P2", "KHZ_96"};
132
133static SOC_ENUM_SINGLE_EXT_DECL(int0_mi2s_rx_sample_rate, int_mi2s_rate_text);
134static SOC_ENUM_SINGLE_EXT_DECL(int0_mi2s_rx_chs, int_mi2s_ch_text);
135static SOC_ENUM_SINGLE_EXT_DECL(int0_mi2s_rx_format, bit_format_text);
136static SOC_ENUM_SINGLE_EXT_DECL(int2_mi2s_tx_sample_rate, int_mi2s_rate_text);
137static SOC_ENUM_SINGLE_EXT_DECL(int2_mi2s_tx_chs, int_mi2s_tx_ch_text);
138static SOC_ENUM_SINGLE_EXT_DECL(int2_mi2s_tx_format, bit_format_text);
139static SOC_ENUM_SINGLE_EXT_DECL(int3_mi2s_tx_sample_rate, int_mi2s_rate_text);
140static SOC_ENUM_SINGLE_EXT_DECL(int3_mi2s_tx_chs, int_mi2s_tx_ch_text);
141static SOC_ENUM_SINGLE_EXT_DECL(int3_mi2s_tx_format, bit_format_text);
142static SOC_ENUM_SINGLE_EXT_DECL(int4_mi2s_rx_sample_rate, int_mi2s_rate_text);
143static SOC_ENUM_SINGLE_EXT_DECL(int4_mi2s_rx_chs, int_mi2s_ch_text);
144static SOC_ENUM_SINGLE_EXT_DECL(int4_mi2s_rx_format, bit_format_text);
145static SOC_ENUM_SINGLE_EXT_DECL(int5_mi2s_tx_chs, int_mi2s_ch_text);
146static SOC_ENUM_SINGLE_EXT_DECL(loopback_mclk_en, loopback_mclk_text);
147static SOC_ENUM_SINGLE_EXT_DECL(bt_sample_rate, bt_sample_rate_text);
148
149static int msm_dmic_event(struct snd_soc_dapm_widget *w,
150 struct snd_kcontrol *kcontrol, int event);
151static int msm_int_enable_dig_cdc_clk(struct snd_soc_component *component,
152 int enable, bool dapm);
153static int msm_int_mclk0_event(struct snd_soc_dapm_widget *w,
154 struct snd_kcontrol *kcontrol, int event);
155static int msm_int_mi2s_snd_startup(struct snd_pcm_substream *substream);
156static void msm_int_mi2s_snd_shutdown(struct snd_pcm_substream *substream);
157
158static struct wcd_mbhc_config *mbhc_cfg_ptr;
159static struct snd_info_entry *codec_root;
160
161static int int_mi2s_get_bit_format_val(int bit_format)
162{
163 int val = 0;
164
165 switch (bit_format) {
166 case SNDRV_PCM_FORMAT_S24_3LE:
167 val = 2;
168 break;
169 case SNDRV_PCM_FORMAT_S24_LE:
170 val = 1;
171 break;
172 case SNDRV_PCM_FORMAT_S16_LE:
173 default:
174 val = 0;
175 break;
176 }
177 return val;
178}
179
180static int int_mi2s_get_bit_format(int val)
181{
182 int bit_fmt = SNDRV_PCM_FORMAT_S16_LE;
183
184 switch (val) {
185 case 0:
186 bit_fmt = SNDRV_PCM_FORMAT_S16_LE;
187 break;
188 case 1:
189 bit_fmt = SNDRV_PCM_FORMAT_S24_LE;
190 break;
191 case 2:
192 bit_fmt = SNDRV_PCM_FORMAT_S24_3LE;
193 break;
194 default:
195 bit_fmt = SNDRV_PCM_FORMAT_S16_LE;
196 break;
197 }
198 return bit_fmt;
199}
200
201static int int_mi2s_get_port_idx(struct snd_kcontrol *kcontrol)
202{
203 int port_id = 0;
204
205 if (strnstr(kcontrol->id.name, "INT0_MI2S", sizeof("INT0_MI2S")))
206 port_id = INT0_MI2S;
207 else if (strnstr(kcontrol->id.name, "INT2_MI2S", sizeof("INT2_MI2S")))
208 port_id = INT2_MI2S;
209 else if (strnstr(kcontrol->id.name, "INT3_MI2S", sizeof("INT3_MI2S")))
210 port_id = INT3_MI2S;
211 else if (strnstr(kcontrol->id.name, "INT4_MI2S", sizeof("INT4_MI2S")))
212 port_id = INT4_MI2S;
213 else {
214 pr_err("%s: unsupported channel: %s",
215 __func__, kcontrol->id.name);
216 return -EINVAL;
217 }
218
219 return port_id;
220}
221
222static int int_mi2s_bit_format_get(struct snd_kcontrol *kcontrol,
223 struct snd_ctl_elem_value *ucontrol)
224{
225 int ch_num = int_mi2s_get_port_idx(kcontrol);
226
227 if (ch_num < 0)
228 return ch_num;
229
230 ucontrol->value.enumerated.item[0] =
231 int_mi2s_get_bit_format_val(int_mi2s_cfg[ch_num].bit_format);
232
233 pr_debug("%s: int_mi2s[%d]_bit_format = %d, ucontrol value = %d\n",
234 __func__, ch_num, int_mi2s_cfg[ch_num].bit_format,
235 ucontrol->value.enumerated.item[0]);
236
237 return 0;
238}
239
240static int int_mi2s_bit_format_put(struct snd_kcontrol *kcontrol,
241 struct snd_ctl_elem_value *ucontrol)
242{
243 int ch_num = int_mi2s_get_port_idx(kcontrol);
244
245 if (ch_num < 0)
246 return ch_num;
247
248 int_mi2s_cfg[ch_num].bit_format =
249 int_mi2s_get_bit_format(ucontrol->value.enumerated.item[0]);
250
251 pr_debug("%s: int_mi2s[%d]_rx_bit_format = %d, ucontrol value = %d\n",
252 __func__, ch_num, int_mi2s_cfg[ch_num].bit_format,
253 ucontrol->value.enumerated.item[0]);
254
255 return 0;
256}
257
258static inline int param_is_mask(int p)
259{
260 return (p >= SNDRV_PCM_HW_PARAM_FIRST_MASK) &&
261 (p <= SNDRV_PCM_HW_PARAM_LAST_MASK);
262}
263
264static inline struct snd_mask *param_to_mask(struct snd_pcm_hw_params *p,
265 int n)
266{
267 return &(p->masks[n - SNDRV_PCM_HW_PARAM_FIRST_MASK]);
268}
269
270static void param_set_mask(struct snd_pcm_hw_params *p, int n, unsigned int bit)
271{
272 if (bit >= SNDRV_MASK_MAX)
273 return;
274 if (param_is_mask(n)) {
275 struct snd_mask *m = param_to_mask(p, n);
276
277 m->bits[0] = 0;
278 m->bits[1] = 0;
279 m->bits[bit >> 5] |= (1 << (bit & 31));
280 }
281}
282
283static int int_mi2s_get_sample_rate_val(int sample_rate)
284{
285 int sample_rate_val;
286
287 switch (sample_rate) {
288 case SAMPLING_RATE_8KHZ:
289 sample_rate_val = 0;
290 break;
291 case SAMPLING_RATE_16KHZ:
292 sample_rate_val = 1;
293 break;
294 case SAMPLING_RATE_32KHZ:
295 sample_rate_val = 2;
296 break;
297 case SAMPLING_RATE_44P1KHZ:
298 sample_rate_val = 3;
299 break;
300 case SAMPLING_RATE_48KHZ:
301 sample_rate_val = 4;
302 break;
303 case SAMPLING_RATE_96KHZ:
304 sample_rate_val = 5;
305 break;
306 case SAMPLING_RATE_192KHZ:
307 sample_rate_val = 6;
308 break;
309 default:
310 sample_rate_val = 4;
311 break;
312 }
313 return sample_rate_val;
314}
315
316static int int_mi2s_get_sample_rate(int value)
317{
318 int sample_rate;
319
320 switch (value) {
321 case 0:
322 sample_rate = SAMPLING_RATE_8KHZ;
323 break;
324 case 1:
325 sample_rate = SAMPLING_RATE_16KHZ;
326 break;
327 case 2:
328 sample_rate = SAMPLING_RATE_32KHZ;
329 break;
330 case 3:
331 sample_rate = SAMPLING_RATE_44P1KHZ;
332 break;
333 case 4:
334 sample_rate = SAMPLING_RATE_48KHZ;
335 break;
336 case 5:
337 sample_rate = SAMPLING_RATE_96KHZ;
338 break;
339 case 6:
340 sample_rate = SAMPLING_RATE_192KHZ;
341 break;
342 default:
343 sample_rate = SAMPLING_RATE_48KHZ;
344 break;
345 }
346 return sample_rate;
347}
348
349static int int_mi2s_sample_rate_put(struct snd_kcontrol *kcontrol,
350 struct snd_ctl_elem_value *ucontrol)
351{
352 int idx = int_mi2s_get_port_idx(kcontrol);
353
354 if (idx < 0)
355 return idx;
356
357 int_mi2s_cfg[idx].sample_rate =
358 int_mi2s_get_sample_rate(ucontrol->value.enumerated.item[0]);
359
360 pr_debug("%s: idx[%d]_sample_rate = %d, item = %d\n", __func__,
361 idx, int_mi2s_cfg[idx].sample_rate,
362 ucontrol->value.enumerated.item[0]);
363
364 return 0;
365}
366
367static int int_mi2s_sample_rate_get(struct snd_kcontrol *kcontrol,
368 struct snd_ctl_elem_value *ucontrol)
369{
370 int idx = int_mi2s_get_port_idx(kcontrol);
371
372 if (idx < 0)
373 return idx;
374
375 ucontrol->value.enumerated.item[0] =
376 int_mi2s_get_sample_rate_val(int_mi2s_cfg[idx].sample_rate);
377
378 pr_debug("%s: idx[%d]_sample_rate = %d, item = %d\n", __func__,
379 idx, int_mi2s_cfg[idx].sample_rate,
380 ucontrol->value.enumerated.item[0]);
381
382 return 0;
383}
384
385static int int_mi2s_ch_get(struct snd_kcontrol *kcontrol,
386 struct snd_ctl_elem_value *ucontrol)
387{
388 int idx = int_mi2s_get_port_idx(kcontrol);
389
390 if (idx < 0)
391 return idx;
392
393 pr_debug("%s: int_mi2s_[%d]_rx_ch = %d\n", __func__,
394 idx, int_mi2s_cfg[idx].channels);
395 ucontrol->value.enumerated.item[0] = int_mi2s_cfg[idx].channels - 1;
396
397 return 0;
398}
399
400static int int_mi2s_ch_put(struct snd_kcontrol *kcontrol,
401 struct snd_ctl_elem_value *ucontrol)
402{
403 int idx = int_mi2s_get_port_idx(kcontrol);
404
405 if (idx < 0)
406 return idx;
407
408 int_mi2s_cfg[idx].channels = ucontrol->value.enumerated.item[0] + 1;
409 pr_debug("%s: int_mi2s_[%d]_ch = %d\n", __func__,
410 idx, int_mi2s_cfg[idx].channels);
411
412 return 1;
413}
414
415static const struct snd_soc_dapm_widget msm_int_dapm_widgets[] = {
416 SND_SOC_DAPM_SUPPLY_S("INT_MCLK0", -1, SND_SOC_NOPM, 0, 0,
417 msm_int_mclk0_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
418 SND_SOC_DAPM_MIC("Handset Mic", NULL),
419 SND_SOC_DAPM_MIC("Headset Mic", NULL),
420 SND_SOC_DAPM_MIC("Secondary Mic", NULL),
421 SND_SOC_DAPM_MIC("Digital Mic1", msm_dmic_event),
422 SND_SOC_DAPM_MIC("Digital Mic2", msm_dmic_event),
423 SND_SOC_DAPM_MIC("Digital Mic3", msm_dmic_event),
424 SND_SOC_DAPM_MIC("Digital Mic4", msm_dmic_event),
425};
426
427static int msm_config_hph_compander_gpio(bool enable,
428 struct snd_soc_component *component)
429{
430 struct snd_soc_card *card = component->card;
431 struct msm_asoc_mach_data *pdata = snd_soc_card_get_drvdata(card);
432 int ret = 0;
433
434 pr_debug("%s: %s HPH Compander\n", __func__,
435 enable ? "Enable" : "Disable");
436
437 if (enable) {
438 ret = msm_cdc_pinctrl_select_active_state(pdata->comp_gpio_p);
439 if (ret) {
440 pr_err("%s: gpio set cannot be activated %s\n",
441 __func__, "comp_gpio");
442 goto done;
443 }
444 } else {
445 ret = msm_cdc_pinctrl_select_sleep_state(pdata->comp_gpio_p);
446 if (ret) {
447 pr_err("%s: gpio set cannot be de-activated %s\n",
448 __func__, "comp_gpio");
449 goto done;
450 }
451 }
452
453done:
454 return ret;
455}
456
457static int is_ext_spk_gpio_support(struct platform_device *pdev,
458 struct msm_asoc_mach_data *pdata)
459{
460 const char *spk_ext_pa = "qcom,msm-spk-ext-pa";
461
462 pr_debug("%s:Enter\n", __func__);
463
464 pdata->spk_ext_pa_gpio = of_get_named_gpio(pdev->dev.of_node,
465 spk_ext_pa, 0);
466
467 if (pdata->spk_ext_pa_gpio < 0) {
468 dev_dbg(&pdev->dev,
469 "%s: missing %s in dt node\n", __func__, spk_ext_pa);
470 } else {
471 if (!gpio_is_valid(pdata->spk_ext_pa_gpio)) {
472 pr_err("%s: Invalid external speaker gpio: %d",
473 __func__, pdata->spk_ext_pa_gpio);
474 return -EINVAL;
475 }
476 }
477 return 0;
478}
479
480static int enable_spk_ext_pa(struct snd_soc_component *component, int enable)
481{
482 struct snd_soc_card *card = component->card;
483 struct msm_asoc_mach_data *pdata = snd_soc_card_get_drvdata(card);
484 int ret;
485
486 if (!gpio_is_valid(pdata->spk_ext_pa_gpio)) {
487 pr_err("%s: Invalid gpio: %d\n", __func__,
488 pdata->spk_ext_pa_gpio);
489 return false;
490 }
491
492 pr_debug("%s: %s external speaker PA\n", __func__,
493 enable ? "Enable" : "Disable");
494
495 if (enable) {
496 ret = msm_cdc_pinctrl_select_active_state(
497 pdata->ext_spk_gpio_p);
498 if (ret) {
499 pr_err("%s: gpio set cannot be de-activated %s\n",
500 __func__, "ext_spk_gpio");
501 return ret;
502 }
503 gpio_set_value_cansleep(pdata->spk_ext_pa_gpio, enable);
504 } else {
505 gpio_set_value_cansleep(pdata->spk_ext_pa_gpio, enable);
506 ret = msm_cdc_pinctrl_select_sleep_state(
507 pdata->ext_spk_gpio_p);
508 if (ret) {
509 pr_err("%s: gpio set cannot be de-activated %s\n",
510 __func__, "ext_spk_gpio");
511 return ret;
512 }
513 }
514 return 0;
515}
516
517static int int_mi2s_get_idx_from_beid(int32_t id)
518{
519 int idx = 0;
520
521 switch (id) {
522 case MSM_BACKEND_DAI_INT0_MI2S_RX:
523 idx = INT0_MI2S;
524 break;
525 case MSM_BACKEND_DAI_INT2_MI2S_TX:
526 idx = INT2_MI2S;
527 break;
528 case MSM_BACKEND_DAI_INT3_MI2S_TX:
529 idx = INT3_MI2S;
530 break;
531 case MSM_BACKEND_DAI_INT4_MI2S_RX:
532 idx = INT4_MI2S;
533 break;
534 case MSM_BACKEND_DAI_INT5_MI2S_TX:
535 idx = INT5_MI2S;
536 break;
537 default:
538 idx = INT0_MI2S;
539 break;
540 }
541
542 return idx;
543}
544
545static int msm_be_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,
546 struct snd_pcm_hw_params *params)
547{
548 struct snd_interval *rate = hw_param_interval(params,
549 SNDRV_PCM_HW_PARAM_RATE);
550
551 struct snd_interval *channels = hw_param_interval(params,
552 SNDRV_PCM_HW_PARAM_CHANNELS);
553
554 pr_debug("%s()\n", __func__);
555 rate->min = rate->max = 48000;
556 channels->min = channels->max = 2;
557
558 return 0;
559}
560
561static int int_mi2s_be_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,
562 struct snd_pcm_hw_params *params)
563{
564 struct snd_soc_dai_link *dai_link = rtd->dai_link;
565 struct snd_interval *rate = hw_param_interval(params,
566 SNDRV_PCM_HW_PARAM_RATE);
567 struct snd_interval *channels = hw_param_interval(params,
568 SNDRV_PCM_HW_PARAM_CHANNELS);
569 int idx;
570
571 pr_debug("%s: format = %d, rate = %d\n",
572 __func__, params_format(params), params_rate(params));
573
574 switch (dai_link->id) {
575 case MSM_BACKEND_DAI_INT0_MI2S_RX:
576 case MSM_BACKEND_DAI_INT2_MI2S_TX:
577 case MSM_BACKEND_DAI_INT3_MI2S_TX:
578 case MSM_BACKEND_DAI_INT4_MI2S_RX:
579 case MSM_BACKEND_DAI_INT5_MI2S_TX:
580 idx = int_mi2s_get_idx_from_beid(dai_link->id);
581 rate->min = rate->max = int_mi2s_cfg[idx].sample_rate;
582 channels->min = channels->max =
583 int_mi2s_cfg[idx].channels;
584 param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
585 int_mi2s_cfg[idx].bit_format);
586 break;
587 default:
588 rate->min = rate->max = SAMPLING_RATE_48KHZ;
589 break;
590 }
591 return 0;
592}
593
594static int msm_btfm_be_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,
595 struct snd_pcm_hw_params *params)
596{
597 struct snd_soc_dai_link *dai_link = rtd->dai_link;
598 struct snd_interval *rate = hw_param_interval(params,
599 SNDRV_PCM_HW_PARAM_RATE);
600 struct snd_interval *channels = hw_param_interval(params,
601 SNDRV_PCM_HW_PARAM_CHANNELS);
602
603 switch (dai_link->id) {
604 case MSM_BACKEND_DAI_SLIMBUS_7_RX:
605 case MSM_BACKEND_DAI_SLIMBUS_7_TX:
606 param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
607 bt_fm_cfg[BT_SLIM7].bit_format);
608 rate->min = rate->max = bt_fm_cfg[BT_SLIM7].sample_rate;
609 channels->min = channels->max =
610 bt_fm_cfg[BT_SLIM7].channels;
611 break;
612
613 case MSM_BACKEND_DAI_SLIMBUS_8_TX:
614 rate->min = rate->max = bt_fm_cfg[FM_SLIM8].sample_rate;
615 channels->min = channels->max =
616 bt_fm_cfg[FM_SLIM8].channels;
617 break;
618
619 default:
620 rate->min = rate->max = SAMPLING_RATE_48KHZ;
621 break;
622 }
623 return 0;
624}
625
626static int msm_vi_feed_tx_ch_get(struct snd_kcontrol *kcontrol,
627 struct snd_ctl_elem_value *ucontrol)
628{
629 ucontrol->value.integer.value[0] =
630 (int_mi2s_cfg[INT5_MI2S].channels/2 - 1);
631 pr_debug("%s: msm_vi_feed_tx_ch = %ld\n", __func__,
632 ucontrol->value.integer.value[0]);
633 return 0;
634}
635
636static int msm_vi_feed_tx_ch_put(struct snd_kcontrol *kcontrol,
637 struct snd_ctl_elem_value *ucontrol)
638{
639 int_mi2s_cfg[INT5_MI2S].channels =
640 roundup_pow_of_two(ucontrol->value.integer.value[0] + 2);
641
642 pr_debug("%s: msm_vi_feed_tx_ch = %d\n",
643 __func__, int_mi2s_cfg[INT5_MI2S].channels);
644 return 1;
645}
646
647static int msm_int_enable_dig_cdc_clk(struct snd_soc_component *component,
648 int enable, bool dapm)
649{
650 int ret = 0;
651 struct msm_asoc_mach_data *pdata = NULL;
652 int clk_freq_in_hz;
653 bool int_mclk0_freq_chg = false;
654
655 pdata = snd_soc_card_get_drvdata(component->card);
656 pr_debug("%s: enable %d mclk ref counter %d\n",
657 __func__, enable,
658 atomic_read(&pdata->int_mclk0_rsc_ref));
659 if (enable) {
660 if (int_mi2s_cfg[INT0_MI2S].sample_rate ==
661 SAMPLING_RATE_44P1KHZ) {
662 clk_freq_in_hz = NATIVE_MCLK_RATE;
663 pdata->native_clk_set = true;
664 } else {
665 clk_freq_in_hz = pdata->mclk_freq;
666 pdata->native_clk_set = false;
667 }
668
669 if (pdata->digital_cdc_core_clk.clk_freq_in_hz
670 != clk_freq_in_hz)
671 int_mclk0_freq_chg = true;
672 if (!atomic_read(&pdata->int_mclk0_rsc_ref) ||
673 int_mclk0_freq_chg) {
674 cancel_delayed_work_sync(
675 &pdata->disable_int_mclk0_work);
676 mutex_lock(&pdata->cdc_int_mclk0_mutex);
677 if (atomic_read(&pdata->int_mclk0_enabled) == false ||
678 int_mclk0_freq_chg) {
679 if (atomic_read(&pdata->int_mclk0_enabled)) {
680 pdata->digital_cdc_core_clk.enable = 0;
681 afe_set_lpass_clock_v2(
682 AFE_PORT_ID_INT0_MI2S_RX,
683 &pdata->digital_cdc_core_clk);
684 }
685 pdata->digital_cdc_core_clk.clk_freq_in_hz =
686 clk_freq_in_hz;
687 pdata->digital_cdc_core_clk.enable = 1;
688 ret = afe_set_lpass_clock_v2(
689 AFE_PORT_ID_INT0_MI2S_RX,
690 &pdata->digital_cdc_core_clk);
691 if (ret < 0) {
692 pr_err("%s: failed to enable CCLK\n",
693 __func__);
694 mutex_unlock(
695 &pdata->cdc_int_mclk0_mutex);
696 return ret;
697 }
698 pr_debug("enabled digital codec core clk\n");
699 atomic_set(&pdata->int_mclk0_enabled, true);
700 }
701 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
702 }
703 atomic_inc(&pdata->int_mclk0_rsc_ref);
704 } else {
705 cancel_delayed_work_sync(&pdata->disable_int_mclk0_work);
706 mutex_lock(&pdata->cdc_int_mclk0_mutex);
707 if (atomic_read(&pdata->int_mclk0_enabled) == true) {
708 pdata->digital_cdc_core_clk.clk_freq_in_hz =
709 DEFAULT_MCLK_RATE;
710 pdata->digital_cdc_core_clk.enable = 0;
711 ret = afe_set_lpass_clock_v2(
712 AFE_PORT_ID_INT0_MI2S_RX,
713 &pdata->digital_cdc_core_clk);
714 if (ret < 0)
715 pr_err("%s: failed to disable CCLK\n",
716 __func__);
717 atomic_set(&pdata->int_mclk0_enabled, false);
718 atomic_set(&pdata->int_mclk0_rsc_ref, 0);
719 }
720 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
721 }
722 return ret;
723}
724
725static int loopback_mclk_get(struct snd_kcontrol *kcontrol,
726 struct snd_ctl_elem_value *ucontrol)
727{
728 pr_debug("%s\n", __func__);
729 return 0;
730}
731
732static int loopback_mclk_put(struct snd_kcontrol *kcontrol,
733 struct snd_ctl_elem_value *ucontrol)
734{
735 int ret = -EINVAL;
736 struct msm_asoc_mach_data *pdata = NULL;
737 struct snd_soc_component *component =
738 snd_soc_kcontrol_component(kcontrol);
739
740 pdata = snd_soc_card_get_drvdata(component->card);
741 pr_debug("%s: mclk_rsc_ref %d enable %ld\n",
742 __func__, atomic_read(&pdata->int_mclk0_rsc_ref),
743 ucontrol->value.integer.value[0]);
744 switch (ucontrol->value.integer.value[0]) {
745 case 1:
746 ret = msm_cdc_pinctrl_select_active_state(pdata->pdm_gpio_p);
747 if (ret) {
748 pr_err("%s: failed to enable the pri gpios: %d\n",
749 __func__, ret);
750 break;
751 }
752 mutex_lock(&pdata->cdc_int_mclk0_mutex);
753 if ((!atomic_read(&pdata->int_mclk0_rsc_ref)) &&
754 (!atomic_read(&pdata->int_mclk0_enabled))) {
755 pdata->digital_cdc_core_clk.enable = 1;
756 ret = afe_set_lpass_clock_v2(
757 AFE_PORT_ID_INT0_MI2S_RX,
758 &pdata->digital_cdc_core_clk);
759 if (ret < 0) {
760 pr_err("%s: failed to enable the MCLK: %d\n",
761 __func__, ret);
762 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
763 ret = msm_cdc_pinctrl_select_sleep_state(
764 pdata->pdm_gpio_p);
765 if (ret)
766 pr_err("%s: failed to disable the pri gpios: %d\n",
767 __func__, ret);
768 break;
769 }
770 atomic_set(&pdata->int_mclk0_enabled, true);
771 }
772 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
773 atomic_inc(&pdata->int_mclk0_rsc_ref);
774 msm_anlg_cdc_mclk_enable(component, 1, true);
775 break;
776 case 0:
777 if (atomic_read(&pdata->int_mclk0_rsc_ref) <= 0)
778 break;
779 msm_anlg_cdc_mclk_enable(component, 0, true);
780 mutex_lock(&pdata->cdc_int_mclk0_mutex);
781 if ((!atomic_dec_return(&pdata->int_mclk0_rsc_ref)) &&
782 (atomic_read(&pdata->int_mclk0_enabled))) {
783 pdata->digital_cdc_core_clk.enable = 0;
784 ret = afe_set_lpass_clock_v2(
785 AFE_PORT_ID_INT0_MI2S_RX,
786 &pdata->digital_cdc_core_clk);
787 if (ret < 0) {
788 pr_err("%s: failed to disable the CCLK: %d\n",
789 __func__, ret);
790 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
791 break;
792 }
793 atomic_set(&pdata->int_mclk0_enabled, false);
794 }
795 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
796 ret = msm_cdc_pinctrl_select_sleep_state(pdata->pdm_gpio_p);
797 if (ret)
798 pr_err("%s: failed to disable the pri gpios: %d\n",
799 __func__, ret);
800 break;
801 default:
802 pr_err("%s: Unexpected input value\n", __func__);
803 break;
804 }
805 return ret;
806}
807
808static int msm_bt_sample_rate_get(struct snd_kcontrol *kcontrol,
809 struct snd_ctl_elem_value *ucontrol)
810{
811 /*
812 * Slimbus_7_Rx/Tx sample rate values should always be in sync (same)
813 * when used for BT_SCO use case. Return either Rx or Tx sample rate
814 * value.
815 */
816 switch (bt_fm_cfg[BT_SLIM7].sample_rate) {
817 case SAMPLING_RATE_96KHZ:
818 ucontrol->value.integer.value[0] = 5;
819 break;
820 case SAMPLING_RATE_88P2KHZ:
821 ucontrol->value.integer.value[0] = 4;
822 break;
823 case SAMPLING_RATE_48KHZ:
824 ucontrol->value.integer.value[0] = 3;
825 break;
826 case SAMPLING_RATE_44P1KHZ:
827 ucontrol->value.integer.value[0] = 2;
828 break;
829 case SAMPLING_RATE_16KHZ:
830 ucontrol->value.integer.value[0] = 1;
831 break;
832 case SAMPLING_RATE_8KHZ:
833 default:
834 ucontrol->value.integer.value[0] = 0;
835 break;
836 }
837 pr_debug("%s: sample rate = %d", __func__,
838 bt_fm_cfg[BT_SLIM7].sample_rate);
839
840 return 0;
841}
842
843static int msm_bt_sample_rate_put(struct snd_kcontrol *kcontrol,
844 struct snd_ctl_elem_value *ucontrol)
845{
846 switch (ucontrol->value.integer.value[0]) {
847 case 1:
848 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_16KHZ;
849 break;
850 case 2:
851 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_44P1KHZ;
852 break;
853 case 3:
854 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_48KHZ;
855 break;
856 case 4:
857 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_88P2KHZ;
858 break;
859 case 5:
860 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_96KHZ;
861 break;
862 case 0:
863 default:
864 bt_fm_cfg[BT_SLIM7].sample_rate = SAMPLING_RATE_8KHZ;
865 break;
866 }
867 pr_debug("%s: sample rates: slim7_rx = %d, value = %d\n",
868 __func__,
869 bt_fm_cfg[BT_SLIM7].sample_rate,
870 ucontrol->value.enumerated.item[0]);
871
872 return 0;
873}
874
875static const struct snd_kcontrol_new msm_snd_controls[] = {
876 SOC_ENUM_EXT("INT0_MI2S_RX Format", int0_mi2s_rx_format,
877 int_mi2s_bit_format_get, int_mi2s_bit_format_put),
878 SOC_ENUM_EXT("INT2_MI2S_TX Format", int2_mi2s_tx_format,
879 int_mi2s_bit_format_get, int_mi2s_bit_format_put),
880 SOC_ENUM_EXT("INT3_MI2S_TX Format", int3_mi2s_tx_format,
881 int_mi2s_bit_format_get, int_mi2s_bit_format_put),
882 SOC_ENUM_EXT("INT0_MI2S_RX SampleRate", int0_mi2s_rx_sample_rate,
883 int_mi2s_sample_rate_get,
884 int_mi2s_sample_rate_put),
885 SOC_ENUM_EXT("INT2_MI2S_TX SampleRate", int2_mi2s_tx_sample_rate,
886 int_mi2s_sample_rate_get,
887 int_mi2s_sample_rate_put),
888 SOC_ENUM_EXT("INT3_MI2S_TX SampleRate", int3_mi2s_tx_sample_rate,
889 int_mi2s_sample_rate_get,
890 int_mi2s_sample_rate_put),
891 SOC_ENUM_EXT("INT0_MI2S_RX Channels", int0_mi2s_rx_chs,
892 int_mi2s_ch_get, int_mi2s_ch_put),
893 SOC_ENUM_EXT("INT2_MI2S_TX Channels", int2_mi2s_tx_chs,
894 int_mi2s_ch_get, int_mi2s_ch_put),
895 SOC_ENUM_EXT("INT3_MI2S_TX Channels", int3_mi2s_tx_chs,
896 int_mi2s_ch_get, int_mi2s_ch_put),
897 SOC_ENUM_EXT("Loopback MCLK", loopback_mclk_en,
898 loopback_mclk_get, loopback_mclk_put),
899 SOC_ENUM_EXT("BT SampleRate", bt_sample_rate,
900 msm_bt_sample_rate_get,
901 msm_bt_sample_rate_put),
902};
903
904static const struct snd_kcontrol_new msm_sdw_controls[] = {
905 SOC_ENUM_EXT("INT4_MI2S_RX Format", int4_mi2s_rx_format,
906 int_mi2s_bit_format_get, int_mi2s_bit_format_put),
907 SOC_ENUM_EXT("INT4_MI2S_RX SampleRate", int4_mi2s_rx_sample_rate,
908 int_mi2s_sample_rate_get,
909 int_mi2s_sample_rate_put),
910 SOC_ENUM_EXT("INT4_MI2S_RX Channels", int4_mi2s_rx_chs,
911 int_mi2s_ch_get, int_mi2s_ch_put),
912 SOC_ENUM_EXT("VI_FEED_TX Channels", int5_mi2s_tx_chs,
913 msm_vi_feed_tx_ch_get, msm_vi_feed_tx_ch_put),
914};
915
916static int msm_dmic_event(struct snd_soc_dapm_widget *w,
917 struct snd_kcontrol *kcontrol, int event)
918{
919 struct msm_asoc_mach_data *pdata = NULL;
920 struct snd_soc_component *component =
921 snd_soc_dapm_to_component(w->dapm);
922 int ret = 0;
923
924 pdata = snd_soc_card_get_drvdata(component->card);
925 pr_debug("%s: event = %d\n", __func__, event);
926 switch (event) {
927 case SND_SOC_DAPM_PRE_PMU:
928 ret = msm_cdc_pinctrl_select_active_state(pdata->dmic_gpio_p);
929 if (ret < 0) {
930 pr_err("%s: gpio set cannot be activated %sd",
931 __func__, "dmic_gpio");
932 return ret;
933 }
934 break;
935 case SND_SOC_DAPM_POST_PMD:
936 ret = msm_cdc_pinctrl_select_sleep_state(pdata->dmic_gpio_p);
937 if (ret < 0) {
938 pr_err("%s: gpio set cannot be de-activated %sd",
939 __func__, "dmic_gpio");
940 return ret;
941 }
942 break;
943 default:
944 pr_err("%s: invalid DAPM event %d\n", __func__, event);
945 return -EINVAL;
946 }
947 return 0;
948}
949
950static int msm_int_mclk0_event(struct snd_soc_dapm_widget *w,
951 struct snd_kcontrol *kcontrol, int event)
952{
953 struct msm_asoc_mach_data *pdata = NULL;
954 struct snd_soc_component *component =
955 snd_soc_dapm_to_component(w->dapm);
956 int ret = 0;
957
958 pdata = snd_soc_card_get_drvdata(component->card);
959 pr_debug("%s: event = %d\n", __func__, event);
960 switch (event) {
961 case SND_SOC_DAPM_PRE_PMU:
962 ret = msm_cdc_pinctrl_select_active_state(pdata->pdm_gpio_p);
963 if (ret < 0) {
964 pr_err("%s: gpio set cannot be activated %s\n",
965 __func__, "int_pdm");
966 return ret;
967 }
968 msm_int_enable_dig_cdc_clk(component, 1, true);
969 msm_anlg_cdc_mclk_enable(component, 1, true);
970 break;
971 case SND_SOC_DAPM_POST_PMD:
972 pr_debug("%s: mclk_res_ref = %d\n",
973 __func__, atomic_read(&pdata->int_mclk0_rsc_ref));
974 ret = msm_cdc_pinctrl_select_sleep_state(pdata->pdm_gpio_p);
975 if (ret < 0) {
976 pr_err("%s: gpio set cannot be de-activated %sd",
977 __func__, "int_pdm");
978 return ret;
979 }
980 pr_debug("%s: disabling MCLK\n", __func__);
981 /* disable the codec mclk config*/
982 msm_anlg_cdc_mclk_enable(component, 0, true);
983 msm_int_enable_dig_cdc_clk(component, 0, true);
984 break;
985 default:
986 pr_err("%s: invalid DAPM event %d\n", __func__, event);
987 return -EINVAL;
988 }
989 return 0;
990}
991
992static int int_mi2s_get_port_id(int id)
993{
994 int afe_port_id;
995
996 switch (id) {
997 case MSM_BACKEND_DAI_INT0_MI2S_RX:
998 afe_port_id = AFE_PORT_ID_INT0_MI2S_RX;
999 break;
1000 case MSM_BACKEND_DAI_INT2_MI2S_TX:
1001 afe_port_id = AFE_PORT_ID_INT2_MI2S_TX;
1002 break;
1003 case MSM_BACKEND_DAI_INT3_MI2S_TX:
1004 afe_port_id = AFE_PORT_ID_INT3_MI2S_TX;
1005 break;
1006 case MSM_BACKEND_DAI_INT4_MI2S_RX:
1007 afe_port_id = AFE_PORT_ID_INT4_MI2S_RX;
1008 break;
1009 case MSM_BACKEND_DAI_INT5_MI2S_TX:
1010 afe_port_id = AFE_PORT_ID_INT5_MI2S_TX;
1011 break;
1012 default:
1013 pr_err("%s: Invalid id: %d\n", __func__, id);
1014 afe_port_id = -EINVAL;
1015 }
1016
1017 return afe_port_id;
1018}
1019
1020static int int_mi2s_get_index(int port_id)
1021{
1022 int index;
1023
1024 switch (port_id) {
1025 case AFE_PORT_ID_INT0_MI2S_RX:
1026 index = INT0_MI2S;
1027 break;
1028 case AFE_PORT_ID_INT2_MI2S_TX:
1029 index = INT2_MI2S;
1030 break;
1031 case AFE_PORT_ID_INT3_MI2S_TX:
1032 index = INT3_MI2S;
1033 break;
1034 case AFE_PORT_ID_INT4_MI2S_RX:
1035 index = INT4_MI2S;
1036 break;
1037 case AFE_PORT_ID_INT5_MI2S_TX:
1038 index = INT5_MI2S;
1039 break;
1040 default:
1041 pr_err("%s: Invalid port_id: %d\n", __func__, port_id);
1042 index = -EINVAL;
1043 }
1044
1045 return index;
1046}
1047
1048static u32 get_int_mi2s_bits_per_sample(u32 bit_format)
1049{
1050 u32 bit_per_sample;
1051
1052 switch (bit_format) {
1053 case SNDRV_PCM_FORMAT_S24_3LE:
1054 case SNDRV_PCM_FORMAT_S24_LE:
1055 bit_per_sample = 32;
1056 break;
1057 case SNDRV_PCM_FORMAT_S16_LE:
1058 default:
1059 bit_per_sample = 16;
1060 break;
1061 }
1062
1063 return bit_per_sample;
1064}
1065
1066static void update_int_mi2s_clk_val(int idx, int stream)
1067{
1068 u32 bit_per_sample;
1069
1070 bit_per_sample =
1071 get_int_mi2s_bits_per_sample(int_mi2s_cfg[idx].bit_format);
1072 int_mi2s_clk[idx].clk_freq_in_hz =
1073 (int_mi2s_cfg[idx].sample_rate * 2 * bit_per_sample);
1074}
1075
1076static int int_mi2s_set_sclk(struct snd_pcm_substream *substream, bool enable)
1077{
1078 int ret = 0;
1079 struct snd_soc_pcm_runtime *rtd = substream->private_data;
1080 int port_id = 0;
1081 int index;
1082
1083 port_id = int_mi2s_get_port_id(rtd->dai_link->id);
1084 if (port_id < 0) {
1085 dev_err(rtd->card->dev, "%s: Invalid port_id\n", __func__);
1086 ret = port_id;
1087 goto done;
1088 }
1089 index = int_mi2s_get_index(port_id);
1090 if (index < 0) {
1091 dev_err(rtd->card->dev, "%s: Invalid port_id\n", __func__);
1092 ret = port_id;
1093 goto done;
1094 }
1095 if (enable) {
1096 update_int_mi2s_clk_val(index, substream->stream);
1097 dev_dbg(rtd->card->dev, "%s: clock rate %ul\n", __func__,
1098 int_mi2s_clk[index].clk_freq_in_hz);
1099 }
1100
1101 int_mi2s_clk[index].enable = enable;
1102 ret = afe_set_lpass_clock_v2(port_id,
1103 &int_mi2s_clk[index]);
1104 if (ret < 0) {
1105 dev_err(rtd->card->dev,
1106 "%s: afe lpass clock failed for port 0x%x , err:%d\n",
1107 __func__, port_id, ret);
1108 goto done;
1109 }
1110
1111done:
1112 return ret;
1113}
1114
1115static int msm_sdw_mi2s_snd_startup(struct snd_pcm_substream *substream)
1116{
1117 struct snd_soc_pcm_runtime *rtd = substream->private_data;
1118 struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
1119 int ret = 0;
1120
1121 pr_debug("%s(): substream = %s stream = %d\n", __func__,
1122 substream->name, substream->stream);
1123
1124 ret = int_mi2s_set_sclk(substream, true);
1125 if (ret < 0) {
1126 pr_err("%s: failed to enable sclk %d\n",
1127 __func__, ret);
1128 return ret;
1129 }
1130 ret = snd_soc_dai_set_fmt(cpu_dai, SND_SOC_DAIFMT_CBS_CFS);
1131 if (ret < 0)
1132 pr_err("%s: set fmt cpu dai failed; ret=%d\n", __func__, ret);
1133
1134 return ret;
1135}
1136
1137static void msm_sdw_mi2s_snd_shutdown(struct snd_pcm_substream *substream)
1138{
1139 int ret;
1140
1141 pr_debug("%s(): substream = %s stream = %d\n", __func__,
1142 substream->name, substream->stream);
1143
1144 ret = int_mi2s_set_sclk(substream, false);
1145 if (ret < 0)
1146 pr_err("%s:clock disable failed; ret=%d\n", __func__,
1147 ret);
1148}
1149
1150static int msm_int_mi2s_snd_startup(struct snd_pcm_substream *substream)
1151{
1152 struct snd_soc_pcm_runtime *rtd = substream->private_data;
1153 struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
1154 struct snd_soc_component *component =
1155 snd_soc_rtdcom_lookup(rtd, "pmic_analog_codec");
1156 int ret = 0;
1157 struct msm_asoc_mach_data *pdata = NULL;
1158
1159 if (!component) {
1160 pr_err("%s: component is NULL\n", __func__);
1161 return -EINVAL;
1162 }
1163
1164 pdata = snd_soc_card_get_drvdata(component->card);
1165 pr_debug("%s(): substream = %s stream = %d\n", __func__,
1166 substream->name, substream->stream);
1167
1168 ret = int_mi2s_set_sclk(substream, true);
1169 if (ret < 0) {
1170 pr_err("%s: failed to enable sclk %d\n",
1171 __func__, ret);
1172 return ret;
1173 }
1174 ret = snd_soc_dai_set_fmt(cpu_dai, SND_SOC_DAIFMT_CBS_CFS);
1175 if (ret < 0)
1176 pr_err("%s: set fmt cpu dai failed; ret=%d\n", __func__, ret);
1177
1178 return ret;
1179}
1180
1181static void msm_int_mi2s_snd_shutdown(struct snd_pcm_substream *substream)
1182{
1183 int ret;
1184
1185 pr_debug("%s(): substream = %s stream = %d\n", __func__,
1186 substream->name, substream->stream);
1187
1188 ret = int_mi2s_set_sclk(substream, false);
1189 if (ret < 0)
1190 pr_err("%s:clock disable failed; ret=%d\n", __func__,
1191 ret);
1192}
1193
1194static void *def_msm_int_wcd_mbhc_cal(void)
1195{
1196 void *msm_int_wcd_cal;
1197 struct wcd_mbhc_btn_detect_cfg *btn_cfg;
1198 u16 *btn_low, *btn_high;
1199
1200 msm_int_wcd_cal = kzalloc(WCD_MBHC_CAL_SIZE(WCD_MBHC_DEF_BUTTONS,
1201 WCD_MBHC_DEF_RLOADS), GFP_KERNEL);
1202 if (!msm_int_wcd_cal)
1203 return NULL;
1204
1205#define S(X, Y) ((WCD_MBHC_CAL_PLUG_TYPE_PTR(msm_int_wcd_cal)->X) = (Y))
1206 S(v_hs_max, 1500);
1207#undef S
1208#define S(X, Y) ((WCD_MBHC_CAL_BTN_DET_PTR(msm_int_wcd_cal)->X) = (Y))
1209 S(num_btn, WCD_MBHC_DEF_BUTTONS);
1210#undef S
1211
1212
1213 btn_cfg = WCD_MBHC_CAL_BTN_DET_PTR(msm_int_wcd_cal);
1214 btn_low = btn_cfg->_v_btn_low;
1215 btn_high = ((void *)&btn_cfg->_v_btn_low) +
1216 (sizeof(btn_cfg->_v_btn_low[0]) * btn_cfg->num_btn);
1217
1218 /*
1219 * In SW we are maintaining two sets of threshold register
1220 * one for current source and another for Micbias.
1221 * all btn_low corresponds to threshold for current source
1222 * all bt_high corresponds to threshold for Micbias
1223 * Below thresholds are based on following resistances
1224 * 0-70 == Button 0
1225 * 110-180 == Button 1
1226 * 210-290 == Button 2
1227 * 360-680 == Button 3
1228 */
1229 btn_low[0] = 75;
1230 btn_high[0] = 75;
1231 btn_low[1] = 150;
1232 btn_high[1] = 150;
1233 btn_low[2] = 225;
1234 btn_high[2] = 225;
1235 btn_low[3] = 450;
1236 btn_high[3] = 450;
1237 btn_low[4] = 500;
1238 btn_high[4] = 500;
1239
1240 return msm_int_wcd_cal;
1241}
1242
1243static int msm_audrx_init(struct snd_soc_pcm_runtime *rtd)
1244{
1245 struct snd_soc_component *dig_cdc =
1246 snd_soc_rtdcom_lookup(rtd, "msm_digital_codec");
1247 struct snd_soc_component *ana_cdc =
1248 snd_soc_rtdcom_lookup(rtd, "pmic_analog_codec");
1249 struct snd_soc_dapm_context *dapm;
1250 struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
1251 struct msm_asoc_mach_data *pdata = snd_soc_card_get_drvdata(rtd->card);
1252 struct snd_card *card;
1253 int ret = -ENOMEM;
1254
1255 pr_debug("%s(),dev_name%s\n", __func__, dev_name(cpu_dai->dev));
1256
1257 if (!dig_cdc || !ana_cdc) {
1258 pr_err("%s: component is NULL\n", __func__);
1259 return -EINVAL;
1260 }
1261
1262 dapm = snd_soc_component_get_dapm(ana_cdc);
1263 ret = snd_soc_add_component_controls(ana_cdc, msm_snd_controls,
1264 ARRAY_SIZE(msm_snd_controls));
1265 if (ret < 0) {
1266 pr_err("%s: add_codec_controls failed: %d\n",
1267 __func__, ret);
1268 return ret;
1269 }
1270 ret = snd_soc_add_component_controls(ana_cdc, msm_common_snd_controls,
1271 msm_common_snd_controls_size());
1272 if (ret < 0) {
1273 pr_err("%s: add common snd controls failed: %d\n",
1274 __func__, ret);
1275 return ret;
1276 }
1277
1278 snd_soc_dapm_new_controls(dapm, msm_int_dapm_widgets,
1279 ARRAY_SIZE(msm_int_dapm_widgets));
1280
1281 snd_soc_dapm_ignore_suspend(dapm, "Handset Mic");
1282 snd_soc_dapm_ignore_suspend(dapm, "Headset Mic");
1283 snd_soc_dapm_ignore_suspend(dapm, "Secondary Mic");
1284 snd_soc_dapm_ignore_suspend(dapm, "Digital Mic1");
1285 snd_soc_dapm_ignore_suspend(dapm, "Digital Mic2");
1286
1287 snd_soc_dapm_ignore_suspend(dapm, "EAR");
1288 snd_soc_dapm_ignore_suspend(dapm, "HEADPHONE");
1289 snd_soc_dapm_ignore_suspend(dapm, "SPK_OUT");
1290 snd_soc_dapm_ignore_suspend(dapm, "AMIC1");
1291 snd_soc_dapm_ignore_suspend(dapm, "AMIC2");
1292 snd_soc_dapm_ignore_suspend(dapm, "AMIC3");
1293 snd_soc_dapm_sync(dapm);
1294
1295 dapm = snd_soc_component_get_dapm(dig_cdc);
1296 snd_soc_dapm_ignore_suspend(dapm, "DMIC1");
1297 snd_soc_dapm_ignore_suspend(dapm, "DMIC2");
1298 snd_soc_dapm_ignore_suspend(dapm, "DMIC3");
1299 snd_soc_dapm_ignore_suspend(dapm, "DMIC4");
1300
1301 snd_soc_dapm_sync(dapm);
1302
1303 msm_anlg_cdc_spk_ext_pa_cb(enable_spk_ext_pa, ana_cdc);
1304 msm_dig_cdc_hph_comp_cb(msm_config_hph_compander_gpio, dig_cdc);
1305
1306 card = rtd->card->snd_card;
1307 if (!codec_root)
1308 codec_root = snd_info_create_subdir(card->module, "codecs",
1309 card->proc_root);
1310 if (!codec_root) {
1311 pr_debug("%s: Cannot create codecs module entry\n",
1312 __func__);
1313 goto done;
1314 }
1315 pdata->codec_root = codec_root;
1316 msm_dig_codec_info_create_codec_entry(codec_root, dig_cdc);
1317 msm_anlg_codec_info_create_codec_entry(codec_root, ana_cdc);
1318done:
1319 msm_set_codec_reg_done(true);
1320 return 0;
1321}
1322
1323static int msm_sdw_audrx_init(struct snd_soc_pcm_runtime *rtd)
1324{
1325 struct snd_soc_dapm_context *dapm;
1326 struct msm_asoc_mach_data *pdata = snd_soc_card_get_drvdata(rtd->card);
1327 struct snd_soc_component *aux_comp;
1328 struct snd_card *card;
1329 struct snd_soc_component *component =
1330 snd_soc_rtdcom_lookup(rtd, "msm_sdw_codec");
1331
1332 if (!component) {
1333 pr_err("%s: component is NULL\n", __func__);
1334 return -EINVAL;
1335 }
1336 dapm = snd_soc_component_get_dapm(component);
1337
1338 snd_soc_add_component_controls(component, msm_sdw_controls,
1339 ARRAY_SIZE(msm_sdw_controls));
1340
1341 snd_soc_dapm_ignore_suspend(dapm, "AIF1_SDW Playback");
1342 snd_soc_dapm_ignore_suspend(dapm, "VIfeed_SDW");
1343 snd_soc_dapm_ignore_suspend(dapm, "SPK1 OUT");
1344 snd_soc_dapm_ignore_suspend(dapm, "SPK2 OUT");
1345 snd_soc_dapm_ignore_suspend(dapm, "AIF1_SDW VI");
1346 snd_soc_dapm_ignore_suspend(dapm, "VIINPUT_SDW");
1347
1348 snd_soc_dapm_sync(dapm);
1349
1350 /*
1351 * Send speaker configuration only for WSA8810.
1352 * Default configuration is for WSA8815.
1353 */
1354 pr_debug("%s: Number of aux devices: %d\n",
1355 __func__, rtd->card->num_aux_devs);
1356 if (rtd->card->num_aux_devs &&
1357 !list_empty(&rtd->card->aux_comp_list)) {
1358 aux_comp = list_first_entry(&rtd->card->aux_comp_list,
1359 struct snd_soc_component, card_aux_list);
1360 if (!strcmp(aux_comp->name, WSA8810_NAME_1) ||
1361 !strcmp(aux_comp->name, WSA8810_NAME_2)) {
1362 msm_sdw_set_spkr_mode(component, SPKR_MODE_1);
1363 msm_sdw_set_spkr_gain_offset(component,
1364 RX_GAIN_OFFSET_M1P5_DB);
1365 }
1366 }
1367 card = rtd->card->snd_card;
1368 if (!codec_root)
1369 codec_root = snd_info_create_subdir(card->module, "codecs",
1370 card->proc_root);
1371 if (!codec_root) {
1372 pr_debug("%s: Cannot create codecs module entry\n",
1373 __func__);
1374 goto done;
1375 }
1376 pdata->codec_root = codec_root;
1377 msm_sdw_codec_info_create_codec_entry(codec_root, component);
1378done:
1379 return 0;
1380}
1381
1382static int msm_wcn_init(struct snd_soc_pcm_runtime *rtd)
1383{
1384 unsigned int rx_ch[WCN_CDC_SLIM_RX_CH_MAX] = {157, 158};
1385 unsigned int tx_ch[WCN_CDC_SLIM_TX_CH_MAX] = {159, 160, 161};
1386 struct snd_soc_dai *component_dai = rtd->codec_dai;
1387
1388 return snd_soc_dai_set_channel_map(component_dai, ARRAY_SIZE(tx_ch),
1389 tx_ch, ARRAY_SIZE(rx_ch), rx_ch);
1390}
1391
1392static int msm_wcn_hw_params(struct snd_pcm_substream *substream,
1393 struct snd_pcm_hw_params *params)
1394{
1395 struct snd_soc_pcm_runtime *rtd = substream->private_data;
1396 struct snd_soc_dai *codec_dai = rtd->codec_dai;
1397 struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
1398 struct snd_soc_dai_link *dai_link = rtd->dai_link;
1399 u32 rx_ch[WCN_CDC_SLIM_RX_CH_MAX], tx_ch[WCN_CDC_SLIM_TX_CH_MAX];
1400 u32 rx_ch_cnt = 0, tx_ch_cnt = 0;
1401 int ret;
1402
1403 dev_dbg(rtd->dev, "%s: %s_tx_dai_id_%d\n", __func__,
1404 codec_dai->name, codec_dai->id);
1405 ret = snd_soc_dai_get_channel_map(codec_dai,
1406 &tx_ch_cnt, tx_ch, &rx_ch_cnt, rx_ch);
1407 if (ret) {
1408 dev_err(rtd->dev,
1409 "%s: failed to get BTFM codec chan map\n, err:%d\n",
1410 __func__, ret);
1411 goto exit;
1412 }
1413
1414 dev_dbg(rtd->dev, "%s: tx_ch_cnt(%d) id %d\n",
1415 __func__, tx_ch_cnt, dai_link->id);
1416
1417 ret = snd_soc_dai_set_channel_map(cpu_dai,
1418 tx_ch_cnt, tx_ch, rx_ch_cnt, rx_ch);
1419 if (ret)
1420 dev_err(rtd->dev, "%s: failed to set cpu chan map, err:%d\n",
1421 __func__, ret);
1422
1423exit:
1424 return ret;
1425}
1426
1427static int msm_snd_card_late_probe(struct snd_soc_card *card)
1428{
1429 const char *be_dl_name = LPASS_BE_INT0_MI2S_RX;
1430 struct snd_soc_component *ana_cdc;
1431 struct snd_soc_pcm_runtime *rtd;
1432 int ret = 0;
1433
1434 rtd = snd_soc_get_pcm_runtime(card, be_dl_name);
1435 if (!rtd) {
1436 dev_err(card->dev,
1437 "%s: snd_soc_get_pcm_runtime for %s failed!\n",
1438 __func__, be_dl_name);
1439 return -EINVAL;
1440 }
1441 ana_cdc = snd_soc_rtdcom_lookup(rtd, "pmic_analog_codec");
1442 if (!ana_cdc) {
1443 dev_err(card->dev,
1444 "%s: component is NULL\n", __func__);
1445 return -EINVAL;
1446 }
1447
1448 mbhc_cfg_ptr->calibration = def_msm_int_wcd_mbhc_cal();
1449 if (!mbhc_cfg_ptr->calibration)
1450 return -ENOMEM;
1451
1452 ret = msm_anlg_cdc_hs_detect(ana_cdc, mbhc_cfg_ptr);
1453 if (ret) {
1454 dev_err(card->dev,
1455 "%s: msm_anlg_cdc_hs_detect failed\n", __func__);
1456 kfree(mbhc_cfg_ptr->calibration);
1457 }
1458
1459 return ret;
1460}
1461
1462static struct snd_soc_ops msm_tdm_be_ops = {
1463 .startup = msm_tdm_snd_startup,
1464 .shutdown = msm_tdm_snd_shutdown,
1465 .hw_params = msm_tdm_snd_hw_params,
1466};
1467
1468static struct snd_soc_ops msm_wcn_ops = {
1469 .hw_params = msm_wcn_hw_params,
1470};
1471
1472static struct snd_soc_ops msm_mi2s_be_ops = {
1473 .startup = msm_mi2s_snd_startup,
1474 .shutdown = msm_mi2s_snd_shutdown,
1475};
1476
1477static struct snd_soc_ops msm_aux_pcm_be_ops = {
1478 .startup = msm_aux_pcm_snd_startup,
1479 .shutdown = msm_aux_pcm_snd_shutdown,
1480};
1481
1482static struct snd_soc_ops msm_int_mi2s_be_ops = {
1483 .startup = msm_int_mi2s_snd_startup,
1484 .shutdown = msm_int_mi2s_snd_shutdown,
1485};
1486
1487static struct snd_soc_ops msm_sdw_mi2s_be_ops = {
1488 .startup = msm_sdw_mi2s_snd_startup,
1489 .shutdown = msm_sdw_mi2s_snd_shutdown,
1490};
1491
1492static int msm_fe_qos_prepare(struct snd_pcm_substream *substream)
1493{
1494 cpumask_t mask;
1495
1496 if (pm_qos_request_active(&substream->latency_pm_qos_req))
1497 pm_qos_remove_request(&substream->latency_pm_qos_req);
1498
1499 cpumask_clear(&mask);
1500 cpumask_set_cpu(1, &mask); /* affine to core 1 */
1501 cpumask_set_cpu(2, &mask); /* affine to core 2 */
1502 cpumask_copy(&substream->latency_pm_qos_req.cpus_affine, &mask);
1503
1504 substream->latency_pm_qos_req.type = PM_QOS_REQ_AFFINE_CORES;
1505
1506 pm_qos_add_request(&substream->latency_pm_qos_req,
1507 PM_QOS_CPU_DMA_LATENCY,
1508 MSM_LL_QOS_VALUE);
1509 return 0;
1510}
1511
1512static struct snd_soc_ops msm_fe_qos_ops = {
1513 .prepare = msm_fe_qos_prepare,
1514};
1515
1516struct snd_soc_dai_link_component dlc_rx1[] = {
1517 {
1518 .of_node = NULL,
1519 .dai_name = "msm_dig_cdc_dai_rx1",
1520 },
1521 {
1522 .of_node = NULL,
1523 .dai_name = "msm_anlg_cdc_i2s_rx1",
1524 },
1525};
1526
1527struct snd_soc_dai_link_component dlc_tx1[] = {
1528 {
1529 .of_node = NULL,
1530 .dai_name = "msm_dig_cdc_dai_tx1",
1531 },
1532 {
1533 .of_node = NULL,
1534 .dai_name = "msm_anlg_cdc_i2s_tx1",
1535 },
1536};
1537
1538struct snd_soc_dai_link_component dlc_tx2[] = {
1539 {
1540 .of_node = NULL,
1541 .dai_name = "msm_dig_cdc_dai_tx2",
1542 },
1543 {
1544 .of_node = NULL,
1545 .dai_name = "msm_anlg_cdc_i2s_tx2",
1546 },
1547};
1548
1549/* Digital audio interface glue - connects codec <---> CPU */
1550static struct snd_soc_dai_link msm_int_dai[] = {
1551 /* FrontEnd DAI Links */
1552 {/* hw:x,0 */
1553 .name = MSM_DAILINK_NAME(Media1),
1554 .stream_name = "MultiMedia1",
1555 .cpu_dai_name = "MultiMedia1",
1556 .platform_name = "msm-pcm-dsp.0",
1557 .dynamic = 1,
1558 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1559 SND_SOC_DPCM_TRIGGER_POST},
1560 .codec_dai_name = "snd-soc-dummy-dai",
1561 .codec_name = "snd-soc-dummy",
1562 .ignore_suspend = 1,
1563 .dpcm_playback = 1,
1564 .dpcm_capture = 1,
1565 /* this dai link has playback support */
1566 .ignore_pmdown_time = 1,
1567 .id = MSM_FRONTEND_DAI_MULTIMEDIA1
1568 },
1569 {/* hw:x,1 */
1570 .name = MSM_DAILINK_NAME(Media2),
1571 .stream_name = "MultiMedia2",
1572 .cpu_dai_name = "MultiMedia2",
1573 .platform_name = "msm-pcm-dsp.0",
1574 .dynamic = 1,
1575 .dpcm_playback = 1,
1576 .dpcm_capture = 1,
1577 .codec_dai_name = "snd-soc-dummy-dai",
1578 .codec_name = "snd-soc-dummy",
1579 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1580 SND_SOC_DPCM_TRIGGER_POST},
1581 .ignore_suspend = 1,
1582 /* this dai link has playback support */
1583 .ignore_pmdown_time = 1,
1584 .id = MSM_FRONTEND_DAI_MULTIMEDIA2,
1585 },
1586 {/* hw:x,2 */
1587 .name = "VoiceMMode1",
1588 .stream_name = "VoiceMMode1",
1589 .cpu_dai_name = "VoiceMMode1",
1590 .platform_name = "msm-pcm-voice",
1591 .dynamic = 1,
1592 .dpcm_capture = 1,
1593 .dpcm_playback = 1,
1594 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1595 SND_SOC_DPCM_TRIGGER_POST},
1596 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1597 .ignore_suspend = 1,
1598 .ignore_pmdown_time = 1,
1599 .codec_dai_name = "snd-soc-dummy-dai",
1600 .codec_name = "snd-soc-dummy",
1601 .id = MSM_FRONTEND_DAI_VOICEMMODE1,
1602 },
1603 {/* hw:x,3 */
1604 .name = "MSM VoIP",
1605 .stream_name = "VoIP",
1606 .cpu_dai_name = "VoIP",
1607 .platform_name = "msm-voip-dsp",
1608 .dynamic = 1,
1609 .dpcm_playback = 1,
1610 .dpcm_capture = 1,
1611 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1612 SND_SOC_DPCM_TRIGGER_POST},
1613 .codec_dai_name = "snd-soc-dummy-dai",
1614 .codec_name = "snd-soc-dummy",
1615 .ignore_suspend = 1,
1616 /* this dai link has playback support */
1617 .ignore_pmdown_time = 1,
1618 .id = MSM_FRONTEND_DAI_VOIP,
1619 },
1620 {/* hw:x,4 */
1621 .name = MSM_DAILINK_NAME(ULL),
1622 .stream_name = "ULL",
1623 .cpu_dai_name = "MultiMedia3",
1624 .platform_name = "msm-pcm-dsp.2",
1625 .dynamic = 1,
1626 .dpcm_playback = 1,
1627 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1628 SND_SOC_DPCM_TRIGGER_POST},
1629 .codec_dai_name = "snd-soc-dummy-dai",
1630 .codec_name = "snd-soc-dummy",
1631 .ignore_suspend = 1,
1632 /* this dai link has playback support */
1633 .ignore_pmdown_time = 1,
1634 .id = MSM_FRONTEND_DAI_MULTIMEDIA3,
1635 },
1636 /* Hostless PCM purpose */
1637 {/* hw:x,5 */
1638 .name = "INT4 MI2S_RX Hostless",
1639 .stream_name = "INT4 MI2S_RX Hostless",
1640 .cpu_dai_name = "INT4_MI2S_RX_HOSTLESS",
1641 .platform_name = "msm-pcm-hostless",
1642 .dynamic = 1,
1643 .dpcm_playback = 1,
1644 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1645 SND_SOC_DPCM_TRIGGER_POST},
1646 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1647 .ignore_suspend = 1,
1648 /* this dailink has playback support */
1649 .ignore_pmdown_time = 1,
1650 /* This dainlink has MI2S support */
1651 .codec_dai_name = "snd-soc-dummy-dai",
1652 .codec_name = "snd-soc-dummy",
1653 },
1654 {/* hw:x,6 */
1655 .name = "MSM AFE-PCM RX",
1656 .stream_name = "AFE-PROXY RX",
1657 .cpu_dai_name = "msm-dai-q6-dev.241",
1658 .codec_name = "msm-stub-codec.1",
1659 .codec_dai_name = "msm-stub-rx",
1660 .platform_name = "msm-pcm-afe",
1661 .ignore_suspend = 1,
1662 /* this dai link has playback support */
1663 .ignore_pmdown_time = 1,
1664 },
1665 {/* hw:x,7 */
1666 .name = "MSM AFE-PCM TX",
1667 .stream_name = "AFE-PROXY TX",
1668 .cpu_dai_name = "msm-dai-q6-dev.240",
1669 .codec_name = "msm-stub-codec.1",
1670 .codec_dai_name = "msm-stub-tx",
1671 .platform_name = "msm-pcm-afe",
1672 .ignore_suspend = 1,
1673 },
1674 {/* hw:x,8 */
1675 .name = MSM_DAILINK_NAME(Compress1),
1676 .stream_name = "Compress1",
1677 .cpu_dai_name = "MultiMedia4",
1678 .platform_name = "msm-compress-dsp",
1679 .async_ops = ASYNC_DPCM_SND_SOC_HW_PARAMS,
1680 .dynamic = 1,
1681 .dpcm_capture = 1,
1682 .dpcm_playback = 1,
1683 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1684 SND_SOC_DPCM_TRIGGER_POST},
1685 .codec_dai_name = "snd-soc-dummy-dai",
1686 .codec_name = "snd-soc-dummy",
1687 .ignore_suspend = 1,
1688 .ignore_pmdown_time = 1,
1689 /* this dai link has playback support */
1690 .id = MSM_FRONTEND_DAI_MULTIMEDIA4,
1691 },
1692 {/* hw:x,9*/
1693 .name = "AUXPCM Hostless",
1694 .stream_name = "AUXPCM Hostless",
1695 .cpu_dai_name = "AUXPCM_HOSTLESS",
1696 .platform_name = "msm-pcm-hostless",
1697 .dynamic = 1,
1698 .dpcm_capture = 1,
1699 .dpcm_playback = 1,
1700 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1701 SND_SOC_DPCM_TRIGGER_POST},
1702 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1703 .ignore_suspend = 1,
1704 /* this dai link has playback support */
1705 .ignore_pmdown_time = 1,
1706 .codec_dai_name = "snd-soc-dummy-dai",
1707 .codec_name = "snd-soc-dummy",
1708 },
1709 {/* hw:x,10 */
1710 .name = "SLIMBUS_1 Hostless",
1711 .stream_name = "SLIMBUS_1 Hostless",
1712 .cpu_dai_name = "SLIMBUS1_HOSTLESS",
1713 .platform_name = "msm-pcm-hostless",
1714 .dynamic = 1,
1715 .dpcm_capture = 1,
1716 .dpcm_playback = 1,
1717 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1718 SND_SOC_DPCM_TRIGGER_POST},
1719 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1720 .ignore_suspend = 1,
1721 .ignore_pmdown_time = 1, /* dai link has playback support */
1722 .codec_dai_name = "snd-soc-dummy-dai",
1723 .codec_name = "snd-soc-dummy",
1724 },
1725 {/* hw:x,11 */
1726 .name = "INT3 MI2S_TX Hostless",
1727 .stream_name = "INT3 MI2S_TX Hostless",
1728 .cpu_dai_name = "INT3_MI2S_TX_HOSTLESS",
1729 .platform_name = "msm-pcm-hostless",
1730 .dynamic = 1,
1731 .dpcm_capture = 1,
1732 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1733 SND_SOC_DPCM_TRIGGER_POST},
1734 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1735 .ignore_suspend = 1,
1736 .codec_dai_name = "snd-soc-dummy-dai",
1737 .codec_name = "snd-soc-dummy",
1738 },
1739 {/* hw:x,12 */
1740 .name = "SLIMBUS_7 Hostless",
1741 .stream_name = "SLIMBUS_7 Hostless",
1742 .cpu_dai_name = "SLIMBUS7_HOSTLESS",
1743 .platform_name = "msm-pcm-hostless",
1744 .dynamic = 1,
1745 .dpcm_capture = 1,
1746 .dpcm_playback = 1,
1747 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1748 SND_SOC_DPCM_TRIGGER_POST},
1749 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1750 .ignore_suspend = 1,
1751 .ignore_pmdown_time = 1, /* dai link has playback support */
1752 .codec_dai_name = "snd-soc-dummy-dai",
1753 .codec_name = "snd-soc-dummy",
1754 },
1755 {/* hw:x,13 */
1756 .name = MSM_DAILINK_NAME(LowLatency),
1757 .stream_name = "MultiMedia5",
1758 .cpu_dai_name = "MultiMedia5",
1759 .platform_name = "msm-pcm-dsp.1",
1760 .dynamic = 1,
1761 .dpcm_capture = 1,
1762 .dpcm_playback = 1,
1763 .codec_dai_name = "snd-soc-dummy-dai",
1764 .codec_name = "snd-soc-dummy",
1765 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1766 SND_SOC_DPCM_TRIGGER_POST},
1767 .ignore_suspend = 1,
1768 /* this dai link has playback support */
1769 .ignore_pmdown_time = 1,
1770 .id = MSM_FRONTEND_DAI_MULTIMEDIA5,
1771 .ops = &msm_fe_qos_ops,
1772 },
1773 /* LSM FE */
1774 {/* hw:x,14 */
1775 .name = "Listen 1 Audio Service",
1776 .stream_name = "Listen 1 Audio Service",
1777 .cpu_dai_name = "LSM1",
1778 .platform_name = "msm-lsm-client",
1779 .dynamic = 1,
1780 .dpcm_capture = 1,
1781 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1782 SND_SOC_DPCM_TRIGGER_POST },
1783 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1784 .ignore_suspend = 1,
1785 .codec_dai_name = "snd-soc-dummy-dai",
1786 .codec_name = "snd-soc-dummy",
1787 .id = MSM_FRONTEND_DAI_LSM1,
1788 },
1789 {/* hw:x,15 */
1790 .name = MSM_DAILINK_NAME(Compress2),
1791 .stream_name = "Compress2",
1792 .cpu_dai_name = "MultiMedia7",
1793 .platform_name = "msm-compress-dsp",
1794 .dynamic = 1,
1795 .dpcm_capture = 1,
1796 .dpcm_playback = 1,
1797 .codec_dai_name = "snd-soc-dummy-dai",
1798 .codec_name = "snd-soc-dummy",
1799 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1800 SND_SOC_DPCM_TRIGGER_POST},
1801 .ignore_suspend = 1,
1802 .id = MSM_FRONTEND_DAI_MULTIMEDIA7,
1803 },
1804 {/* hw:x,16 */
1805 .name = MSM_DAILINK_NAME(MultiMedia10),
1806 .stream_name = "MultiMedia10",
1807 .cpu_dai_name = "MultiMedia10",
1808 .platform_name = "msm-pcm-dsp.1",
1809 .dynamic = 1,
1810 .dpcm_capture = 1,
1811 .dpcm_playback = 1,
1812 .dpcm_capture = 1,
1813 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1814 SND_SOC_DPCM_TRIGGER_POST},
1815 .codec_dai_name = "snd-soc-dummy-dai",
1816 .codec_name = "snd-soc-dummy",
1817 .ignore_suspend = 1,
1818 .ignore_pmdown_time = 1,
1819 /* this dai link has playback support */
1820 .id = MSM_FRONTEND_DAI_MULTIMEDIA10,
1821 },
1822 {/* hw:x,17 */
1823 .name = MSM_DAILINK_NAME(ULL_NOIRQ),
1824 .stream_name = "MM_NOIRQ",
1825 .cpu_dai_name = "MultiMedia8",
1826 .platform_name = "msm-pcm-dsp-noirq",
1827 .dynamic = 1,
1828 .dpcm_capture = 1,
1829 .dpcm_playback = 1,
1830 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1831 SND_SOC_DPCM_TRIGGER_POST},
1832 .codec_dai_name = "snd-soc-dummy-dai",
1833 .codec_name = "snd-soc-dummy",
1834 .ignore_suspend = 1,
1835 .ignore_pmdown_time = 1,
1836 /* this dai link has playback support */
1837 .id = MSM_FRONTEND_DAI_MULTIMEDIA8,
1838 .ops = &msm_fe_qos_ops,
1839 },
1840 {/* hw:x,18 */
1841 .name = "HDMI_RX_HOSTLESS",
1842 .stream_name = "HDMI_RX_HOSTLESS",
1843 .cpu_dai_name = "HDMI_HOSTLESS",
1844 .platform_name = "msm-pcm-hostless",
1845 .dynamic = 1,
1846 .dpcm_playback = 1,
1847 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1848 SND_SOC_DPCM_TRIGGER_POST},
1849 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1850 .ignore_suspend = 1,
1851 .ignore_pmdown_time = 1,
1852 .codec_dai_name = "snd-soc-dummy-dai",
1853 .codec_name = "snd-soc-dummy",
1854 },
1855 {/* hw:x,19 */
1856 .name = "VoiceMMode2",
1857 .stream_name = "VoiceMMode2",
1858 .cpu_dai_name = "VoiceMMode2",
1859 .platform_name = "msm-pcm-voice",
1860 .dynamic = 1,
1861 .dpcm_capture = 1,
1862 .dpcm_playback = 1,
1863 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1864 SND_SOC_DPCM_TRIGGER_POST},
1865 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1866 .ignore_suspend = 1,
1867 .ignore_pmdown_time = 1,
1868 .codec_dai_name = "snd-soc-dummy-dai",
1869 .codec_name = "snd-soc-dummy",
1870 .id = MSM_FRONTEND_DAI_VOICEMMODE2,
1871 },
1872 {/* hw:x,20 */
1873 .name = "Listen 2 Audio Service",
1874 .stream_name = "Listen 2 Audio Service",
1875 .cpu_dai_name = "LSM2",
1876 .platform_name = "msm-lsm-client",
1877 .dynamic = 1,
1878 .dpcm_capture = 1,
1879 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1880 SND_SOC_DPCM_TRIGGER_POST },
1881 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1882 .ignore_suspend = 1,
1883 .codec_dai_name = "snd-soc-dummy-dai",
1884 .codec_name = "snd-soc-dummy",
1885 .id = MSM_FRONTEND_DAI_LSM2,
1886 },
1887 {/* hw:x,21 */
1888 .name = "Listen 3 Audio Service",
1889 .stream_name = "Listen 3 Audio Service",
1890 .cpu_dai_name = "LSM3",
1891 .platform_name = "msm-lsm-client",
1892 .dynamic = 1,
1893 .dpcm_capture = 1,
1894 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1895 SND_SOC_DPCM_TRIGGER_POST },
1896 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1897 .ignore_suspend = 1,
1898 .codec_dai_name = "snd-soc-dummy-dai",
1899 .codec_name = "snd-soc-dummy",
1900 .id = MSM_FRONTEND_DAI_LSM3,
1901 },
1902 {/* hw:x,22 */
1903 .name = "Listen 4 Audio Service",
1904 .stream_name = "Listen 4 Audio Service",
1905 .cpu_dai_name = "LSM4",
1906 .platform_name = "msm-lsm-client",
1907 .dynamic = 1,
1908 .dpcm_capture = 1,
1909 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1910 SND_SOC_DPCM_TRIGGER_POST },
1911 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1912 .ignore_suspend = 1,
1913 .codec_dai_name = "snd-soc-dummy-dai",
1914 .codec_name = "snd-soc-dummy",
1915 .id = MSM_FRONTEND_DAI_LSM4,
1916 },
1917 {/* hw:x,23 */
1918 .name = "Listen 5 Audio Service",
1919 .stream_name = "Listen 5 Audio Service",
1920 .cpu_dai_name = "LSM5",
1921 .platform_name = "msm-lsm-client",
1922 .dynamic = 1,
1923 .dpcm_capture = 1,
1924 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1925 SND_SOC_DPCM_TRIGGER_POST },
1926 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1927 .ignore_suspend = 1,
1928 .codec_dai_name = "snd-soc-dummy-dai",
1929 .codec_name = "snd-soc-dummy",
1930 .id = MSM_FRONTEND_DAI_LSM5,
1931 },
1932 {/* hw:x,24 */
1933 .name = "Listen 6 Audio Service",
1934 .stream_name = "Listen 6 Audio Service",
1935 .cpu_dai_name = "LSM6",
1936 .platform_name = "msm-lsm-client",
1937 .dynamic = 1,
1938 .dpcm_capture = 1,
1939 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1940 SND_SOC_DPCM_TRIGGER_POST },
1941 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1942 .ignore_suspend = 1,
1943 .codec_dai_name = "snd-soc-dummy-dai",
1944 .codec_name = "snd-soc-dummy",
1945 .id = MSM_FRONTEND_DAI_LSM6
1946 },
1947 {/* hw:x,25 */
1948 .name = "Listen 7 Audio Service",
1949 .stream_name = "Listen 7 Audio Service",
1950 .cpu_dai_name = "LSM7",
1951 .platform_name = "msm-lsm-client",
1952 .dynamic = 1,
1953 .dpcm_capture = 1,
1954 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1955 SND_SOC_DPCM_TRIGGER_POST },
1956 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1957 .ignore_suspend = 1,
1958 .codec_dai_name = "snd-soc-dummy-dai",
1959 .codec_name = "snd-soc-dummy",
1960 .id = MSM_FRONTEND_DAI_LSM7,
1961 },
1962 {/* hw:x,26 */
1963 .name = "Listen 8 Audio Service",
1964 .stream_name = "Listen 8 Audio Service",
1965 .cpu_dai_name = "LSM8",
1966 .platform_name = "msm-lsm-client",
1967 .dynamic = 1,
1968 .dpcm_capture = 1,
1969 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1970 SND_SOC_DPCM_TRIGGER_POST },
1971 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
1972 .ignore_suspend = 1,
1973 .codec_dai_name = "snd-soc-dummy-dai",
1974 .codec_name = "snd-soc-dummy",
1975 .id = MSM_FRONTEND_DAI_LSM8,
1976 },
1977 {/* hw:x,27 */
1978 .name = MSM_DAILINK_NAME(Media9),
1979 .stream_name = "MultiMedia9",
1980 .cpu_dai_name = "MultiMedia9",
1981 .platform_name = "msm-pcm-dsp.0",
1982 .dynamic = 1,
1983 .dpcm_capture = 1,
1984 .dpcm_playback = 1,
1985 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
1986 SND_SOC_DPCM_TRIGGER_POST},
1987 .codec_dai_name = "snd-soc-dummy-dai",
1988 .codec_name = "snd-soc-dummy",
1989 .ignore_suspend = 1,
1990 .ignore_pmdown_time = 1,
1991 /* this dai link has playback support */
1992 .id = MSM_FRONTEND_DAI_MULTIMEDIA9,
1993 },
1994 {/* hw:x,28 */
1995 .name = MSM_DAILINK_NAME(Compress4),
1996 .stream_name = "Compress4",
1997 .cpu_dai_name = "MultiMedia11",
1998 .platform_name = "msm-compress-dsp",
1999 .dynamic = 1,
2000 .dpcm_capture = 1,
2001 .dpcm_playback = 1,
2002 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2003 SND_SOC_DPCM_TRIGGER_POST},
2004 .codec_dai_name = "snd-soc-dummy-dai",
2005 .codec_name = "snd-soc-dummy",
2006 .ignore_suspend = 1,
2007 .ignore_pmdown_time = 1,
2008 /* this dai link has playback support */
2009 .id = MSM_FRONTEND_DAI_MULTIMEDIA11,
2010 },
2011 {/* hw:x,29 */
2012 .name = MSM_DAILINK_NAME(Compress5),
2013 .stream_name = "Compress5",
2014 .cpu_dai_name = "MultiMedia12",
2015 .platform_name = "msm-compress-dsp",
2016 .dynamic = 1,
2017 .dpcm_capture = 1,
2018 .dpcm_playback = 1,
2019 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2020 SND_SOC_DPCM_TRIGGER_POST},
2021 .codec_dai_name = "snd-soc-dummy-dai",
2022 .codec_name = "snd-soc-dummy",
2023 .ignore_suspend = 1,
2024 .ignore_pmdown_time = 1,
2025 /* this dai link has playback support */
2026 .id = MSM_FRONTEND_DAI_MULTIMEDIA12,
2027 },
2028 {/* hw:x,30 */
2029 .name = MSM_DAILINK_NAME(Compress6),
2030 .stream_name = "Compress6",
2031 .cpu_dai_name = "MultiMedia13",
2032 .platform_name = "msm-compress-dsp",
2033 .dynamic = 1,
2034 .dpcm_capture = 1,
2035 .dpcm_playback = 1,
2036 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2037 SND_SOC_DPCM_TRIGGER_POST},
2038 .codec_dai_name = "snd-soc-dummy-dai",
2039 .codec_name = "snd-soc-dummy",
2040 .ignore_suspend = 1,
2041 .ignore_pmdown_time = 1,
2042 /* this dai link has playback support */
2043 .id = MSM_FRONTEND_DAI_MULTIMEDIA13,
2044 },
2045 {/* hw:x,31 */
2046 .name = MSM_DAILINK_NAME(Compress7),
2047 .stream_name = "Compress7",
2048 .cpu_dai_name = "MultiMedia14",
2049 .platform_name = "msm-compress-dsp",
2050 .dynamic = 1,
2051 .dpcm_capture = 1,
2052 .dpcm_playback = 1,
2053 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2054 SND_SOC_DPCM_TRIGGER_POST},
2055 .codec_dai_name = "snd-soc-dummy-dai",
2056 .codec_name = "snd-soc-dummy",
2057 .ignore_suspend = 1,
2058 .ignore_pmdown_time = 1,
2059 /* this dai link has playback support */
2060 .id = MSM_FRONTEND_DAI_MULTIMEDIA14,
2061 },
2062 {/* hw:x,32 */
2063 .name = MSM_DAILINK_NAME(Compress8),
2064 .stream_name = "Compress8",
2065 .cpu_dai_name = "MultiMedia15",
2066 .platform_name = "msm-compress-dsp",
2067 .dynamic = 1,
2068 .dpcm_capture = 1,
2069 .dpcm_playback = 1,
2070 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2071 SND_SOC_DPCM_TRIGGER_POST},
2072 .codec_dai_name = "snd-soc-dummy-dai",
2073 .codec_name = "snd-soc-dummy",
2074 .ignore_suspend = 1,
2075 .ignore_pmdown_time = 1,
2076 /* this dai link has playback support */
2077 .id = MSM_FRONTEND_DAI_MULTIMEDIA15,
2078 },
2079 {/* hw:x,33 */
2080 .name = MSM_DAILINK_NAME(ULL_NOIRQ_2),
2081 .stream_name = "MM_NOIRQ_2",
2082 .cpu_dai_name = "MultiMedia16",
2083 .platform_name = "msm-pcm-dsp-noirq",
2084 .dynamic = 1,
2085 .dpcm_capture = 1,
2086 .dpcm_playback = 1,
2087 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2088 SND_SOC_DPCM_TRIGGER_POST},
2089 .codec_dai_name = "snd-soc-dummy-dai",
2090 .codec_name = "snd-soc-dummy",
2091 .ignore_suspend = 1,
2092 .ignore_pmdown_time = 1,
2093 /* this dai link has playback support */
2094 .id = MSM_FRONTEND_DAI_MULTIMEDIA16,
2095 },
2096 {/* hw:x,34 */
2097 .name = "SLIMBUS_8 Hostless",
2098 .stream_name = "SLIMBUS8_HOSTLESS Capture",
2099 .cpu_dai_name = "SLIMBUS8_HOSTLESS",
2100 .platform_name = "msm-pcm-hostless",
2101 .dynamic = 1,
2102 .dpcm_capture = 1,
2103 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2104 SND_SOC_DPCM_TRIGGER_POST},
2105 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2106 .ignore_suspend = 1,
2107 .codec_dai_name = "snd-soc-dummy-dai",
2108 .codec_name = "snd-soc-dummy",
2109 },
2110 {/* hw:x,35 */
2111 .name = "Primary MI2S_RX Hostless",
2112 .stream_name = "Primary MI2S_RX Hostless",
2113 .cpu_dai_name = "PRI_MI2S_RX_HOSTLESS",
2114 .platform_name = "msm-pcm-hostless",
2115 .dynamic = 1,
2116 .dpcm_playback = 1,
2117 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2118 SND_SOC_DPCM_TRIGGER_POST},
2119 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2120 .ignore_suspend = 1,
2121 /* this dailink has playback support */
2122 .ignore_pmdown_time = 1,
2123 /* This dainlink has MI2S support */
2124 .codec_dai_name = "snd-soc-dummy-dai",
2125 .codec_name = "snd-soc-dummy",
2126 },
2127 {/* hw:x,36 */
2128 .name = "Secondary MI2S_RX Hostless",
2129 .stream_name = "Secondary MI2S_RX Hostless",
2130 .cpu_dai_name = "SEC_MI2S_RX_HOSTLESS",
2131 .platform_name = "msm-pcm-hostless",
2132 .dynamic = 1,
2133 .dpcm_playback = 1,
2134 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2135 SND_SOC_DPCM_TRIGGER_POST},
2136 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2137 .ignore_suspend = 1,
2138 /* this dailink has playback support */
2139 .ignore_pmdown_time = 1,
2140 /* This dainlink has MI2S support */
2141 .codec_dai_name = "snd-soc-dummy-dai",
2142 .codec_name = "snd-soc-dummy",
2143 },
2144 {/* hw:x,37 */
2145 .name = "Tertiary MI2S_RX Hostless",
2146 .stream_name = "Tertiary MI2S_RX Hostless",
2147 .cpu_dai_name = "TERT_MI2S_RX_HOSTLESS",
2148 .platform_name = "msm-pcm-hostless",
2149 .dynamic = 1,
2150 .dpcm_playback = 1,
2151 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2152 SND_SOC_DPCM_TRIGGER_POST},
2153 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2154 .ignore_suspend = 1,
2155 /* this dailink has playback support */
2156 .ignore_pmdown_time = 1,
2157 /* This dainlink has MI2S support */
2158 .codec_dai_name = "snd-soc-dummy-dai",
2159 .codec_name = "snd-soc-dummy",
2160 },
2161 {/* hw:x,38 */
2162 .name = "INT0 MI2S_RX Hostless",
2163 .stream_name = "INT0 MI2S_RX Hostless",
2164 .cpu_dai_name = "INT0_MI2S_RX_HOSTLESS",
2165 .platform_name = "msm-pcm-hostless",
2166 .dynamic = 1,
2167 .dpcm_playback = 1,
2168 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2169 SND_SOC_DPCM_TRIGGER_POST},
2170 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2171 .ignore_suspend = 1,
2172 /* this dailink has playback support */
2173 .ignore_pmdown_time = 1,
2174 /* This dainlink has MI2S support */
2175 .codec_dai_name = "snd-soc-dummy-dai",
2176 .codec_name = "snd-soc-dummy",
2177 },
2178 {/* hw:x,39 */
2179 .name = "SDM660 HFP TX",
2180 .stream_name = "MultiMedia6",
2181 .cpu_dai_name = "MultiMedia6",
2182 .platform_name = "msm-pcm-loopback",
2183 .dynamic = 1,
2184 .dpcm_playback = 1,
2185 .dpcm_capture = 1,
2186 .codec_dai_name = "snd-soc-dummy-dai",
2187 .codec_name = "snd-soc-dummy",
2188 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2189 SND_SOC_DPCM_TRIGGER_POST},
2190 .ignore_suspend = 1,
2191 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2192 .ignore_pmdown_time = 1,
2193 .id = MSM_FRONTEND_DAI_MULTIMEDIA6,
2194 },
2195};
2196
2197
2198static struct snd_soc_dai_link msm_int_wsa_dai[] = {
2199 {/* hw:x,40 */
2200 .name = LPASS_BE_INT5_MI2S_TX,
2201 .stream_name = "INT5_mi2s Capture",
2202 .cpu_dai_name = "msm-dai-q6-mi2s.12",
2203 .platform_name = "msm-pcm-hostless",
2204 .codec_name = "msm_sdw_codec",
2205 .codec_dai_name = "msm_sdw_vifeedback",
2206 .id = MSM_BACKEND_DAI_INT5_MI2S_TX,
2207 .be_hw_params_fixup = int_mi2s_be_hw_params_fixup,
2208 .ops = &msm_sdw_mi2s_be_ops,
2209 .no_host_mode = SND_SOC_DAI_LINK_NO_HOST,
2210 .ignore_suspend = 1,
2211 .dpcm_capture = 1,
2212 },
2213};
2214
2215static struct snd_soc_dai_link msm_int_compress_capture_dai[] = {
2216 {/* hw:x,41 */
2217 .name = "Compress9",
2218 .stream_name = "Compress9",
2219 .cpu_dai_name = "MultiMedia17",
2220 .platform_name = "msm-compress-dsp",
2221 .dynamic = 1,
2222 .dpcm_capture = 1,
2223 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2224 SND_SOC_DPCM_TRIGGER_POST},
2225 .codec_dai_name = "snd-soc-dummy-dai",
2226 .codec_name = "snd-soc-dummy",
2227 .ignore_suspend = 1,
2228 .id = MSM_FRONTEND_DAI_MULTIMEDIA17,
2229 },
2230 {/* hw:x,42 */
2231 .name = "Compress10",
2232 .stream_name = "Compress10",
2233 .cpu_dai_name = "MultiMedia18",
2234 .platform_name = "msm-compress-dsp",
2235 .dynamic = 1,
2236 .dpcm_capture = 1,
2237 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2238 SND_SOC_DPCM_TRIGGER_POST},
2239 .codec_dai_name = "snd-soc-dummy-dai",
2240 .codec_name = "snd-soc-dummy",
2241 .ignore_suspend = 1,
2242 .id = MSM_FRONTEND_DAI_MULTIMEDIA18,
2243 },
2244 {/* hw:x,43 */
2245 .name = "Compress11",
2246 .stream_name = "Compress11",
2247 .cpu_dai_name = "MultiMedia19",
2248 .platform_name = "msm-compress-dsp",
2249 .dynamic = 1,
2250 .dpcm_capture = 1,
2251 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2252 SND_SOC_DPCM_TRIGGER_POST},
2253 .codec_dai_name = "snd-soc-dummy-dai",
2254 .codec_name = "snd-soc-dummy",
2255 .ignore_suspend = 1,
2256 .id = MSM_FRONTEND_DAI_MULTIMEDIA19,
2257 },
2258 {/* hw:x,44 */
2259 .name = "Compress12",
2260 .stream_name = "Compress12",
2261 .cpu_dai_name = "MultiMedia28",
2262 .platform_name = "msm-compress-dsp",
2263 .dynamic = 1,
2264 .dpcm_capture = 1,
2265 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2266 SND_SOC_DPCM_TRIGGER_POST},
2267 .codec_dai_name = "snd-soc-dummy-dai",
2268 .codec_name = "snd-soc-dummy",
2269 .ignore_suspend = 1,
2270 .id = MSM_FRONTEND_DAI_MULTIMEDIA28,
2271 },
2272 {/* hw:x,45 */
2273 .name = "Compress13",
2274 .stream_name = "Compress13",
2275 .cpu_dai_name = "MultiMedia29",
2276 .platform_name = "msm-compress-dsp",
2277 .dynamic = 1,
2278 .dpcm_capture = 1,
2279 .trigger = {SND_SOC_DPCM_TRIGGER_POST,
2280 SND_SOC_DPCM_TRIGGER_POST},
2281 .codec_dai_name = "snd-soc-dummy-dai",
2282 .codec_name = "snd-soc-dummy",
2283 .ignore_suspend = 1,
2284 .id = MSM_FRONTEND_DAI_MULTIMEDIA29,
2285 },
2286};
2287
2288static struct snd_soc_dai_link msm_int_be_dai[] = {
2289 /* Backend I2S DAI Links */
2290 {
2291 .name = LPASS_BE_INT0_MI2S_RX,
2292 .stream_name = "INT0 MI2S Playback",
2293 .cpu_dai_name = "msm-dai-q6-mi2s.7",
2294 .platform_name = "msm-pcm-routing",
2295 .codecs = dlc_rx1,
2296 .num_codecs = CODECS_MAX,
2297 .no_pcm = 1,
2298 .dpcm_playback = 1,
2299 .async_ops = ASYNC_DPCM_SND_SOC_PREPARE |
2300 ASYNC_DPCM_SND_SOC_HW_PARAMS,
2301 .id = MSM_BACKEND_DAI_INT0_MI2S_RX,
2302 .init = &msm_audrx_init,
2303 .be_hw_params_fixup = int_mi2s_be_hw_params_fixup,
2304 .ops = &msm_int_mi2s_be_ops,
2305 .ignore_suspend = 1,
2306 },
2307 {
2308 .name = LPASS_BE_INT3_MI2S_TX,
2309 .stream_name = "INT3 MI2S Capture",
2310 .cpu_dai_name = "msm-dai-q6-mi2s.10",
2311 .platform_name = "msm-pcm-routing",
2312 .codecs = dlc_tx1,
2313 .num_codecs = CODECS_MAX,
2314 .no_pcm = 1,
2315 .dpcm_capture = 1,
2316 .async_ops = ASYNC_DPCM_SND_SOC_PREPARE |
2317 ASYNC_DPCM_SND_SOC_HW_PARAMS,
2318 .id = MSM_BACKEND_DAI_INT3_MI2S_TX,
2319 .be_hw_params_fixup = int_mi2s_be_hw_params_fixup,
2320 .ops = &msm_int_mi2s_be_ops,
2321 .ignore_suspend = 1,
2322 },
2323 {
2324 .name = LPASS_BE_INT2_MI2S_TX,
2325 .stream_name = "INT2 MI2S Capture",
2326 .cpu_dai_name = "msm-dai-q6-mi2s.9",
2327 .platform_name = "msm-pcm-routing",
2328 .codecs = dlc_tx2,
2329 .num_codecs = CODECS_MAX,
2330 .no_pcm = 1,
2331 .dpcm_capture = 1,
2332 .async_ops = ASYNC_DPCM_SND_SOC_PREPARE |
2333 ASYNC_DPCM_SND_SOC_HW_PARAMS,
2334 .id = MSM_BACKEND_DAI_INT2_MI2S_TX,
2335 .be_hw_params_fixup = int_mi2s_be_hw_params_fixup,
2336 .ops = &msm_int_mi2s_be_ops,
2337 .ignore_suspend = 1,
2338 },
2339 {
2340 .name = LPASS_BE_AFE_PCM_RX,
2341 .stream_name = "AFE Playback",
2342 .cpu_dai_name = "msm-dai-q6-dev.224",
2343 .platform_name = "msm-pcm-routing",
2344 .codec_name = "msm-stub-codec.1",
2345 .codec_dai_name = "msm-stub-rx",
2346 .no_pcm = 1,
2347 .dpcm_playback = 1,
2348 .id = MSM_BACKEND_DAI_AFE_PCM_RX,
2349 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2350 /* this dainlink has playback support */
2351 .ignore_pmdown_time = 1,
2352 .ignore_suspend = 1,
2353 },
2354 {
2355 .name = LPASS_BE_AFE_PCM_TX,
2356 .stream_name = "AFE Capture",
2357 .cpu_dai_name = "msm-dai-q6-dev.225",
2358 .platform_name = "msm-pcm-routing",
2359 .codec_name = "msm-stub-codec.1",
2360 .codec_dai_name = "msm-stub-tx",
2361 .no_pcm = 1,
2362 .dpcm_capture = 1,
2363 .id = MSM_BACKEND_DAI_AFE_PCM_TX,
2364 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2365 .ignore_suspend = 1,
2366 },
2367 /* Incall Record Uplink BACK END DAI Link */
2368 {
2369 .name = LPASS_BE_INCALL_RECORD_TX,
2370 .stream_name = "Voice Uplink Capture",
2371 .cpu_dai_name = "msm-dai-q6-dev.32772",
2372 .platform_name = "msm-pcm-routing",
2373 .codec_name = "msm-stub-codec.1",
2374 .codec_dai_name = "msm-stub-tx",
2375 .no_pcm = 1,
2376 .dpcm_capture = 1,
2377 .id = MSM_BACKEND_DAI_INCALL_RECORD_TX,
2378 .be_hw_params_fixup = msm_be_hw_params_fixup,
2379 .ignore_suspend = 1,
2380 },
2381 /* Incall Record Downlink BACK END DAI Link */
2382 {
2383 .name = LPASS_BE_INCALL_RECORD_RX,
2384 .stream_name = "Voice Downlink Capture",
2385 .cpu_dai_name = "msm-dai-q6-dev.32771",
2386 .platform_name = "msm-pcm-routing",
2387 .codec_name = "msm-stub-codec.1",
2388 .codec_dai_name = "msm-stub-tx",
2389 .no_pcm = 1,
2390 .dpcm_capture = 1,
2391 .id = MSM_BACKEND_DAI_INCALL_RECORD_RX,
2392 .be_hw_params_fixup = msm_be_hw_params_fixup,
2393 .ignore_suspend = 1,
2394 },
2395 /* Incall Music BACK END DAI Link */
2396 {
2397 .name = LPASS_BE_VOICE_PLAYBACK_TX,
2398 .stream_name = "Voice Farend Playback",
2399 .cpu_dai_name = "msm-dai-q6-dev.32773",
2400 .platform_name = "msm-pcm-routing",
2401 .codec_name = "msm-stub-codec.1",
2402 .codec_dai_name = "msm-stub-rx",
2403 .no_pcm = 1,
2404 .dpcm_playback = 1,
2405 .id = MSM_BACKEND_DAI_VOICE_PLAYBACK_TX,
2406 .be_hw_params_fixup = msm_be_hw_params_fixup,
2407 .ignore_suspend = 1,
2408 .ignore_pmdown_time = 1,
2409 },
2410 /* Incall Music 2 BACK END DAI Link */
2411 {
2412 .name = LPASS_BE_VOICE2_PLAYBACK_TX,
2413 .stream_name = "Voice2 Farend Playback",
2414 .cpu_dai_name = "msm-dai-q6-dev.32770",
2415 .platform_name = "msm-pcm-routing",
2416 .codec_name = "msm-stub-codec.1",
2417 .codec_dai_name = "msm-stub-rx",
2418 .no_pcm = 1,
2419 .dpcm_playback = 1,
2420 .id = MSM_BACKEND_DAI_VOICE2_PLAYBACK_TX,
2421 .be_hw_params_fixup = msm_be_hw_params_fixup,
2422 .ignore_suspend = 1,
2423 .ignore_pmdown_time = 1,
2424 },
2425 {
2426 .name = LPASS_BE_USB_AUDIO_RX,
2427 .stream_name = "USB Audio Playback",
2428 .cpu_dai_name = "msm-dai-q6-dev.28672",
2429 .platform_name = "msm-pcm-routing",
2430 .codec_name = "msm-stub-codec.1",
2431 .codec_dai_name = "msm-stub-rx",
2432 .no_pcm = 1,
2433 .dpcm_playback = 1,
2434 .id = MSM_BACKEND_DAI_USB_RX,
2435 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2436 .ignore_pmdown_time = 1,
2437 .ignore_suspend = 1,
2438 },
2439 {
2440 .name = LPASS_BE_USB_AUDIO_TX,
2441 .stream_name = "USB Audio Capture",
2442 .cpu_dai_name = "msm-dai-q6-dev.28673",
2443 .platform_name = "msm-pcm-routing",
2444 .codec_name = "msm-stub-codec.1",
2445 .codec_dai_name = "msm-stub-tx",
2446 .no_pcm = 1,
2447 .dpcm_capture = 1,
2448 .id = MSM_BACKEND_DAI_USB_TX,
2449 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2450 .ignore_suspend = 1,
2451 },
2452 {
2453 .name = LPASS_BE_PRI_TDM_RX_0,
2454 .stream_name = "Primary TDM0 Playback",
2455 .cpu_dai_name = "msm-dai-q6-tdm.36864",
2456 .platform_name = "msm-pcm-routing",
2457 .codec_name = "msm-stub-codec.1",
2458 .codec_dai_name = "msm-stub-rx",
2459 .no_pcm = 1,
2460 .dpcm_playback = 1,
2461 .id = MSM_BACKEND_DAI_PRI_TDM_RX_0,
2462 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2463 .ops = &msm_tdm_be_ops,
2464 .ignore_suspend = 1,
2465 .ignore_pmdown_time = 1,
2466 },
2467 {
2468 .name = LPASS_BE_PRI_TDM_TX_0,
2469 .stream_name = "Primary TDM0 Capture",
2470 .cpu_dai_name = "msm-dai-q6-tdm.36865",
2471 .platform_name = "msm-pcm-routing",
2472 .codec_name = "msm-stub-codec.1",
2473 .codec_dai_name = "msm-stub-tx",
2474 .no_pcm = 1,
2475 .dpcm_capture = 1,
2476 .id = MSM_BACKEND_DAI_PRI_TDM_TX_0,
2477 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2478 .ops = &msm_tdm_be_ops,
2479 .ignore_suspend = 1,
2480 },
2481 {
2482 .name = LPASS_BE_SEC_TDM_RX_0,
2483 .stream_name = "Secondary TDM0 Playback",
2484 .cpu_dai_name = "msm-dai-q6-tdm.36880",
2485 .platform_name = "msm-pcm-routing",
2486 .codec_name = "msm-stub-codec.1",
2487 .codec_dai_name = "msm-stub-rx",
2488 .no_pcm = 1,
2489 .dpcm_playback = 1,
2490 .id = MSM_BACKEND_DAI_SEC_TDM_RX_0,
2491 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2492 .ops = &msm_tdm_be_ops,
2493 .ignore_suspend = 1,
2494 .ignore_pmdown_time = 1,
2495 },
2496 {
2497 .name = LPASS_BE_SEC_TDM_TX_0,
2498 .stream_name = "Secondary TDM0 Capture",
2499 .cpu_dai_name = "msm-dai-q6-tdm.36881",
2500 .platform_name = "msm-pcm-routing",
2501 .codec_name = "msm-stub-codec.1",
2502 .codec_dai_name = "msm-stub-tx",
2503 .no_pcm = 1,
2504 .dpcm_capture = 1,
2505 .id = MSM_BACKEND_DAI_SEC_TDM_TX_0,
2506 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2507 .ops = &msm_tdm_be_ops,
2508 .ignore_suspend = 1,
2509 },
2510 {
2511 .name = LPASS_BE_TERT_TDM_RX_0,
2512 .stream_name = "Tertiary TDM0 Playback",
2513 .cpu_dai_name = "msm-dai-q6-tdm.36896",
2514 .platform_name = "msm-pcm-routing",
2515 .codec_name = "msm-stub-codec.1",
2516 .codec_dai_name = "msm-stub-rx",
2517 .no_pcm = 1,
2518 .dpcm_playback = 1,
2519 .id = MSM_BACKEND_DAI_TERT_TDM_RX_0,
2520 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2521 .ops = &msm_tdm_be_ops,
2522 .ignore_suspend = 1,
2523 .ignore_pmdown_time = 1,
2524 },
2525 {
2526 .name = LPASS_BE_TERT_TDM_TX_0,
2527 .stream_name = "Tertiary TDM0 Capture",
2528 .cpu_dai_name = "msm-dai-q6-tdm.36897",
2529 .platform_name = "msm-pcm-routing",
2530 .codec_name = "msm-stub-codec.1",
2531 .codec_dai_name = "msm-stub-tx",
2532 .no_pcm = 1,
2533 .dpcm_capture = 1,
2534 .id = MSM_BACKEND_DAI_TERT_TDM_TX_0,
2535 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2536 .ops = &msm_tdm_be_ops,
2537 .ignore_suspend = 1,
2538 },
2539 {
2540 .name = LPASS_BE_QUAT_TDM_RX_0,
2541 .stream_name = "Quaternary TDM0 Playback",
2542 .cpu_dai_name = "msm-dai-q6-tdm.36912",
2543 .platform_name = "msm-pcm-routing",
2544 .codec_name = "msm-stub-codec.1",
2545 .codec_dai_name = "msm-stub-rx",
2546 .no_pcm = 1,
2547 .dpcm_playback = 1,
2548 .id = MSM_BACKEND_DAI_QUAT_TDM_RX_0,
2549 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2550 .ops = &msm_tdm_be_ops,
2551 .ignore_suspend = 1,
2552 .ignore_pmdown_time = 1,
2553 },
2554 {
2555 .name = LPASS_BE_QUAT_TDM_TX_0,
2556 .stream_name = "Quaternary TDM0 Capture",
2557 .cpu_dai_name = "msm-dai-q6-tdm.36913",
2558 .platform_name = "msm-pcm-routing",
2559 .codec_name = "msm-stub-codec.1",
2560 .codec_dai_name = "msm-stub-tx",
2561 .no_pcm = 1,
2562 .dpcm_capture = 1,
2563 .id = MSM_BACKEND_DAI_QUAT_TDM_TX_0,
2564 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2565 .ops = &msm_tdm_be_ops,
2566 .ignore_suspend = 1,
2567 },
2568 {
2569 .name = LPASS_BE_QUIN_TDM_RX_0,
2570 .stream_name = "Quinary TDM0 Playback",
2571 .cpu_dai_name = "msm-dai-q6-tdm.36928",
2572 .platform_name = "msm-pcm-routing",
2573 .codec_name = "msm-stub-codec.1",
2574 .codec_dai_name = "msm-stub-rx",
2575 .no_pcm = 1,
2576 .dpcm_playback = 1,
2577 .id = MSM_BACKEND_DAI_QUIN_TDM_RX_0,
2578 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2579 .ops = &msm_tdm_be_ops,
2580 .ignore_suspend = 1,
2581 .ignore_pmdown_time = 1,
2582 },
2583 {
2584 .name = LPASS_BE_QUIN_TDM_TX_0,
2585 .stream_name = "Quinary TDM0 Capture",
2586 .cpu_dai_name = "msm-dai-q6-tdm.36929",
2587 .platform_name = "msm-pcm-routing",
2588 .codec_name = "msm-stub-codec.1",
2589 .codec_dai_name = "msm-stub-tx",
2590 .no_pcm = 1,
2591 .dpcm_capture = 1,
2592 .id = MSM_BACKEND_DAI_QUIN_TDM_TX_0,
2593 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2594 .ops = &msm_tdm_be_ops,
2595 .ignore_suspend = 1,
2596 },
2597};
2598
2599static struct snd_soc_dai_link msm_mi2s_be_dai_links[] = {
2600 {
2601 .name = LPASS_BE_PRI_MI2S_RX,
2602 .stream_name = "Primary MI2S Playback",
2603 .cpu_dai_name = "msm-dai-q6-mi2s.0",
2604 .platform_name = "msm-pcm-routing",
2605 .codec_name = "msm-stub-codec.1",
2606 .codec_dai_name = "msm-stub-rx",
2607 .no_pcm = 1,
2608 .dpcm_playback = 1,
2609 .id = MSM_BACKEND_DAI_PRI_MI2S_RX,
2610 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2611 .ops = &msm_mi2s_be_ops,
2612 .ignore_suspend = 1,
2613 .ignore_pmdown_time = 1,
2614 },
2615 {
2616 .name = LPASS_BE_PRI_MI2S_TX,
2617 .stream_name = "Primary MI2S Capture",
2618 .cpu_dai_name = "msm-dai-q6-mi2s.0",
2619 .platform_name = "msm-pcm-routing",
2620 .codec_name = "msm-stub-codec.1",
2621 .codec_dai_name = "msm-stub-tx",
2622 .no_pcm = 1,
2623 .dpcm_capture = 1,
2624 .id = MSM_BACKEND_DAI_PRI_MI2S_TX,
2625 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2626 .ops = &msm_mi2s_be_ops,
2627 .ignore_suspend = 1,
2628 },
2629 {
2630 .name = LPASS_BE_SEC_MI2S_RX,
2631 .stream_name = "Secondary MI2S Playback",
2632 .cpu_dai_name = "msm-dai-q6-mi2s.1",
2633 .platform_name = "msm-pcm-routing",
2634 .codec_name = "msm-stub-codec.1",
2635 .codec_dai_name = "msm-stub-rx",
2636 .no_pcm = 1,
2637 .dpcm_playback = 1,
2638 .id = MSM_BACKEND_DAI_SECONDARY_MI2S_RX,
2639 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2640 .ops = &msm_mi2s_be_ops,
2641 .ignore_suspend = 1,
2642 .ignore_pmdown_time = 1,
2643 },
2644 {
2645 .name = LPASS_BE_SEC_MI2S_TX,
2646 .stream_name = "Secondary MI2S Capture",
2647 .cpu_dai_name = "msm-dai-q6-mi2s.1",
2648 .platform_name = "msm-pcm-routing",
2649 .codec_name = "msm-stub-codec.1",
2650 .codec_dai_name = "msm-stub-tx",
2651 .no_pcm = 1,
2652 .dpcm_capture = 1,
2653 .id = MSM_BACKEND_DAI_SECONDARY_MI2S_TX,
2654 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2655 .ops = &msm_mi2s_be_ops,
2656 .ignore_suspend = 1,
2657 },
2658 {
2659 .name = LPASS_BE_TERT_MI2S_RX,
2660 .stream_name = "Tertiary MI2S Playback",
2661 .cpu_dai_name = "msm-dai-q6-mi2s.2",
2662 .platform_name = "msm-pcm-routing",
2663 .codec_name = "msm-stub-codec.1",
2664 .codec_dai_name = "msm-stub-rx",
2665 .no_pcm = 1,
2666 .dpcm_playback = 1,
2667 .id = MSM_BACKEND_DAI_TERTIARY_MI2S_RX,
2668 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2669 .ops = &msm_mi2s_be_ops,
2670 .ignore_suspend = 1,
2671 .ignore_pmdown_time = 1,
2672 },
2673 {
2674 .name = LPASS_BE_TERT_MI2S_TX,
2675 .stream_name = "Tertiary MI2S Capture",
2676 .cpu_dai_name = "msm-dai-q6-mi2s.2",
2677 .platform_name = "msm-pcm-routing",
2678 .codec_name = "msm-stub-codec.1",
2679 .codec_dai_name = "msm-stub-tx",
2680 .no_pcm = 1,
2681 .dpcm_capture = 1,
2682 .id = MSM_BACKEND_DAI_TERTIARY_MI2S_TX,
2683 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2684 .ops = &msm_mi2s_be_ops,
2685 .ignore_suspend = 1,
2686 },
2687 {
2688 .name = LPASS_BE_QUAT_MI2S_RX,
2689 .stream_name = "Quaternary MI2S Playback",
2690 .cpu_dai_name = "msm-dai-q6-mi2s.3",
2691 .platform_name = "msm-pcm-routing",
2692 .codec_name = "msm-stub-codec.1",
2693 .codec_dai_name = "msm-stub-rx",
2694 .no_pcm = 1,
2695 .dpcm_playback = 1,
2696 .id = MSM_BACKEND_DAI_QUATERNARY_MI2S_RX,
2697 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2698 .ops = &msm_mi2s_be_ops,
2699 .ignore_suspend = 1,
2700 .ignore_pmdown_time = 1,
2701 },
2702 {
2703 .name = LPASS_BE_QUAT_MI2S_TX,
2704 .stream_name = "Quaternary MI2S Capture",
2705 .cpu_dai_name = "msm-dai-q6-mi2s.3",
2706 .platform_name = "msm-pcm-routing",
2707 .codec_name = "msm-stub-codec.1",
2708 .codec_dai_name = "msm-stub-tx",
2709 .no_pcm = 1,
2710 .dpcm_capture = 1,
2711 .id = MSM_BACKEND_DAI_QUATERNARY_MI2S_TX,
2712 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2713 .ops = &msm_mi2s_be_ops,
2714 .ignore_suspend = 1,
2715 },
2716 {
2717 .name = LPASS_BE_QUIN_MI2S_RX,
2718 .stream_name = "Quinary MI2S Playback",
2719 .cpu_dai_name = "msm-dai-q6-mi2s.4",
2720 .platform_name = "msm-pcm-routing",
2721 .codec_name = "msm-stub-codec.1",
2722 .codec_dai_name = "msm-stub-rx",
2723 .no_pcm = 1,
2724 .dpcm_playback = 1,
2725 .id = MSM_BACKEND_DAI_QUINARY_MI2S_RX,
2726 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2727 .ops = &msm_mi2s_be_ops,
2728 .ignore_suspend = 1,
2729 .ignore_pmdown_time = 1,
2730 },
2731 {
2732 .name = LPASS_BE_QUIN_MI2S_TX,
2733 .stream_name = "Quinary MI2S Capture",
2734 .cpu_dai_name = "msm-dai-q6-mi2s.4",
2735 .platform_name = "msm-pcm-routing",
2736 .codec_name = "msm-stub-codec.1",
2737 .codec_dai_name = "msm-stub-tx",
2738 .no_pcm = 1,
2739 .dpcm_capture = 1,
2740 .id = MSM_BACKEND_DAI_QUINARY_MI2S_TX,
2741 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2742 .ops = &msm_mi2s_be_ops,
2743 .ignore_suspend = 1,
2744 },
2745};
2746
2747static struct snd_soc_dai_link msm_auxpcm_be_dai_links[] = {
2748 /* Primary AUX PCM Backend DAI Links */
2749 {
2750 .name = LPASS_BE_AUXPCM_RX,
2751 .stream_name = "AUX PCM Playback",
2752 .cpu_dai_name = "msm-dai-q6-auxpcm.1",
2753 .platform_name = "msm-pcm-routing",
2754 .codec_name = "msm-stub-codec.1",
2755 .codec_dai_name = "msm-stub-rx",
2756 .no_pcm = 1,
2757 .dpcm_playback = 1,
2758 .id = MSM_BACKEND_DAI_AUXPCM_RX,
2759 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2760 .ignore_pmdown_time = 1,
2761 .ignore_suspend = 1,
2762 .ops = &msm_aux_pcm_be_ops,
2763 },
2764 {
2765 .name = LPASS_BE_AUXPCM_TX,
2766 .stream_name = "AUX PCM Capture",
2767 .cpu_dai_name = "msm-dai-q6-auxpcm.1",
2768 .platform_name = "msm-pcm-routing",
2769 .codec_name = "msm-stub-codec.1",
2770 .codec_dai_name = "msm-stub-tx",
2771 .no_pcm = 1,
2772 .dpcm_capture = 1,
2773 .id = MSM_BACKEND_DAI_AUXPCM_TX,
2774 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2775 .ignore_suspend = 1,
2776 .ops = &msm_aux_pcm_be_ops,
2777 },
2778 /* Secondary AUX PCM Backend DAI Links */
2779 {
2780 .name = LPASS_BE_SEC_AUXPCM_RX,
2781 .stream_name = "Sec AUX PCM Playback",
2782 .cpu_dai_name = "msm-dai-q6-auxpcm.2",
2783 .platform_name = "msm-pcm-routing",
2784 .codec_name = "msm-stub-codec.1",
2785 .codec_dai_name = "msm-stub-rx",
2786 .no_pcm = 1,
2787 .dpcm_playback = 1,
2788 .id = MSM_BACKEND_DAI_SEC_AUXPCM_RX,
2789 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2790 .ignore_pmdown_time = 1,
2791 .ignore_suspend = 1,
2792 .ops = &msm_aux_pcm_be_ops,
2793 },
2794 {
2795 .name = LPASS_BE_SEC_AUXPCM_TX,
2796 .stream_name = "Sec AUX PCM Capture",
2797 .cpu_dai_name = "msm-dai-q6-auxpcm.2",
2798 .platform_name = "msm-pcm-routing",
2799 .codec_name = "msm-stub-codec.1",
2800 .codec_dai_name = "msm-stub-tx",
2801 .no_pcm = 1,
2802 .dpcm_capture = 1,
2803 .id = MSM_BACKEND_DAI_SEC_AUXPCM_TX,
2804 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2805 .ignore_suspend = 1,
2806 .ops = &msm_aux_pcm_be_ops,
2807 },
2808 /* Tertiary AUX PCM Backend DAI Links */
2809 {
2810 .name = LPASS_BE_TERT_AUXPCM_RX,
2811 .stream_name = "Tert AUX PCM Playback",
2812 .cpu_dai_name = "msm-dai-q6-auxpcm.3",
2813 .platform_name = "msm-pcm-routing",
2814 .codec_name = "msm-stub-codec.1",
2815 .codec_dai_name = "msm-stub-rx",
2816 .no_pcm = 1,
2817 .dpcm_playback = 1,
2818 .id = MSM_BACKEND_DAI_TERT_AUXPCM_RX,
2819 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2820 .ignore_pmdown_time = 1,
2821 .ignore_suspend = 1,
2822 .ops = &msm_aux_pcm_be_ops,
2823 },
2824 {
2825 .name = LPASS_BE_TERT_AUXPCM_TX,
2826 .stream_name = "Tert AUX PCM Capture",
2827 .cpu_dai_name = "msm-dai-q6-auxpcm.3",
2828 .platform_name = "msm-pcm-routing",
2829 .codec_name = "msm-stub-codec.1",
2830 .codec_dai_name = "msm-stub-tx",
2831 .no_pcm = 1,
2832 .dpcm_capture = 1,
2833 .id = MSM_BACKEND_DAI_TERT_AUXPCM_TX,
2834 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2835 .ignore_suspend = 1,
2836 .ops = &msm_aux_pcm_be_ops,
2837 },
2838 /* Quaternary AUX PCM Backend DAI Links */
2839 {
2840 .name = LPASS_BE_QUAT_AUXPCM_RX,
2841 .stream_name = "Quat AUX PCM Playback",
2842 .cpu_dai_name = "msm-dai-q6-auxpcm.4",
2843 .platform_name = "msm-pcm-routing",
2844 .codec_name = "msm-stub-codec.1",
2845 .codec_dai_name = "msm-stub-rx",
2846 .no_pcm = 1,
2847 .dpcm_playback = 1,
2848 .id = MSM_BACKEND_DAI_QUAT_AUXPCM_RX,
2849 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2850 .ignore_pmdown_time = 1,
2851 .ignore_suspend = 1,
2852 .ops = &msm_aux_pcm_be_ops,
2853 },
2854 {
2855 .name = LPASS_BE_QUAT_AUXPCM_TX,
2856 .stream_name = "Quat AUX PCM Capture",
2857 .cpu_dai_name = "msm-dai-q6-auxpcm.4",
2858 .platform_name = "msm-pcm-routing",
2859 .codec_name = "msm-stub-codec.1",
2860 .codec_dai_name = "msm-stub-tx",
2861 .no_pcm = 1,
2862 .dpcm_capture = 1,
2863 .id = MSM_BACKEND_DAI_QUAT_AUXPCM_TX,
2864 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2865 .ignore_suspend = 1,
2866 .ops = &msm_aux_pcm_be_ops,
2867 },
2868 /* Quinary AUX PCM Backend DAI Links */
2869 {
2870 .name = LPASS_BE_QUIN_AUXPCM_RX,
2871 .stream_name = "Quin AUX PCM Playback",
2872 .cpu_dai_name = "msm-dai-q6-auxpcm.5",
2873 .platform_name = "msm-pcm-routing",
2874 .codec_name = "msm-stub-codec.1",
2875 .codec_dai_name = "msm-stub-rx",
2876 .no_pcm = 1,
2877 .dpcm_playback = 1,
2878 .id = MSM_BACKEND_DAI_QUIN_AUXPCM_RX,
2879 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2880 .ignore_pmdown_time = 1,
2881 .ignore_suspend = 1,
2882 .ops = &msm_aux_pcm_be_ops,
2883 },
2884 {
2885 .name = LPASS_BE_QUIN_AUXPCM_TX,
2886 .stream_name = "Quin AUX PCM Capture",
2887 .cpu_dai_name = "msm-dai-q6-auxpcm.5",
2888 .platform_name = "msm-pcm-routing",
2889 .codec_name = "msm-stub-codec.1",
2890 .codec_dai_name = "msm-stub-tx",
2891 .no_pcm = 1,
2892 .dpcm_capture = 1,
2893 .id = MSM_BACKEND_DAI_QUIN_AUXPCM_TX,
2894 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2895 .ignore_suspend = 1,
2896 .ops = &msm_aux_pcm_be_ops,
2897 },
2898};
2899
2900
2901static struct snd_soc_dai_link msm_wcn_be_dai_links[] = {
2902 {
2903 .name = LPASS_BE_SLIMBUS_7_RX,
2904 .stream_name = "Slimbus7 Playback",
2905 .cpu_dai_name = "msm-dai-q6-dev.16398",
2906 .platform_name = "msm-pcm-routing",
2907 .codec_name = "btfmslim_slave",
2908 /* BT codec driver determines capabilities based on
2909 * dai name, bt codecdai name should always contains
2910 * supported usecase information
2911 */
2912 .codec_dai_name = "btfm_bt_sco_a2dp_slim_rx",
2913 .no_pcm = 1,
2914 .dpcm_playback = 1,
2915 .id = MSM_BACKEND_DAI_SLIMBUS_7_RX,
2916 .be_hw_params_fixup = msm_btfm_be_hw_params_fixup,
2917 .ops = &msm_wcn_ops,
2918 /* dai link has playback support */
2919 .ignore_pmdown_time = 1,
2920 .ignore_suspend = 1,
2921 },
2922 {
2923 .name = LPASS_BE_SLIMBUS_7_TX,
2924 .stream_name = "Slimbus7 Capture",
2925 .cpu_dai_name = "msm-dai-q6-dev.16399",
2926 .platform_name = "msm-pcm-routing",
2927 .codec_name = "btfmslim_slave",
2928 .codec_dai_name = "btfm_bt_sco_slim_tx",
2929 .no_pcm = 1,
2930 .dpcm_capture = 1,
2931 .id = MSM_BACKEND_DAI_SLIMBUS_7_TX,
2932 .be_hw_params_fixup = msm_btfm_be_hw_params_fixup,
2933 .ops = &msm_wcn_ops,
2934 .ignore_suspend = 1,
2935 },
2936 {
2937 .name = LPASS_BE_SLIMBUS_8_TX,
2938 .stream_name = "Slimbus8 Capture",
2939 .cpu_dai_name = "msm-dai-q6-dev.16401",
2940 .platform_name = "msm-pcm-routing",
2941 .codec_name = "btfmslim_slave",
2942 .codec_dai_name = "btfm_fm_slim_tx",
2943 .no_pcm = 1,
2944 .dpcm_capture = 1,
2945 .id = MSM_BACKEND_DAI_SLIMBUS_8_TX,
2946 .be_hw_params_fixup = msm_btfm_be_hw_params_fixup,
2947 .init = &msm_wcn_init,
2948 .ops = &msm_wcn_ops,
2949 .ignore_suspend = 1,
2950 },
2951};
2952
2953static struct snd_soc_dai_link msm_wsa_be_dai_links[] = {
2954 {
2955 .name = LPASS_BE_INT4_MI2S_RX,
2956 .stream_name = "INT4 MI2S Playback",
2957 .cpu_dai_name = "msm-dai-q6-mi2s.11",
2958 .platform_name = "msm-pcm-routing",
2959 .codec_name = "msm_sdw_codec",
2960 .codec_dai_name = "msm_sdw_i2s_rx1",
2961 .no_pcm = 1,
2962 .dpcm_playback = 1,
2963 .id = MSM_BACKEND_DAI_INT4_MI2S_RX,
2964 .init = &msm_sdw_audrx_init,
2965 .be_hw_params_fixup = int_mi2s_be_hw_params_fixup,
2966 .ops = &msm_sdw_mi2s_be_ops,
2967 .ignore_suspend = 1,
2968 },
2969};
2970
2971static struct snd_soc_dai_link ext_disp_be_dai_link[] = {
2972 /* DISP PORT BACK END DAI Link */
2973 {
2974 .name = LPASS_BE_DISPLAY_PORT,
2975 .stream_name = "Display Port Playback",
2976 .cpu_dai_name = "msm-dai-q6-dp.24608",
2977 .platform_name = "msm-pcm-routing",
2978 .codec_name = "msm-ext-disp-audio-codec-rx",
2979 .codec_dai_name = "msm_dp_audio_codec_rx_dai",
2980 .no_pcm = 1,
2981 .dpcm_playback = 1,
2982 .id = MSM_BACKEND_DAI_DISPLAY_PORT_RX,
2983 .be_hw_params_fixup = msm_common_be_hw_params_fixup,
2984 .ignore_pmdown_time = 1,
2985 .ignore_suspend = 1,
2986 },
2987};
2988
2989static struct snd_soc_dai_link msm_int_dai_links[
2990ARRAY_SIZE(msm_int_dai) +
2991ARRAY_SIZE(msm_int_wsa_dai) +
2992ARRAY_SIZE(msm_int_compress_capture_dai) +
2993ARRAY_SIZE(msm_int_be_dai) +
2994ARRAY_SIZE(msm_mi2s_be_dai_links) +
2995ARRAY_SIZE(msm_auxpcm_be_dai_links)+
2996ARRAY_SIZE(msm_wcn_be_dai_links) +
2997ARRAY_SIZE(msm_wsa_be_dai_links) +
2998ARRAY_SIZE(ext_disp_be_dai_link)];
2999
3000static struct snd_soc_card sdm660_card = {
3001 /* snd_soc_card_sdm660 */
3002 .name = "sdm660-snd-card",
3003 .dai_link = msm_int_dai,
3004 .num_links = ARRAY_SIZE(msm_int_dai),
3005 .late_probe = msm_snd_card_late_probe,
3006};
3007
3008static void msm_disable_int_mclk0(struct work_struct *work)
3009{
3010 struct msm_asoc_mach_data *pdata = NULL;
3011 struct delayed_work *dwork;
3012 int ret = 0;
3013
3014 dwork = to_delayed_work(work);
3015 pdata = container_of(dwork, struct msm_asoc_mach_data,
3016 disable_int_mclk0_work);
3017 mutex_lock(&pdata->cdc_int_mclk0_mutex);
3018 pr_debug("%s: mclk_enabled %d mclk_rsc_ref %d\n", __func__,
3019 atomic_read(&pdata->int_mclk0_enabled),
3020 atomic_read(&pdata->int_mclk0_rsc_ref));
3021
3022 if (atomic_read(&pdata->int_mclk0_enabled) == true
3023 && atomic_read(&pdata->int_mclk0_rsc_ref) == 0) {
3024 pr_debug("Disable the mclk\n");
3025 pdata->digital_cdc_core_clk.enable = 0;
3026 pdata->digital_cdc_core_clk.clk_freq_in_hz =
3027 DEFAULT_MCLK_RATE;
3028 ret = afe_set_lpass_clock_v2(
3029 AFE_PORT_ID_INT0_MI2S_RX,
3030 &pdata->digital_cdc_core_clk);
3031 if (ret < 0)
3032 pr_err("%s failed to disable the CCLK\n", __func__);
3033 atomic_set(&pdata->int_mclk0_enabled, false);
3034 }
3035 mutex_unlock(&pdata->cdc_int_mclk0_mutex);
3036}
3037
3038static void msm_int_dt_parse_cap_info(struct platform_device *pdev,
3039 struct msm_asoc_mach_data *pdata)
3040{
3041 const char *ext1_cap = "qcom,msm-micbias1-ext-cap";
3042 const char *ext2_cap = "qcom,msm-micbias2-ext-cap";
3043
3044 pdata->micbias1_cap_mode =
3045 (of_property_read_bool(pdev->dev.of_node, ext1_cap) ?
3046 MICBIAS_EXT_BYP_CAP : MICBIAS_NO_EXT_BYP_CAP);
3047
3048 pdata->micbias2_cap_mode =
3049 (of_property_read_bool(pdev->dev.of_node, ext2_cap) ?
3050 MICBIAS_EXT_BYP_CAP : MICBIAS_NO_EXT_BYP_CAP);
3051}
3052
3053static struct snd_soc_card *msm_int_populate_sndcard_dailinks(
3054 struct device *dev)
3055{
3056 struct snd_soc_card *card = &sdm660_card;
3057 struct snd_soc_dai_link *dailink;
3058 int len1;
3059
3060 card->name = dev_name(dev);
3061 len1 = ARRAY_SIZE(msm_int_dai);
3062 memcpy(msm_int_dai_links, msm_int_dai, sizeof(msm_int_dai));
3063 dailink = msm_int_dai_links;
3064 if (!of_property_read_bool(dev->of_node,
3065 "qcom,wsa-disable")) {
3066 memcpy(dailink + len1,
3067 msm_int_wsa_dai,
3068 sizeof(msm_int_wsa_dai));
3069 len1 += ARRAY_SIZE(msm_int_wsa_dai);
3070 }
3071 memcpy(dailink + len1, msm_int_compress_capture_dai,
3072 sizeof(msm_int_compress_capture_dai));
3073 len1 += ARRAY_SIZE(msm_int_compress_capture_dai);
3074
3075 memcpy(dailink + len1, msm_int_be_dai, sizeof(msm_int_be_dai));
3076 len1 += ARRAY_SIZE(msm_int_be_dai);
3077
3078 if (of_property_read_bool(dev->of_node,
3079 "qcom,mi2s-audio-intf")) {
3080 memcpy(dailink + len1,
3081 msm_mi2s_be_dai_links,
3082 sizeof(msm_mi2s_be_dai_links));
3083 len1 += ARRAY_SIZE(msm_mi2s_be_dai_links);
3084 }
3085 if (of_property_read_bool(dev->of_node,
3086 "qcom,auxpcm-audio-intf")) {
3087 memcpy(dailink + len1,
3088 msm_auxpcm_be_dai_links,
3089 sizeof(msm_auxpcm_be_dai_links));
3090 len1 += ARRAY_SIZE(msm_auxpcm_be_dai_links);
3091 }
3092 if (of_property_read_bool(dev->of_node, "qcom,wcn-btfm")) {
3093 dev_dbg(dev, "%s(): WCN BTFM support present\n",
3094 __func__);
3095 memcpy(dailink + len1,
3096 msm_wcn_be_dai_links,
3097 sizeof(msm_wcn_be_dai_links));
3098 len1 += ARRAY_SIZE(msm_wcn_be_dai_links);
3099 }
3100 if (!of_property_read_bool(dev->of_node, "qcom,wsa-disable")) {
3101 memcpy(dailink + len1,
3102 msm_wsa_be_dai_links,
3103 sizeof(msm_wsa_be_dai_links));
3104 len1 += ARRAY_SIZE(msm_wsa_be_dai_links);
3105 }
3106 if (of_property_read_bool(dev->of_node, "qcom,ext-disp-audio-rx")) {
3107 dev_dbg(dev, "%s(): ext disp audio support present\n",
3108 __func__);
3109 memcpy(dailink + len1,
3110 ext_disp_be_dai_link,
3111 sizeof(ext_disp_be_dai_link));
3112 len1 += ARRAY_SIZE(ext_disp_be_dai_link);
3113 }
3114 card->dai_link = dailink;
3115 card->num_links = len1;
3116 return card;
3117}
3118
3119static int msm_internal_init(struct platform_device *pdev,
3120 struct msm_asoc_mach_data *pdata,
3121 struct snd_soc_card *card)
3122{
3123 const char *type = NULL;
3124 const char *hs_micbias_type = "qcom,msm-hs-micbias-type";
3125 int ret;
3126
3127 ret = is_ext_spk_gpio_support(pdev, pdata);
3128 if (ret < 0)
3129 dev_dbg(&pdev->dev,
3130 "%s: doesn't support external speaker pa\n",
3131 __func__);
3132
3133 ret = of_property_read_string(pdev->dev.of_node,
3134 hs_micbias_type, &type);
3135 if (ret) {
3136 dev_err(&pdev->dev, "%s: missing %s in dt node\n",
3137 __func__, hs_micbias_type);
3138 goto err;
3139 }
3140 if (!strcmp(type, "external")) {
3141 dev_dbg(&pdev->dev, "Headset is using external micbias\n");
3142 mbhc_cfg_ptr->hs_ext_micbias = true;
3143 } else {
3144 dev_dbg(&pdev->dev, "Headset is using internal micbias\n");
3145 mbhc_cfg_ptr->hs_ext_micbias = false;
3146 }
3147
3148 /* initialize the int_mclk0 */
3149 pdata->digital_cdc_core_clk.clk_set_minor_version =
3150 AFE_API_VERSION_I2S_CONFIG;
3151 pdata->digital_cdc_core_clk.clk_id =
3152 Q6AFE_LPASS_CLK_ID_INT_MCLK_0;
3153 pdata->digital_cdc_core_clk.clk_freq_in_hz = pdata->mclk_freq;
3154 pdata->digital_cdc_core_clk.clk_attri =
3155 Q6AFE_LPASS_CLK_ATTRIBUTE_COUPLE_NO;
3156 pdata->digital_cdc_core_clk.clk_root =
3157 Q6AFE_LPASS_CLK_ROOT_DEFAULT;
3158 pdata->digital_cdc_core_clk.enable = 1;
3159
3160 /* Initialize loopback mode to false */
3161 pdata->lb_mode = false;
3162
3163 msm_int_dt_parse_cap_info(pdev, pdata);
3164
3165 card->dev = &pdev->dev;
3166 platform_set_drvdata(pdev, card);
3167 snd_soc_card_set_drvdata(card, pdata);
3168 ret = snd_soc_of_parse_card_name(card, "qcom,model");
3169 if (ret)
3170 goto err;
3171 /* initialize timer */
3172 INIT_DELAYED_WORK(&pdata->disable_int_mclk0_work,
3173 msm_disable_int_mclk0);
3174 mutex_init(&pdata->cdc_int_mclk0_mutex);
3175 atomic_set(&pdata->int_mclk0_rsc_ref, 0);
3176 atomic_set(&pdata->int_mclk0_enabled, false);
3177
3178 dev_info(&pdev->dev, "%s: default codec configured\n", __func__);
3179
3180 return 0;
3181err:
3182 return ret;
3183}
3184
3185/**
3186 * msm_int_cdc_init - internal codec machine specific init.
3187 *
3188 * @pdev: platform device handle
3189 * @pdata: private data of machine driver
3190 * @card: sound card pointer reference
3191 * @mbhc_cfg: MBHC config reference
3192 *
3193 * Returns 0.
3194 */
3195int msm_int_cdc_init(struct platform_device *pdev,
3196 struct msm_asoc_mach_data *pdata,
3197 struct snd_soc_card **card,
3198 struct wcd_mbhc_config *mbhc_cfg)
3199{
3200 mbhc_cfg_ptr = mbhc_cfg;
3201
3202 *card = msm_int_populate_sndcard_dailinks(&pdev->dev);
3203 msm_internal_init(pdev, pdata, *card);
3204 return 0;
3205}
3206EXPORT_SYMBOL(msm_int_cdc_init);