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