OSDN Git Service

09591144ea7d2ed1bc6159a534a356e1242b767c
[uclinux-h8/linux.git] / sound / soc / intel / boards / bytcr_rt5640.c
1 /*
2  *  byt_cr_dpcm_rt5640.c - ASoc Machine driver for Intel Byt CR platform
3  *
4  *  Copyright (C) 2014 Intel Corp
5  *  Author: Subhransu S. Prusty <subhransu.s.prusty@intel.com>
6  *  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
7  *
8  *  This program is free software; you can redistribute it and/or modify
9  *  it under the terms of the GNU General Public License as published by
10  *  the Free Software Foundation; version 2 of the License.
11  *
12  *  This program is distributed in the hope that it will be useful, but
13  *  WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  *  General Public License for more details.
16  *
17  * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
18  */
19
20 #include <linux/i2c.h>
21 #include <linux/init.h>
22 #include <linux/module.h>
23 #include <linux/moduleparam.h>
24 #include <linux/platform_device.h>
25 #include <linux/acpi.h>
26 #include <linux/clk.h>
27 #include <linux/device.h>
28 #include <linux/dmi.h>
29 #include <linux/input.h>
30 #include <linux/slab.h>
31 #include <asm/cpu_device_id.h>
32 #include <sound/pcm.h>
33 #include <sound/pcm_params.h>
34 #include <sound/soc.h>
35 #include <sound/jack.h>
36 #include <sound/soc-acpi.h>
37 #include <dt-bindings/sound/rt5640.h>
38 #include "../../codecs/rt5640.h"
39 #include "../atom/sst-atom-controls.h"
40 #include "../common/sst-dsp.h"
41
42 enum {
43         BYT_RT5640_DMIC1_MAP,
44         BYT_RT5640_DMIC2_MAP,
45         BYT_RT5640_IN1_MAP,
46         BYT_RT5640_IN3_MAP,
47 };
48
49 enum {
50         BYT_RT5640_JD_SRC_GPIO1         = (RT5640_JD_SRC_GPIO1 << 4),
51         BYT_RT5640_JD_SRC_JD1_IN4P      = (RT5640_JD_SRC_JD1_IN4P << 4),
52         BYT_RT5640_JD_SRC_JD2_IN4N      = (RT5640_JD_SRC_JD2_IN4N << 4),
53         BYT_RT5640_JD_SRC_GPIO2         = (RT5640_JD_SRC_GPIO2 << 4),
54         BYT_RT5640_JD_SRC_GPIO3         = (RT5640_JD_SRC_GPIO3 << 4),
55         BYT_RT5640_JD_SRC_GPIO4         = (RT5640_JD_SRC_GPIO4 << 4),
56 };
57
58 enum {
59         BYT_RT5640_OVCD_TH_600UA        = (6 << 8),
60         BYT_RT5640_OVCD_TH_1500UA       = (15 << 8),
61         BYT_RT5640_OVCD_TH_2000UA       = (20 << 8),
62 };
63
64 enum {
65         BYT_RT5640_OVCD_SF_0P5          = (RT5640_OVCD_SF_0P5 << 13),
66         BYT_RT5640_OVCD_SF_0P75         = (RT5640_OVCD_SF_0P75 << 13),
67         BYT_RT5640_OVCD_SF_1P0          = (RT5640_OVCD_SF_1P0 << 13),
68         BYT_RT5640_OVCD_SF_1P5          = (RT5640_OVCD_SF_1P5 << 13),
69 };
70
71 #define BYT_RT5640_MAP(quirk)           ((quirk) &  GENMASK(3, 0))
72 #define BYT_RT5640_JDSRC(quirk)         (((quirk) & GENMASK(7, 4)) >> 4)
73 #define BYT_RT5640_OVCD_TH(quirk)       (((quirk) & GENMASK(12, 8)) >> 8)
74 #define BYT_RT5640_OVCD_SF(quirk)       (((quirk) & GENMASK(14, 13)) >> 13)
75 #define BYT_RT5640_JD_NOT_INV           BIT(16)
76 #define BYT_RT5640_MONO_SPEAKER         BIT(17)
77 #define BYT_RT5640_DIFF_MIC             BIT(18) /* default is single-ended */
78 #define BYT_RT5640_SSP2_AIF2            BIT(19) /* default is using AIF1  */
79 #define BYT_RT5640_SSP0_AIF1            BIT(20)
80 #define BYT_RT5640_SSP0_AIF2            BIT(21)
81 #define BYT_RT5640_MCLK_EN              BIT(22)
82 #define BYT_RT5640_MCLK_25MHZ           BIT(23)
83
84 #define BYTCR_INPUT_DEFAULTS                            \
85         (BYT_RT5640_IN3_MAP |                           \
86          BYT_RT5640_JD_SRC_JD1_IN4P |                   \
87          BYT_RT5640_OVCD_TH_2000UA |                    \
88          BYT_RT5640_OVCD_SF_0P75 |                      \
89          BYT_RT5640_DIFF_MIC)
90
91 /* in-diff or dmic-pin + jdsrc + ovcd-th + -sf + jd-inv + terminating entry */
92 #define MAX_NO_PROPS 6
93
94 struct byt_rt5640_private {
95         struct snd_soc_jack jack;
96         struct clk *mclk;
97 };
98 static bool is_bytcr;
99
100 static unsigned long byt_rt5640_quirk = BYT_RT5640_MCLK_EN;
101 static unsigned int quirk_override;
102 module_param_named(quirk, quirk_override, uint, 0444);
103 MODULE_PARM_DESC(quirk, "Board-specific quirk override");
104
105 static void log_quirks(struct device *dev)
106 {
107         int map;
108         bool has_mclk = false;
109         bool has_ssp0 = false;
110         bool has_ssp0_aif1 = false;
111         bool has_ssp0_aif2 = false;
112         bool has_ssp2_aif2 = false;
113
114         map = BYT_RT5640_MAP(byt_rt5640_quirk);
115         switch (map) {
116         case BYT_RT5640_DMIC1_MAP:
117                 dev_info(dev, "quirk DMIC1_MAP enabled\n");
118                 break;
119         case BYT_RT5640_DMIC2_MAP:
120                 dev_info(dev, "quirk DMIC2_MAP enabled\n");
121                 break;
122         case BYT_RT5640_IN1_MAP:
123                 dev_info(dev, "quirk IN1_MAP enabled\n");
124                 break;
125         case BYT_RT5640_IN3_MAP:
126                 dev_info(dev, "quirk IN3_MAP enabled\n");
127                 break;
128         default:
129                 dev_err(dev, "quirk map 0x%x is not supported, microphone input will not work\n", map);
130                 break;
131         }
132         if (BYT_RT5640_JDSRC(byt_rt5640_quirk)) {
133                 dev_info(dev, "quirk realtek,jack-detect-source %ld\n",
134                          BYT_RT5640_JDSRC(byt_rt5640_quirk));
135                 dev_info(dev, "quirk realtek,over-current-threshold-microamp %ld\n",
136                          BYT_RT5640_OVCD_TH(byt_rt5640_quirk) * 100);
137                 dev_info(dev, "quirk realtek,over-current-scale-factor %ld\n",
138                          BYT_RT5640_OVCD_SF(byt_rt5640_quirk));
139         }
140         if (byt_rt5640_quirk & BYT_RT5640_JD_NOT_INV)
141                 dev_info(dev, "quirk JD_NOT_INV enabled\n");
142         if (byt_rt5640_quirk & BYT_RT5640_MONO_SPEAKER)
143                 dev_info(dev, "quirk MONO_SPEAKER enabled\n");
144         if (byt_rt5640_quirk & BYT_RT5640_DIFF_MIC)
145                 dev_info(dev, "quirk DIFF_MIC enabled\n");
146         if (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF1) {
147                 dev_info(dev, "quirk SSP0_AIF1 enabled\n");
148                 has_ssp0 = true;
149                 has_ssp0_aif1 = true;
150         }
151         if (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2) {
152                 dev_info(dev, "quirk SSP0_AIF2 enabled\n");
153                 has_ssp0 = true;
154                 has_ssp0_aif2 = true;
155         }
156         if (byt_rt5640_quirk & BYT_RT5640_SSP2_AIF2) {
157                 dev_info(dev, "quirk SSP2_AIF2 enabled\n");
158                 has_ssp2_aif2 = true;
159         }
160         if (is_bytcr && !has_ssp0)
161                 dev_err(dev, "Invalid routing, bytcr detected but no SSP0-based quirk, audio cannot work with SSP2 on bytcr\n");
162         if (has_ssp0_aif1 && has_ssp0_aif2)
163                 dev_err(dev, "Invalid routing, SSP0 cannot be connected to both AIF1 and AIF2\n");
164         if (has_ssp0 && has_ssp2_aif2)
165                 dev_err(dev, "Invalid routing, cannot have both SSP0 and SSP2 connected to codec\n");
166
167         if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN) {
168                 dev_info(dev, "quirk MCLK_EN enabled\n");
169                 has_mclk = true;
170         }
171         if (byt_rt5640_quirk & BYT_RT5640_MCLK_25MHZ) {
172                 if (has_mclk)
173                         dev_info(dev, "quirk MCLK_25MHZ enabled\n");
174                 else
175                         dev_err(dev, "quirk MCLK_25MHZ enabled but quirk MCLK not selected, will be ignored\n");
176         }
177 }
178
179 static int byt_rt5640_prepare_and_enable_pll1(struct snd_soc_dai *codec_dai,
180                                               int rate)
181 {
182         int ret;
183
184         /* Configure the PLL before selecting it */
185         if (!(byt_rt5640_quirk & BYT_RT5640_MCLK_EN)) {
186                 /* use bitclock as PLL input */
187                 if ((byt_rt5640_quirk & BYT_RT5640_SSP0_AIF1) ||
188                     (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2)) {
189                         /* 2x16 bit slots on SSP0 */
190                         ret = snd_soc_dai_set_pll(codec_dai, 0,
191                                                   RT5640_PLL1_S_BCLK1,
192                                                   rate * 32, rate * 512);
193                 } else {
194                         /* 2x15 bit slots on SSP2 */
195                         ret = snd_soc_dai_set_pll(codec_dai, 0,
196                                                   RT5640_PLL1_S_BCLK1,
197                                                   rate * 50, rate * 512);
198                 }
199         } else {
200                 if (byt_rt5640_quirk & BYT_RT5640_MCLK_25MHZ) {
201                         ret = snd_soc_dai_set_pll(codec_dai, 0,
202                                                   RT5640_PLL1_S_MCLK,
203                                                   25000000, rate * 512);
204                 } else {
205                         ret = snd_soc_dai_set_pll(codec_dai, 0,
206                                                   RT5640_PLL1_S_MCLK,
207                                                   19200000, rate * 512);
208                 }
209         }
210
211         if (ret < 0) {
212                 dev_err(codec_dai->component->dev, "can't set pll: %d\n", ret);
213                 return ret;
214         }
215
216         ret = snd_soc_dai_set_sysclk(codec_dai, RT5640_SCLK_S_PLL1,
217                                      rate * 512, SND_SOC_CLOCK_IN);
218         if (ret < 0) {
219                 dev_err(codec_dai->component->dev, "can't set clock %d\n", ret);
220                 return ret;
221         }
222
223         return 0;
224 }
225
226 #define BYT_CODEC_DAI1  "rt5640-aif1"
227 #define BYT_CODEC_DAI2  "rt5640-aif2"
228
229 static int platform_clock_control(struct snd_soc_dapm_widget *w,
230                                   struct snd_kcontrol *k, int  event)
231 {
232         struct snd_soc_dapm_context *dapm = w->dapm;
233         struct snd_soc_card *card = dapm->card;
234         struct snd_soc_dai *codec_dai;
235         struct byt_rt5640_private *priv = snd_soc_card_get_drvdata(card);
236         int ret;
237
238         codec_dai = snd_soc_card_get_codec_dai(card, BYT_CODEC_DAI1);
239         if (!codec_dai)
240                 codec_dai = snd_soc_card_get_codec_dai(card, BYT_CODEC_DAI2);
241
242         if (!codec_dai) {
243                 dev_err(card->dev,
244                         "Codec dai not found; Unable to set platform clock\n");
245                 return -EIO;
246         }
247
248         if (SND_SOC_DAPM_EVENT_ON(event)) {
249                 if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN) {
250                         ret = clk_prepare_enable(priv->mclk);
251                         if (ret < 0) {
252                                 dev_err(card->dev,
253                                         "could not configure MCLK state\n");
254                                 return ret;
255                         }
256                 }
257                 ret = byt_rt5640_prepare_and_enable_pll1(codec_dai, 48000);
258         } else {
259                 /*
260                  * Set codec clock source to internal clock before
261                  * turning off the platform clock. Codec needs clock
262                  * for Jack detection and button press
263                  */
264                 ret = snd_soc_dai_set_sysclk(codec_dai, RT5640_SCLK_S_RCCLK,
265                                              48000 * 512,
266                                              SND_SOC_CLOCK_IN);
267                 if (!ret) {
268                         if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN)
269                                 clk_disable_unprepare(priv->mclk);
270                 }
271         }
272
273         if (ret < 0) {
274                 dev_err(card->dev, "can't set codec sysclk: %d\n", ret);
275                 return ret;
276         }
277
278         return 0;
279 }
280
281 static const struct snd_soc_dapm_widget byt_rt5640_widgets[] = {
282         SND_SOC_DAPM_HP("Headphone", NULL),
283         SND_SOC_DAPM_MIC("Headset Mic", NULL),
284         SND_SOC_DAPM_MIC("Internal Mic", NULL),
285         SND_SOC_DAPM_SPK("Speaker", NULL),
286         SND_SOC_DAPM_SUPPLY("Platform Clock", SND_SOC_NOPM, 0, 0,
287                             platform_clock_control, SND_SOC_DAPM_PRE_PMU |
288                             SND_SOC_DAPM_POST_PMD),
289
290 };
291
292 static const struct snd_soc_dapm_route byt_rt5640_audio_map[] = {
293         {"Headphone", NULL, "Platform Clock"},
294         {"Headset Mic", NULL, "Platform Clock"},
295         {"Internal Mic", NULL, "Platform Clock"},
296         {"Speaker", NULL, "Platform Clock"},
297
298         {"Headset Mic", NULL, "MICBIAS1"},
299         {"IN2P", NULL, "Headset Mic"},
300         {"Headphone", NULL, "HPOL"},
301         {"Headphone", NULL, "HPOR"},
302 };
303
304 static const struct snd_soc_dapm_route byt_rt5640_intmic_dmic1_map[] = {
305         {"DMIC1", NULL, "Internal Mic"},
306 };
307
308 static const struct snd_soc_dapm_route byt_rt5640_intmic_dmic2_map[] = {
309         {"DMIC2", NULL, "Internal Mic"},
310 };
311
312 static const struct snd_soc_dapm_route byt_rt5640_intmic_in1_map[] = {
313         {"Internal Mic", NULL, "MICBIAS1"},
314         {"IN1P", NULL, "Internal Mic"},
315 };
316
317 static const struct snd_soc_dapm_route byt_rt5640_intmic_in3_map[] = {
318         {"Internal Mic", NULL, "MICBIAS1"},
319         {"IN3P", NULL, "Internal Mic"},
320 };
321
322 static const struct snd_soc_dapm_route byt_rt5640_ssp2_aif1_map[] = {
323         {"ssp2 Tx", NULL, "codec_out0"},
324         {"ssp2 Tx", NULL, "codec_out1"},
325         {"codec_in0", NULL, "ssp2 Rx"},
326         {"codec_in1", NULL, "ssp2 Rx"},
327
328         {"AIF1 Playback", NULL, "ssp2 Tx"},
329         {"ssp2 Rx", NULL, "AIF1 Capture"},
330 };
331
332 static const struct snd_soc_dapm_route byt_rt5640_ssp2_aif2_map[] = {
333         {"ssp2 Tx", NULL, "codec_out0"},
334         {"ssp2 Tx", NULL, "codec_out1"},
335         {"codec_in0", NULL, "ssp2 Rx"},
336         {"codec_in1", NULL, "ssp2 Rx"},
337
338         {"AIF2 Playback", NULL, "ssp2 Tx"},
339         {"ssp2 Rx", NULL, "AIF2 Capture"},
340 };
341
342 static const struct snd_soc_dapm_route byt_rt5640_ssp0_aif1_map[] = {
343         {"ssp0 Tx", NULL, "modem_out"},
344         {"modem_in", NULL, "ssp0 Rx"},
345
346         {"AIF1 Playback", NULL, "ssp0 Tx"},
347         {"ssp0 Rx", NULL, "AIF1 Capture"},
348 };
349
350 static const struct snd_soc_dapm_route byt_rt5640_ssp0_aif2_map[] = {
351         {"ssp0 Tx", NULL, "modem_out"},
352         {"modem_in", NULL, "ssp0 Rx"},
353
354         {"AIF2 Playback", NULL, "ssp0 Tx"},
355         {"ssp0 Rx", NULL, "AIF2 Capture"},
356 };
357
358 static const struct snd_soc_dapm_route byt_rt5640_stereo_spk_map[] = {
359         {"Speaker", NULL, "SPOLP"},
360         {"Speaker", NULL, "SPOLN"},
361         {"Speaker", NULL, "SPORP"},
362         {"Speaker", NULL, "SPORN"},
363 };
364
365 static const struct snd_soc_dapm_route byt_rt5640_mono_spk_map[] = {
366         {"Speaker", NULL, "SPOLP"},
367         {"Speaker", NULL, "SPOLN"},
368 };
369
370 static const struct snd_kcontrol_new byt_rt5640_controls[] = {
371         SOC_DAPM_PIN_SWITCH("Headphone"),
372         SOC_DAPM_PIN_SWITCH("Headset Mic"),
373         SOC_DAPM_PIN_SWITCH("Internal Mic"),
374         SOC_DAPM_PIN_SWITCH("Speaker"),
375 };
376
377 static struct snd_soc_jack_pin rt5640_pins[] = {
378         {
379                 .pin    = "Headphone",
380                 .mask   = SND_JACK_HEADPHONE,
381         },
382         {
383                 .pin    = "Headset Mic",
384                 .mask   = SND_JACK_MICROPHONE,
385         },
386 };
387
388 static int byt_rt5640_aif1_hw_params(struct snd_pcm_substream *substream,
389                                         struct snd_pcm_hw_params *params)
390 {
391         struct snd_soc_pcm_runtime *rtd = substream->private_data;
392         struct snd_soc_dai *dai = rtd->codec_dai;
393
394         return byt_rt5640_prepare_and_enable_pll1(dai, params_rate(params));
395 }
396
397 /* Please keep this list alphabetically sorted */
398 static const struct dmi_system_id byt_rt5640_quirk_table[] = {
399         {       /* Acer Iconia Tab 8 W1-810 */
400                 .matches = {
401                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Acer"),
402                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Iconia W1-810"),
403                 },
404                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP |
405                                         BYT_RT5640_JD_SRC_JD1_IN4P |
406                                         BYT_RT5640_OVCD_TH_1500UA |
407                                         BYT_RT5640_OVCD_SF_0P75 |
408                                         BYT_RT5640_SSP0_AIF1 |
409                                         BYT_RT5640_MCLK_EN),
410         },
411         {
412                 .matches = {
413                         DMI_MATCH(DMI_SYS_VENDOR, "Acer"),
414                         DMI_MATCH(DMI_PRODUCT_NAME, "Aspire SW5-012"),
415                 },
416                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
417                                                  BYT_RT5640_MCLK_EN |
418                                                  BYT_RT5640_SSP0_AIF1),
419
420         },
421         {
422                 .matches = {
423                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "ARCHOS"),
424                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "ARCHOS 80 Cesium"),
425                 },
426                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
427                                         BYT_RT5640_MONO_SPEAKER |
428                                         BYT_RT5640_SSP0_AIF1 |
429                                         BYT_RT5640_MCLK_EN),
430         },
431         {
432                 .matches = {
433                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."),
434                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "T100TA"),
435                 },
436                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
437                                         BYT_RT5640_JD_SRC_JD2_IN4N |
438                                         BYT_RT5640_OVCD_TH_2000UA |
439                                         BYT_RT5640_OVCD_SF_0P75 |
440                                         BYT_RT5640_MCLK_EN),
441         },
442         {
443                 .matches = {
444                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."),
445                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "T100TAF"),
446                 },
447                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
448                                         BYT_RT5640_MONO_SPEAKER |
449                                         BYT_RT5640_DIFF_MIC |
450                                         BYT_RT5640_SSP0_AIF2 |
451                                         BYT_RT5640_MCLK_EN),
452         },
453         {       /* Chuwi Vi8 (CWI506) */
454                 .matches = {
455                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Insyde"),
456                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "i86"),
457                         /* The above are too generic, also match BIOS info */
458                         DMI_MATCH(DMI_BIOS_VERSION, "CHUWI.D86JLBNR"),
459                 },
460                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
461                                         BYT_RT5640_MONO_SPEAKER |
462                                         BYT_RT5640_SSP0_AIF1 |
463                                         BYT_RT5640_MCLK_EN),
464         },
465         {
466                 /* Chuwi Vi10 (CWI505) */
467                 .matches = {
468                         DMI_MATCH(DMI_BOARD_VENDOR, "Hampoo"),
469                         DMI_MATCH(DMI_BOARD_NAME, "BYT-PF02"),
470                         DMI_MATCH(DMI_SYS_VENDOR, "ilife"),
471                         DMI_MATCH(DMI_PRODUCT_NAME, "S165"),
472                 },
473                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
474                                         BYT_RT5640_JD_SRC_JD2_IN4N |
475                                         BYT_RT5640_OVCD_TH_2000UA |
476                                         BYT_RT5640_OVCD_SF_0P75 |
477                                         BYT_RT5640_DIFF_MIC |
478                                         BYT_RT5640_SSP0_AIF1 |
479                                         BYT_RT5640_MCLK_EN),
480         },
481         {
482                 .matches = {
483                         DMI_MATCH(DMI_SYS_VENDOR, "Circuitco"),
484                         DMI_MATCH(DMI_PRODUCT_NAME, "Minnowboard Max B3 PLATFORM"),
485                 },
486                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP),
487         },
488         {       /* Connect Tablet 9 */
489                 .matches = {
490                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Connect"),
491                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Tablet 9"),
492                 },
493                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
494                                         BYT_RT5640_MONO_SPEAKER |
495                                         BYT_RT5640_SSP0_AIF1 |
496                                         BYT_RT5640_MCLK_EN),
497         },
498         {
499                 .matches = {
500                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Dell Inc."),
501                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "Venue 8 Pro 5830"),
502                 },
503                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP |
504                                         BYT_RT5640_JD_SRC_JD2_IN4N |
505                                         BYT_RT5640_OVCD_TH_2000UA |
506                                         BYT_RT5640_OVCD_SF_0P75 |
507                                         BYT_RT5640_MONO_SPEAKER |
508                                         BYT_RT5640_MCLK_EN),
509         },
510         {
511                 .matches = {
512                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"),
513                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "HP ElitePad 1000 G2"),
514                 },
515                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
516                                         BYT_RT5640_MCLK_EN),
517         },
518         {       /* HP Pavilion x2 10-n000nd */
519                 .matches = {
520                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"),
521                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "HP Pavilion x2 Detachable"),
522                 },
523                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP |
524                                         BYT_RT5640_JD_SRC_JD2_IN4N |
525                                         BYT_RT5640_OVCD_TH_1500UA |
526                                         BYT_RT5640_OVCD_SF_0P75 |
527                                         BYT_RT5640_SSP0_AIF1 |
528                                         BYT_RT5640_MCLK_EN),
529         },
530         {       /* HP Stream 7 */
531                 .matches = {
532                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"),
533                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "HP Stream 7 Tablet"),
534                 },
535                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
536                                         BYT_RT5640_MONO_SPEAKER |
537                                         BYT_RT5640_JD_NOT_INV |
538                                         BYT_RT5640_SSP0_AIF1 |
539                                         BYT_RT5640_MCLK_EN),
540         },
541         {       /* I.T.Works TW891 */
542                 .matches = {
543                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "To be filled by O.E.M."),
544                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "TW891"),
545                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "To be filled by O.E.M."),
546                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "TW891"),
547                 },
548                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
549                                         BYT_RT5640_MONO_SPEAKER |
550                                         BYT_RT5640_SSP0_AIF1 |
551                                         BYT_RT5640_MCLK_EN),
552         },
553         {       /* Lamina I8270 / T701BR.SE */
554                 .matches = {
555                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "Lamina"),
556                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "T701BR.SE"),
557                 },
558                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
559                                         BYT_RT5640_MONO_SPEAKER |
560                                         BYT_RT5640_JD_NOT_INV |
561                                         BYT_RT5640_SSP0_AIF1 |
562                                         BYT_RT5640_MCLK_EN),
563         },
564         {       /* Lenovo Miix 2 8 */
565                 .matches = {
566                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "LENOVO"),
567                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "20326"),
568                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "Hiking"),
569                 },
570                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP |
571                                         BYT_RT5640_JD_SRC_JD2_IN4N |
572                                         BYT_RT5640_OVCD_TH_2000UA |
573                                         BYT_RT5640_OVCD_SF_0P75 |
574                                         BYT_RT5640_MONO_SPEAKER |
575                                         BYT_RT5640_MCLK_EN),
576         },
577         {       /* Linx Linx7 tablet */
578                 .matches = {
579                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "LINX"),
580                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "LINX7"),
581                 },
582                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
583                                         BYT_RT5640_MONO_SPEAKER |
584                                         BYT_RT5640_JD_NOT_INV |
585                                         BYT_RT5640_SSP0_AIF1 |
586                                         BYT_RT5640_MCLK_EN),
587         },
588         {       /* MSI S100 tablet */
589                 .matches = {
590                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "Micro-Star International Co., Ltd."),
591                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "S100"),
592                 },
593                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
594                                         BYT_RT5640_JD_SRC_JD2_IN4N |
595                                         BYT_RT5640_OVCD_TH_2000UA |
596                                         BYT_RT5640_OVCD_SF_0P75 |
597                                         BYT_RT5640_MONO_SPEAKER |
598                                         BYT_RT5640_DIFF_MIC |
599                                         BYT_RT5640_MCLK_EN),
600         },
601         {       /* Nuvison/TMax TM800W560 */
602                 .matches = {
603                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "TMAX"),
604                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "TM800W560L"),
605                 },
606                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
607                                         BYT_RT5640_JD_SRC_JD2_IN4N |
608                                         BYT_RT5640_OVCD_TH_2000UA |
609                                         BYT_RT5640_OVCD_SF_0P75 |
610                                         BYT_RT5640_JD_NOT_INV |
611                                         BYT_RT5640_DIFF_MIC |
612                                         BYT_RT5640_SSP0_AIF1 |
613                                         BYT_RT5640_MCLK_EN),
614         },
615         {       /* Onda v975w */
616                 .matches = {
617                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "AMI Corporation"),
618                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "Aptio CRB"),
619                         /* The above are too generic, also match BIOS info */
620                         DMI_EXACT_MATCH(DMI_BIOS_VERSION, "5.6.5"),
621                         DMI_EXACT_MATCH(DMI_BIOS_DATE, "07/25/2014"),
622                 },
623                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
624                                         BYT_RT5640_JD_SRC_JD2_IN4N |
625                                         BYT_RT5640_OVCD_TH_2000UA |
626                                         BYT_RT5640_OVCD_SF_0P75 |
627                                         BYT_RT5640_DIFF_MIC |
628                                         BYT_RT5640_MCLK_EN),
629         },
630         {       /* Pipo W4 */
631                 .matches = {
632                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "AMI Corporation"),
633                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "Aptio CRB"),
634                         /* The above are too generic, also match BIOS info */
635                         DMI_MATCH(DMI_BIOS_VERSION, "V8L_WIN32_CHIPHD"),
636                 },
637                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
638                                         BYT_RT5640_MONO_SPEAKER |
639                                         BYT_RT5640_SSP0_AIF1 |
640                                         BYT_RT5640_MCLK_EN),
641         },
642         {       /* Point of View Mobii TAB-P800W (V2.0) */
643                 .matches = {
644                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "AMI Corporation"),
645                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "Aptio CRB"),
646                         /* The above are too generic, also match BIOS info */
647                         DMI_EXACT_MATCH(DMI_BIOS_VERSION, "3BAIR1014"),
648                         DMI_EXACT_MATCH(DMI_BIOS_DATE, "10/24/2014"),
649                 },
650                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
651                                         BYT_RT5640_JD_SRC_JD2_IN4N |
652                                         BYT_RT5640_OVCD_TH_2000UA |
653                                         BYT_RT5640_OVCD_SF_0P75 |
654                                         BYT_RT5640_MONO_SPEAKER |
655                                         BYT_RT5640_DIFF_MIC |
656                                         BYT_RT5640_SSP0_AIF2 |
657                                         BYT_RT5640_MCLK_EN),
658         },
659         {       /* Point of View Mobii TAB-P800W (V2.1) */
660                 .matches = {
661                         DMI_EXACT_MATCH(DMI_BOARD_VENDOR, "AMI Corporation"),
662                         DMI_EXACT_MATCH(DMI_BOARD_NAME, "Aptio CRB"),
663                         /* The above are too generic, also match BIOS info */
664                         DMI_EXACT_MATCH(DMI_BIOS_VERSION, "3BAIR1013"),
665                         DMI_EXACT_MATCH(DMI_BIOS_DATE, "08/22/2014"),
666                 },
667                 .driver_data = (void *)(BYT_RT5640_IN1_MAP |
668                                         BYT_RT5640_JD_SRC_JD2_IN4N |
669                                         BYT_RT5640_OVCD_TH_2000UA |
670                                         BYT_RT5640_OVCD_SF_0P75 |
671                                         BYT_RT5640_MONO_SPEAKER |
672                                         BYT_RT5640_DIFF_MIC |
673                                         BYT_RT5640_SSP0_AIF2 |
674                                         BYT_RT5640_MCLK_EN),
675         },
676         {
677                 .matches = {
678                         DMI_MATCH(DMI_BOARD_VENDOR, "TECLAST"),
679                         DMI_MATCH(DMI_BOARD_NAME, "tPAD"),
680                 },
681                 .driver_data = (void *)(BYT_RT5640_IN3_MAP |
682                                         BYT_RT5640_MCLK_EN |
683                                         BYT_RT5640_SSP0_AIF1),
684         },
685         {       /* Toshiba Satellite Click Mini L9W-B */
686                 .matches = {
687                         DMI_EXACT_MATCH(DMI_SYS_VENDOR, "TOSHIBA"),
688                         DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "SATELLITE Click Mini L9W-B"),
689                 },
690                 .driver_data = (void *)(BYT_RT5640_DMIC1_MAP |
691                                         BYT_RT5640_JD_SRC_JD2_IN4N |
692                                         BYT_RT5640_OVCD_TH_1500UA |
693                                         BYT_RT5640_OVCD_SF_0P75 |
694                                         BYT_RT5640_SSP0_AIF1 |
695                                         BYT_RT5640_MCLK_EN),
696         },
697         {       /* Catch-all for generic Insyde tablets, must be last */
698                 .matches = {
699                         DMI_MATCH(DMI_SYS_VENDOR, "Insyde"),
700                 },
701                 .driver_data = (void *)(BYTCR_INPUT_DEFAULTS |
702                                         BYT_RT5640_MCLK_EN |
703                                         BYT_RT5640_SSP0_AIF1),
704
705         },
706         {}
707 };
708
709 /*
710  * Note this MUST be called before snd_soc_register_card(), so that the props
711  * are in place before the codec component driver's probe function parses them.
712  */
713 static int byt_rt5640_add_codec_device_props(const char *i2c_dev_name)
714 {
715         struct property_entry props[MAX_NO_PROPS] = {};
716         struct device *i2c_dev;
717         int ret, cnt = 0;
718
719         i2c_dev = bus_find_device_by_name(&i2c_bus_type, NULL, i2c_dev_name);
720         if (!i2c_dev)
721                 return -EPROBE_DEFER;
722
723         switch (BYT_RT5640_MAP(byt_rt5640_quirk)) {
724         case BYT_RT5640_DMIC1_MAP:
725                 props[cnt++] = PROPERTY_ENTRY_U32("realtek,dmic1-data-pin",
726                                                   RT5640_DMIC1_DATA_PIN_IN1P);
727                 break;
728         case BYT_RT5640_DMIC2_MAP:
729                 props[cnt++] = PROPERTY_ENTRY_U32("realtek,dmic2-data-pin",
730                                                   RT5640_DMIC2_DATA_PIN_IN1N);
731                 break;
732         case BYT_RT5640_IN1_MAP:
733                 if (byt_rt5640_quirk & BYT_RT5640_DIFF_MIC)
734                         props[cnt++] =
735                                 PROPERTY_ENTRY_BOOL("realtek,in1-differential");
736                 break;
737         case BYT_RT5640_IN3_MAP:
738                 if (byt_rt5640_quirk & BYT_RT5640_DIFF_MIC)
739                         props[cnt++] =
740                                 PROPERTY_ENTRY_BOOL("realtek,in3-differential");
741                 break;
742         }
743
744         if (BYT_RT5640_JDSRC(byt_rt5640_quirk)) {
745                 props[cnt++] = PROPERTY_ENTRY_U32(
746                                     "realtek,jack-detect-source",
747                                     BYT_RT5640_JDSRC(byt_rt5640_quirk));
748
749                 props[cnt++] = PROPERTY_ENTRY_U32(
750                                     "realtek,over-current-threshold-microamp",
751                                     BYT_RT5640_OVCD_TH(byt_rt5640_quirk) * 100);
752
753                 props[cnt++] = PROPERTY_ENTRY_U32(
754                                     "realtek,over-current-scale-factor",
755                                     BYT_RT5640_OVCD_SF(byt_rt5640_quirk));
756         }
757
758         if (byt_rt5640_quirk & BYT_RT5640_JD_NOT_INV)
759                 props[cnt++] = PROPERTY_ENTRY_BOOL("realtek,jack-detect-not-inverted");
760
761         ret = device_add_properties(i2c_dev, props);
762         put_device(i2c_dev);
763
764         return ret;
765 }
766
767 static int byt_rt5640_init(struct snd_soc_pcm_runtime *runtime)
768 {
769         struct snd_soc_card *card = runtime->card;
770         struct byt_rt5640_private *priv = snd_soc_card_get_drvdata(card);
771         struct snd_soc_component *component = runtime->codec_dai->component;
772         const struct snd_soc_dapm_route *custom_map;
773         int num_routes;
774         int ret;
775
776         card->dapm.idle_bias_off = true;
777
778         /* Start with RC clk for jack-detect (we disable MCLK below) */
779         if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN)
780                 snd_soc_component_update_bits(component, RT5640_GLB_CLK,
781                         RT5640_SCLK_SRC_MASK, RT5640_SCLK_SRC_RCCLK);
782
783         rt5640_sel_asrc_clk_src(component,
784                                 RT5640_DA_STEREO_FILTER |
785                                 RT5640_DA_MONO_L_FILTER |
786                                 RT5640_DA_MONO_R_FILTER |
787                                 RT5640_AD_STEREO_FILTER |
788                                 RT5640_AD_MONO_L_FILTER |
789                                 RT5640_AD_MONO_R_FILTER,
790                                 RT5640_CLK_SEL_ASRC);
791
792         ret = snd_soc_add_card_controls(card, byt_rt5640_controls,
793                                         ARRAY_SIZE(byt_rt5640_controls));
794         if (ret) {
795                 dev_err(card->dev, "unable to add card controls\n");
796                 return ret;
797         }
798
799         switch (BYT_RT5640_MAP(byt_rt5640_quirk)) {
800         case BYT_RT5640_IN1_MAP:
801                 custom_map = byt_rt5640_intmic_in1_map;
802                 num_routes = ARRAY_SIZE(byt_rt5640_intmic_in1_map);
803                 break;
804         case BYT_RT5640_IN3_MAP:
805                 custom_map = byt_rt5640_intmic_in3_map;
806                 num_routes = ARRAY_SIZE(byt_rt5640_intmic_in3_map);
807                 break;
808         case BYT_RT5640_DMIC2_MAP:
809                 custom_map = byt_rt5640_intmic_dmic2_map;
810                 num_routes = ARRAY_SIZE(byt_rt5640_intmic_dmic2_map);
811                 break;
812         default:
813                 custom_map = byt_rt5640_intmic_dmic1_map;
814                 num_routes = ARRAY_SIZE(byt_rt5640_intmic_dmic1_map);
815         }
816
817         ret = snd_soc_dapm_add_routes(&card->dapm, custom_map, num_routes);
818         if (ret)
819                 return ret;
820
821         if (byt_rt5640_quirk & BYT_RT5640_SSP2_AIF2) {
822                 ret = snd_soc_dapm_add_routes(&card->dapm,
823                                         byt_rt5640_ssp2_aif2_map,
824                                         ARRAY_SIZE(byt_rt5640_ssp2_aif2_map));
825         } else if (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF1) {
826                 ret = snd_soc_dapm_add_routes(&card->dapm,
827                                         byt_rt5640_ssp0_aif1_map,
828                                         ARRAY_SIZE(byt_rt5640_ssp0_aif1_map));
829         } else if (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2) {
830                 ret = snd_soc_dapm_add_routes(&card->dapm,
831                                         byt_rt5640_ssp0_aif2_map,
832                                         ARRAY_SIZE(byt_rt5640_ssp0_aif2_map));
833         } else {
834                 ret = snd_soc_dapm_add_routes(&card->dapm,
835                                         byt_rt5640_ssp2_aif1_map,
836                                         ARRAY_SIZE(byt_rt5640_ssp2_aif1_map));
837         }
838         if (ret)
839                 return ret;
840
841         if (byt_rt5640_quirk & BYT_RT5640_MONO_SPEAKER) {
842                 ret = snd_soc_dapm_add_routes(&card->dapm,
843                                         byt_rt5640_mono_spk_map,
844                                         ARRAY_SIZE(byt_rt5640_mono_spk_map));
845         } else {
846                 ret = snd_soc_dapm_add_routes(&card->dapm,
847                                         byt_rt5640_stereo_spk_map,
848                                         ARRAY_SIZE(byt_rt5640_stereo_spk_map));
849         }
850         if (ret)
851                 return ret;
852
853         snd_soc_dapm_ignore_suspend(&card->dapm, "Headphone");
854         snd_soc_dapm_ignore_suspend(&card->dapm, "Speaker");
855
856         if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN) {
857                 /*
858                  * The firmware might enable the clock at
859                  * boot (this information may or may not
860                  * be reflected in the enable clock register).
861                  * To change the rate we must disable the clock
862                  * first to cover these cases. Due to common
863                  * clock framework restrictions that do not allow
864                  * to disable a clock that has not been enabled,
865                  * we need to enable the clock first.
866                  */
867                 ret = clk_prepare_enable(priv->mclk);
868                 if (!ret)
869                         clk_disable_unprepare(priv->mclk);
870
871                 if (byt_rt5640_quirk & BYT_RT5640_MCLK_25MHZ)
872                         ret = clk_set_rate(priv->mclk, 25000000);
873                 else
874                         ret = clk_set_rate(priv->mclk, 19200000);
875
876                 if (ret) {
877                         dev_err(card->dev, "unable to set MCLK rate\n");
878                         return ret;
879                 }
880         }
881
882         if (BYT_RT5640_JDSRC(byt_rt5640_quirk)) {
883                 ret = snd_soc_card_jack_new(card, "Headset",
884                                             SND_JACK_HEADSET | SND_JACK_BTN_0,
885                                             &priv->jack, rt5640_pins,
886                                             ARRAY_SIZE(rt5640_pins));
887                 if (ret) {
888                         dev_err(card->dev, "Jack creation failed %d\n", ret);
889                         return ret;
890                 }
891                 snd_jack_set_key(priv->jack.jack, SND_JACK_BTN_0,
892                                  KEY_PLAYPAUSE);
893                 snd_soc_component_set_jack(component, &priv->jack, NULL);
894         }
895
896         return 0;
897 }
898
899 static const struct snd_soc_pcm_stream byt_rt5640_dai_params = {
900         .formats = SNDRV_PCM_FMTBIT_S24_LE,
901         .rate_min = 48000,
902         .rate_max = 48000,
903         .channels_min = 2,
904         .channels_max = 2,
905 };
906
907 static int byt_rt5640_codec_fixup(struct snd_soc_pcm_runtime *rtd,
908                             struct snd_pcm_hw_params *params)
909 {
910         struct snd_interval *rate = hw_param_interval(params,
911                         SNDRV_PCM_HW_PARAM_RATE);
912         struct snd_interval *channels = hw_param_interval(params,
913                                                 SNDRV_PCM_HW_PARAM_CHANNELS);
914         int ret;
915
916         /* The DSP will covert the FE rate to 48k, stereo */
917         rate->min = rate->max = 48000;
918         channels->min = channels->max = 2;
919
920         if ((byt_rt5640_quirk & BYT_RT5640_SSP0_AIF1) ||
921                 (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2)) {
922
923                 /* set SSP0 to 16-bit */
924                 params_set_format(params, SNDRV_PCM_FORMAT_S16_LE);
925
926                 /*
927                  * Default mode for SSP configuration is TDM 4 slot, override config
928                  * with explicit setting to I2S 2ch 16-bit. The word length is set with
929                  * dai_set_tdm_slot() since there is no other API exposed
930                  */
931                 ret = snd_soc_dai_set_fmt(rtd->cpu_dai,
932                                         SND_SOC_DAIFMT_I2S     |
933                                         SND_SOC_DAIFMT_NB_NF   |
934                                         SND_SOC_DAIFMT_CBS_CFS
935                         );
936                 if (ret < 0) {
937                         dev_err(rtd->dev, "can't set format to I2S, err %d\n", ret);
938                         return ret;
939                 }
940
941                 ret = snd_soc_dai_set_tdm_slot(rtd->cpu_dai, 0x3, 0x3, 2, 16);
942                 if (ret < 0) {
943                         dev_err(rtd->dev, "can't set I2S config, err %d\n", ret);
944                         return ret;
945                 }
946
947         } else {
948
949                 /* set SSP2 to 24-bit */
950                 params_set_format(params, SNDRV_PCM_FORMAT_S24_LE);
951
952                 /*
953                  * Default mode for SSP configuration is TDM 4 slot, override config
954                  * with explicit setting to I2S 2ch 24-bit. The word length is set with
955                  * dai_set_tdm_slot() since there is no other API exposed
956                  */
957                 ret = snd_soc_dai_set_fmt(rtd->cpu_dai,
958                                         SND_SOC_DAIFMT_I2S     |
959                                         SND_SOC_DAIFMT_NB_NF   |
960                                         SND_SOC_DAIFMT_CBS_CFS
961                         );
962                 if (ret < 0) {
963                         dev_err(rtd->dev, "can't set format to I2S, err %d\n", ret);
964                         return ret;
965                 }
966
967                 ret = snd_soc_dai_set_tdm_slot(rtd->cpu_dai, 0x3, 0x3, 2, 24);
968                 if (ret < 0) {
969                         dev_err(rtd->dev, "can't set I2S config, err %d\n", ret);
970                         return ret;
971                 }
972         }
973         return 0;
974 }
975
976 static int byt_rt5640_aif1_startup(struct snd_pcm_substream *substream)
977 {
978         return snd_pcm_hw_constraint_single(substream->runtime,
979                         SNDRV_PCM_HW_PARAM_RATE, 48000);
980 }
981
982 static const struct snd_soc_ops byt_rt5640_aif1_ops = {
983         .startup = byt_rt5640_aif1_startup,
984 };
985
986 static const struct snd_soc_ops byt_rt5640_be_ssp2_ops = {
987         .hw_params = byt_rt5640_aif1_hw_params,
988 };
989
990 static struct snd_soc_dai_link byt_rt5640_dais[] = {
991         [MERR_DPCM_AUDIO] = {
992                 .name = "Baytrail Audio Port",
993                 .stream_name = "Baytrail Audio",
994                 .cpu_dai_name = "media-cpu-dai",
995                 .codec_dai_name = "snd-soc-dummy-dai",
996                 .codec_name = "snd-soc-dummy",
997                 .platform_name = "sst-mfld-platform",
998                 .nonatomic = true,
999                 .dynamic = 1,
1000                 .dpcm_playback = 1,
1001                 .dpcm_capture = 1,
1002                 .ops = &byt_rt5640_aif1_ops,
1003         },
1004         [MERR_DPCM_DEEP_BUFFER] = {
1005                 .name = "Deep-Buffer Audio Port",
1006                 .stream_name = "Deep-Buffer Audio",
1007                 .cpu_dai_name = "deepbuffer-cpu-dai",
1008                 .codec_dai_name = "snd-soc-dummy-dai",
1009                 .codec_name = "snd-soc-dummy",
1010                 .platform_name = "sst-mfld-platform",
1011                 .nonatomic = true,
1012                 .dynamic = 1,
1013                 .dpcm_playback = 1,
1014                 .ops = &byt_rt5640_aif1_ops,
1015         },
1016                 /* back ends */
1017         {
1018                 .name = "SSP2-Codec",
1019                 .id = 0,
1020                 .cpu_dai_name = "ssp2-port", /* overwritten for ssp0 routing */
1021                 .platform_name = "sst-mfld-platform",
1022                 .no_pcm = 1,
1023                 .codec_dai_name = "rt5640-aif1", /* changed w/ quirk */
1024                 .codec_name = "i2c-10EC5640:00", /* overwritten with HID */
1025                 .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF
1026                                                 | SND_SOC_DAIFMT_CBS_CFS,
1027                 .be_hw_params_fixup = byt_rt5640_codec_fixup,
1028                 .ignore_suspend = 1,
1029                 .nonatomic = true,
1030                 .dpcm_playback = 1,
1031                 .dpcm_capture = 1,
1032                 .init = byt_rt5640_init,
1033                 .ops = &byt_rt5640_be_ssp2_ops,
1034         },
1035 };
1036
1037 /* SoC card */
1038 static char byt_rt5640_codec_name[SND_ACPI_I2C_ID_LEN];
1039 static char byt_rt5640_codec_aif_name[12]; /*  = "rt5640-aif[1|2]" */
1040 static char byt_rt5640_cpu_dai_name[10]; /*  = "ssp[0|2]-port" */
1041 static char byt_rt5640_long_name[40]; /* = "bytcr-rt5640-*-spk-*-mic" */
1042
1043 static int byt_rt5640_suspend(struct snd_soc_card *card)
1044 {
1045         struct snd_soc_component *component;
1046
1047         if (!BYT_RT5640_JDSRC(byt_rt5640_quirk))
1048                 return 0;
1049
1050         for_each_card_components(card, component) {
1051                 if (!strcmp(component->name, byt_rt5640_codec_name)) {
1052                         dev_dbg(component->dev, "disabling jack detect before suspend\n");
1053                         snd_soc_component_set_jack(component, NULL, NULL);
1054                         break;
1055                 }
1056         }
1057
1058         return 0;
1059 }
1060
1061 static int byt_rt5640_resume(struct snd_soc_card *card)
1062 {
1063         struct byt_rt5640_private *priv = snd_soc_card_get_drvdata(card);
1064         struct snd_soc_component *component;
1065
1066         if (!BYT_RT5640_JDSRC(byt_rt5640_quirk))
1067                 return 0;
1068
1069         for_each_card_components(card, component) {
1070                 if (!strcmp(component->name, byt_rt5640_codec_name)) {
1071                         dev_dbg(component->dev, "re-enabling jack detect after resume\n");
1072                         snd_soc_component_set_jack(component, &priv->jack, NULL);
1073                         break;
1074                 }
1075         }
1076
1077         return 0;
1078 }
1079
1080 static struct snd_soc_card byt_rt5640_card = {
1081         .name = "bytcr-rt5640",
1082         .owner = THIS_MODULE,
1083         .dai_link = byt_rt5640_dais,
1084         .num_links = ARRAY_SIZE(byt_rt5640_dais),
1085         .dapm_widgets = byt_rt5640_widgets,
1086         .num_dapm_widgets = ARRAY_SIZE(byt_rt5640_widgets),
1087         .dapm_routes = byt_rt5640_audio_map,
1088         .num_dapm_routes = ARRAY_SIZE(byt_rt5640_audio_map),
1089         .fully_routed = true,
1090         .suspend_pre = byt_rt5640_suspend,
1091         .resume_post = byt_rt5640_resume,
1092 };
1093
1094 static bool is_valleyview(void)
1095 {
1096         static const struct x86_cpu_id cpu_ids[] = {
1097                 { X86_VENDOR_INTEL, 6, 55 }, /* Valleyview, Bay Trail */
1098                 {}
1099         };
1100
1101         if (!x86_match_cpu(cpu_ids))
1102                 return false;
1103         return true;
1104 }
1105
1106 struct acpi_chan_package {   /* ACPICA seems to require 64 bit integers */
1107         u64 aif_value;       /* 1: AIF1, 2: AIF2 */
1108         u64 mclock_value;    /* usually 25MHz (0x17d7940), ignored */
1109 };
1110
1111 static int snd_byt_rt5640_mc_probe(struct platform_device *pdev)
1112 {
1113         const char * const map_name[] = { "dmic1", "dmic2", "in1", "in3" };
1114         const struct dmi_system_id *dmi_id;
1115         struct byt_rt5640_private *priv;
1116         struct snd_soc_acpi_mach *mach;
1117         const char *i2c_name = NULL;
1118         int ret_val = 0;
1119         int dai_index = 0;
1120         int i;
1121
1122         is_bytcr = false;
1123         priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
1124         if (!priv)
1125                 return -ENOMEM;
1126
1127         /* register the soc card */
1128         byt_rt5640_card.dev = &pdev->dev;
1129         mach = byt_rt5640_card.dev->platform_data;
1130         snd_soc_card_set_drvdata(&byt_rt5640_card, priv);
1131
1132         /* fix index of codec dai */
1133         for (i = 0; i < ARRAY_SIZE(byt_rt5640_dais); i++) {
1134                 if (!strcmp(byt_rt5640_dais[i].codec_name, "i2c-10EC5640:00")) {
1135                         dai_index = i;
1136                         break;
1137                 }
1138         }
1139
1140         /* fixup codec name based on HID */
1141         i2c_name = acpi_dev_get_first_match_name(mach->id, NULL, -1);
1142         if (i2c_name) {
1143                 snprintf(byt_rt5640_codec_name, sizeof(byt_rt5640_codec_name),
1144                         "%s%s", "i2c-", i2c_name);
1145
1146                 byt_rt5640_dais[dai_index].codec_name = byt_rt5640_codec_name;
1147         }
1148
1149         /*
1150          * swap SSP0 if bytcr is detected
1151          * (will be overridden if DMI quirk is detected)
1152          */
1153         if (is_valleyview()) {
1154                 if (mach->mach_params.acpi_ipc_irq_index == 0)
1155                         is_bytcr = true;
1156         }
1157
1158         if (is_bytcr) {
1159                 /*
1160                  * Baytrail CR platforms may have CHAN package in BIOS, try
1161                  * to find relevant routing quirk based as done on Windows
1162                  * platforms. We have to read the information directly from the
1163                  * BIOS, at this stage the card is not created and the links
1164                  * with the codec driver/pdata are non-existent
1165                  */
1166
1167                 struct acpi_chan_package chan_package;
1168
1169                 /* format specified: 2 64-bit integers */
1170                 struct acpi_buffer format = {sizeof("NN"), "NN"};
1171                 struct acpi_buffer state = {0, NULL};
1172                 struct snd_soc_acpi_package_context pkg_ctx;
1173                 bool pkg_found = false;
1174
1175                 state.length = sizeof(chan_package);
1176                 state.pointer = &chan_package;
1177
1178                 pkg_ctx.name = "CHAN";
1179                 pkg_ctx.length = 2;
1180                 pkg_ctx.format = &format;
1181                 pkg_ctx.state = &state;
1182                 pkg_ctx.data_valid = false;
1183
1184                 pkg_found = snd_soc_acpi_find_package_from_hid(mach->id,
1185                                                                &pkg_ctx);
1186                 if (pkg_found) {
1187                         if (chan_package.aif_value == 1) {
1188                                 dev_info(&pdev->dev, "BIOS Routing: AIF1 connected\n");
1189                                 byt_rt5640_quirk |= BYT_RT5640_SSP0_AIF1;
1190                         } else  if (chan_package.aif_value == 2) {
1191                                 dev_info(&pdev->dev, "BIOS Routing: AIF2 connected\n");
1192                                 byt_rt5640_quirk |= BYT_RT5640_SSP0_AIF2;
1193                         } else {
1194                                 dev_info(&pdev->dev, "BIOS Routing isn't valid, ignored\n");
1195                                 pkg_found = false;
1196                         }
1197                 }
1198
1199                 if (!pkg_found) {
1200                         /* no BIOS indications, assume SSP0-AIF2 connection */
1201                         byt_rt5640_quirk |= BYT_RT5640_SSP0_AIF2;
1202                 }
1203
1204                 /* change defaults for Baytrail-CR capture */
1205                 byt_rt5640_quirk |= BYTCR_INPUT_DEFAULTS;
1206         } else {
1207                 byt_rt5640_quirk |= BYT_RT5640_DMIC1_MAP |
1208                                     BYT_RT5640_JD_SRC_JD2_IN4N |
1209                                     BYT_RT5640_OVCD_TH_2000UA |
1210                                     BYT_RT5640_OVCD_SF_0P75;
1211         }
1212
1213         /* check quirks before creating card */
1214         dmi_id = dmi_first_match(byt_rt5640_quirk_table);
1215         if (dmi_id)
1216                 byt_rt5640_quirk = (unsigned long)dmi_id->driver_data;
1217         if (quirk_override) {
1218                 dev_info(&pdev->dev, "Overriding quirk 0x%x => 0x%x\n",
1219                          (unsigned int)byt_rt5640_quirk, quirk_override);
1220                 byt_rt5640_quirk = quirk_override;
1221         }
1222
1223         /* Must be called before register_card, also see declaration comment. */
1224         ret_val = byt_rt5640_add_codec_device_props(byt_rt5640_codec_name);
1225         if (ret_val)
1226                 return ret_val;
1227
1228         log_quirks(&pdev->dev);
1229
1230         if ((byt_rt5640_quirk & BYT_RT5640_SSP2_AIF2) ||
1231             (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2)) {
1232
1233                 /* fixup codec aif name */
1234                 snprintf(byt_rt5640_codec_aif_name,
1235                         sizeof(byt_rt5640_codec_aif_name),
1236                         "%s", "rt5640-aif2");
1237
1238                 byt_rt5640_dais[dai_index].codec_dai_name =
1239                         byt_rt5640_codec_aif_name;
1240         }
1241
1242         if ((byt_rt5640_quirk & BYT_RT5640_SSP0_AIF1) ||
1243             (byt_rt5640_quirk & BYT_RT5640_SSP0_AIF2)) {
1244
1245                 /* fixup cpu dai name name */
1246                 snprintf(byt_rt5640_cpu_dai_name,
1247                         sizeof(byt_rt5640_cpu_dai_name),
1248                         "%s", "ssp0-port");
1249
1250                 byt_rt5640_dais[dai_index].cpu_dai_name =
1251                         byt_rt5640_cpu_dai_name;
1252         }
1253
1254         if (byt_rt5640_quirk & BYT_RT5640_MCLK_EN) {
1255                 priv->mclk = devm_clk_get(&pdev->dev, "pmc_plt_clk_3");
1256                 if (IS_ERR(priv->mclk)) {
1257                         ret_val = PTR_ERR(priv->mclk);
1258
1259                         dev_err(&pdev->dev,
1260                                 "Failed to get MCLK from pmc_plt_clk_3: %d\n",
1261                                 ret_val);
1262
1263                         /*
1264                          * Fall back to bit clock usage for -ENOENT (clock not
1265                          * available likely due to missing dependencies), bail
1266                          * for all other errors, including -EPROBE_DEFER
1267                          */
1268                         if (ret_val != -ENOENT)
1269                                 return ret_val;
1270                         byt_rt5640_quirk &= ~BYT_RT5640_MCLK_EN;
1271                 }
1272         }
1273
1274         snprintf(byt_rt5640_long_name, sizeof(byt_rt5640_long_name),
1275                  "bytcr-rt5640-%s-spk-%s-mic",
1276                  (byt_rt5640_quirk & BYT_RT5640_MONO_SPEAKER) ?
1277                         "mono" : "stereo",
1278                  map_name[BYT_RT5640_MAP(byt_rt5640_quirk)]);
1279         byt_rt5640_card.long_name = byt_rt5640_long_name;
1280
1281         ret_val = devm_snd_soc_register_card(&pdev->dev, &byt_rt5640_card);
1282
1283         if (ret_val) {
1284                 dev_err(&pdev->dev, "devm_snd_soc_register_card failed %d\n",
1285                         ret_val);
1286                 return ret_val;
1287         }
1288         platform_set_drvdata(pdev, &byt_rt5640_card);
1289         return ret_val;
1290 }
1291
1292 static struct platform_driver snd_byt_rt5640_mc_driver = {
1293         .driver = {
1294                 .name = "bytcr_rt5640",
1295         },
1296         .probe = snd_byt_rt5640_mc_probe,
1297 };
1298
1299 module_platform_driver(snd_byt_rt5640_mc_driver);
1300
1301 MODULE_DESCRIPTION("ASoC Intel(R) Baytrail CR Machine driver");
1302 MODULE_AUTHOR("Subhransu S. Prusty <subhransu.s.prusty@intel.com>");
1303 MODULE_LICENSE("GPL v2");
1304 MODULE_ALIAS("platform:bytcr_rt5640");