1 // SPDX-License-Identifier: GPL-2.0 2 // 3 // mt8183-da7219-max98357.c 4 // -- MT8183-DA7219-MAX98357 ALSA SoC machine driver 5 // 6 // Copyright (c) 2018 MediaTek Inc. 7 // Author: Shunli Wang <shunli.wang@mediatek.com> 8 9 #include <linux/input.h> 10 #include <linux/module.h> 11 #include <linux/of_device.h> 12 #include <linux/pinctrl/consumer.h> 13 #include <sound/jack.h> 14 #include <sound/pcm_params.h> 15 #include <sound/soc.h> 16 17 #include "../../codecs/da7219-aad.h" 18 #include "../../codecs/da7219.h" 19 #include "../../codecs/rt1015.h" 20 #include "mt8183-afe-common.h" 21 22 #define DA7219_CODEC_DAI "da7219-hifi" 23 #define DA7219_DEV_NAME "da7219.5-001a" 24 #define RT1015_CODEC_DAI "rt1015-aif" 25 #define RT1015_DEV0_NAME "rt1015.6-0028" 26 #define RT1015_DEV1_NAME "rt1015.6-0029" 27 28 struct mt8183_da7219_max98357_priv { 29 struct snd_soc_jack headset_jack, hdmi_jack; 30 }; 31 32 static int mt8183_mt6358_i2s_hw_params(struct snd_pcm_substream *substream, 33 struct snd_pcm_hw_params *params) 34 { 35 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 36 unsigned int rate = params_rate(params); 37 unsigned int mclk_fs_ratio = 128; 38 unsigned int mclk_fs = rate * mclk_fs_ratio; 39 40 return snd_soc_dai_set_sysclk(asoc_rtd_to_cpu(rtd, 0), 41 0, mclk_fs, SND_SOC_CLOCK_OUT); 42 } 43 44 static const struct snd_soc_ops mt8183_mt6358_i2s_ops = { 45 .hw_params = mt8183_mt6358_i2s_hw_params, 46 }; 47 48 static int mt8183_da7219_i2s_hw_params(struct snd_pcm_substream *substream, 49 struct snd_pcm_hw_params *params) 50 { 51 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 52 struct snd_soc_dai *codec_dai; 53 unsigned int rate = params_rate(params); 54 unsigned int mclk_fs_ratio = 256; 55 unsigned int mclk_fs = rate * mclk_fs_ratio; 56 unsigned int freq; 57 int ret = 0, j; 58 59 ret = snd_soc_dai_set_sysclk(asoc_rtd_to_cpu(rtd, 0), 0, 60 mclk_fs, SND_SOC_CLOCK_OUT); 61 if (ret < 0) 62 dev_err(rtd->dev, "failed to set cpu dai sysclk\n"); 63 64 for_each_rtd_codec_dais(rtd, j, codec_dai) { 65 if (!strcmp(codec_dai->component->name, DA7219_DEV_NAME)) { 66 ret = snd_soc_dai_set_sysclk(codec_dai, 67 DA7219_CLKSRC_MCLK, 68 mclk_fs, 69 SND_SOC_CLOCK_IN); 70 if (ret < 0) 71 dev_err(rtd->dev, "failed to set sysclk\n"); 72 73 if ((rate % 8000) == 0) 74 freq = DA7219_PLL_FREQ_OUT_98304; 75 else 76 freq = DA7219_PLL_FREQ_OUT_90316; 77 78 ret = snd_soc_dai_set_pll(codec_dai, 0, 79 DA7219_SYSCLK_PLL_SRM, 80 0, freq); 81 if (ret) 82 dev_err(rtd->dev, "failed to start PLL: %d\n", 83 ret); 84 } 85 } 86 87 return ret; 88 } 89 90 static int mt8183_da7219_hw_free(struct snd_pcm_substream *substream) 91 { 92 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 93 struct snd_soc_dai *codec_dai; 94 int ret = 0, j; 95 96 for_each_rtd_codec_dais(rtd, j, codec_dai) { 97 if (!strcmp(codec_dai->component->name, DA7219_DEV_NAME)) { 98 ret = snd_soc_dai_set_pll(codec_dai, 99 0, DA7219_SYSCLK_MCLK, 0, 0); 100 if (ret < 0) { 101 dev_err(rtd->dev, "failed to stop PLL: %d\n", 102 ret); 103 break; 104 } 105 } 106 } 107 108 return ret; 109 } 110 111 static const struct snd_soc_ops mt8183_da7219_i2s_ops = { 112 .hw_params = mt8183_da7219_i2s_hw_params, 113 .hw_free = mt8183_da7219_hw_free, 114 }; 115 116 static int 117 mt8183_da7219_rt1015_i2s_hw_params(struct snd_pcm_substream *substream, 118 struct snd_pcm_hw_params *params) 119 { 120 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 121 unsigned int rate = params_rate(params); 122 struct snd_soc_dai *codec_dai; 123 int ret = 0, i; 124 125 for_each_rtd_codec_dais(rtd, i, codec_dai) { 126 if (!strcmp(codec_dai->component->name, RT1015_DEV0_NAME) || 127 !strcmp(codec_dai->component->name, RT1015_DEV1_NAME)) { 128 ret = snd_soc_dai_set_bclk_ratio(codec_dai, 64); 129 if (ret) { 130 dev_err(rtd->dev, "failed to set bclk ratio\n"); 131 return ret; 132 } 133 134 ret = snd_soc_dai_set_pll(codec_dai, 0, 135 RT1015_PLL_S_BCLK, 136 rate * 64, rate * 256); 137 if (ret) { 138 dev_err(rtd->dev, "failed to set pll\n"); 139 return ret; 140 } 141 142 ret = snd_soc_dai_set_sysclk(codec_dai, 143 RT1015_SCLK_S_PLL, 144 rate * 256, 145 SND_SOC_CLOCK_IN); 146 if (ret) { 147 dev_err(rtd->dev, "failed to set sysclk\n"); 148 return ret; 149 } 150 } 151 } 152 153 return mt8183_da7219_i2s_hw_params(substream, params); 154 } 155 156 static const struct snd_soc_ops mt8183_da7219_rt1015_i2s_ops = { 157 .hw_params = mt8183_da7219_rt1015_i2s_hw_params, 158 .hw_free = mt8183_da7219_hw_free, 159 }; 160 161 static int mt8183_i2s_hw_params_fixup(struct snd_soc_pcm_runtime *rtd, 162 struct snd_pcm_hw_params *params) 163 { 164 /* fix BE i2s format to 32bit, clean param mask first */ 165 snd_mask_reset_range(hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT), 166 0, SNDRV_PCM_FORMAT_LAST); 167 168 params_set_format(params, SNDRV_PCM_FORMAT_S32_LE); 169 170 return 0; 171 } 172 173 static int mt8183_rt1015_i2s_hw_params_fixup(struct snd_soc_pcm_runtime *rtd, 174 struct snd_pcm_hw_params *params) 175 { 176 /* fix BE i2s format to 32bit, clean param mask first */ 177 snd_mask_reset_range(hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT), 178 0, SNDRV_PCM_FORMAT_LAST); 179 180 params_set_format(params, SNDRV_PCM_FORMAT_S24_LE); 181 182 return 0; 183 } 184 185 static int 186 mt8183_da7219_max98357_startup( 187 struct snd_pcm_substream *substream) 188 { 189 static const unsigned int rates[] = { 190 48000, 191 }; 192 static const struct snd_pcm_hw_constraint_list constraints_rates = { 193 .count = ARRAY_SIZE(rates), 194 .list = rates, 195 .mask = 0, 196 }; 197 static const unsigned int channels[] = { 198 2, 199 }; 200 static const struct snd_pcm_hw_constraint_list constraints_channels = { 201 .count = ARRAY_SIZE(channels), 202 .list = channels, 203 .mask = 0, 204 }; 205 206 struct snd_pcm_runtime *runtime = substream->runtime; 207 208 snd_pcm_hw_constraint_list(runtime, 0, 209 SNDRV_PCM_HW_PARAM_RATE, &constraints_rates); 210 runtime->hw.channels_max = 2; 211 snd_pcm_hw_constraint_list(runtime, 0, 212 SNDRV_PCM_HW_PARAM_CHANNELS, 213 &constraints_channels); 214 215 runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE; 216 snd_pcm_hw_constraint_msbits(runtime, 0, 16, 16); 217 218 return 0; 219 } 220 221 static const struct snd_soc_ops mt8183_da7219_max98357_ops = { 222 .startup = mt8183_da7219_max98357_startup, 223 }; 224 225 static int 226 mt8183_da7219_max98357_bt_sco_startup( 227 struct snd_pcm_substream *substream) 228 { 229 static const unsigned int rates[] = { 230 8000, 16000 231 }; 232 static const struct snd_pcm_hw_constraint_list constraints_rates = { 233 .count = ARRAY_SIZE(rates), 234 .list = rates, 235 .mask = 0, 236 }; 237 static const unsigned int channels[] = { 238 1, 239 }; 240 static const struct snd_pcm_hw_constraint_list constraints_channels = { 241 .count = ARRAY_SIZE(channels), 242 .list = channels, 243 .mask = 0, 244 }; 245 246 struct snd_pcm_runtime *runtime = substream->runtime; 247 248 snd_pcm_hw_constraint_list(runtime, 0, 249 SNDRV_PCM_HW_PARAM_RATE, &constraints_rates); 250 runtime->hw.channels_max = 1; 251 snd_pcm_hw_constraint_list(runtime, 0, 252 SNDRV_PCM_HW_PARAM_CHANNELS, 253 &constraints_channels); 254 255 runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE; 256 snd_pcm_hw_constraint_msbits(runtime, 0, 16, 16); 257 258 return 0; 259 } 260 261 static const struct snd_soc_ops mt8183_da7219_max98357_bt_sco_ops = { 262 .startup = mt8183_da7219_max98357_bt_sco_startup, 263 }; 264 265 /* FE */ 266 SND_SOC_DAILINK_DEFS(playback1, 267 DAILINK_COMP_ARRAY(COMP_CPU("DL1")), 268 DAILINK_COMP_ARRAY(COMP_DUMMY()), 269 DAILINK_COMP_ARRAY(COMP_EMPTY())); 270 271 SND_SOC_DAILINK_DEFS(playback2, 272 DAILINK_COMP_ARRAY(COMP_CPU("DL2")), 273 DAILINK_COMP_ARRAY(COMP_DUMMY()), 274 DAILINK_COMP_ARRAY(COMP_EMPTY())); 275 276 SND_SOC_DAILINK_DEFS(playback3, 277 DAILINK_COMP_ARRAY(COMP_CPU("DL3")), 278 DAILINK_COMP_ARRAY(COMP_DUMMY()), 279 DAILINK_COMP_ARRAY(COMP_EMPTY())); 280 281 SND_SOC_DAILINK_DEFS(capture1, 282 DAILINK_COMP_ARRAY(COMP_CPU("UL1")), 283 DAILINK_COMP_ARRAY(COMP_DUMMY()), 284 DAILINK_COMP_ARRAY(COMP_EMPTY())); 285 286 SND_SOC_DAILINK_DEFS(capture2, 287 DAILINK_COMP_ARRAY(COMP_CPU("UL2")), 288 DAILINK_COMP_ARRAY(COMP_DUMMY()), 289 DAILINK_COMP_ARRAY(COMP_EMPTY())); 290 291 SND_SOC_DAILINK_DEFS(capture3, 292 DAILINK_COMP_ARRAY(COMP_CPU("UL3")), 293 DAILINK_COMP_ARRAY(COMP_DUMMY()), 294 DAILINK_COMP_ARRAY(COMP_EMPTY())); 295 296 SND_SOC_DAILINK_DEFS(capture_mono, 297 DAILINK_COMP_ARRAY(COMP_CPU("UL_MONO_1")), 298 DAILINK_COMP_ARRAY(COMP_DUMMY()), 299 DAILINK_COMP_ARRAY(COMP_EMPTY())); 300 301 SND_SOC_DAILINK_DEFS(playback_hdmi, 302 DAILINK_COMP_ARRAY(COMP_CPU("HDMI")), 303 DAILINK_COMP_ARRAY(COMP_DUMMY()), 304 DAILINK_COMP_ARRAY(COMP_EMPTY())); 305 306 /* BE */ 307 SND_SOC_DAILINK_DEFS(primary_codec, 308 DAILINK_COMP_ARRAY(COMP_CPU("ADDA")), 309 DAILINK_COMP_ARRAY(COMP_CODEC("mt6358-sound", "mt6358-snd-codec-aif1")), 310 DAILINK_COMP_ARRAY(COMP_EMPTY())); 311 312 SND_SOC_DAILINK_DEFS(pcm1, 313 DAILINK_COMP_ARRAY(COMP_CPU("PCM 1")), 314 DAILINK_COMP_ARRAY(COMP_DUMMY()), 315 DAILINK_COMP_ARRAY(COMP_EMPTY())); 316 317 SND_SOC_DAILINK_DEFS(pcm2, 318 DAILINK_COMP_ARRAY(COMP_CPU("PCM 2")), 319 DAILINK_COMP_ARRAY(COMP_DUMMY()), 320 DAILINK_COMP_ARRAY(COMP_EMPTY())); 321 322 SND_SOC_DAILINK_DEFS(i2s0, 323 DAILINK_COMP_ARRAY(COMP_CPU("I2S0")), 324 DAILINK_COMP_ARRAY(COMP_CODEC("bt-sco", "bt-sco-pcm")), 325 DAILINK_COMP_ARRAY(COMP_EMPTY())); 326 327 SND_SOC_DAILINK_DEFS(i2s1, 328 DAILINK_COMP_ARRAY(COMP_CPU("I2S1")), 329 DAILINK_COMP_ARRAY(COMP_DUMMY()), 330 DAILINK_COMP_ARRAY(COMP_EMPTY())); 331 332 SND_SOC_DAILINK_DEFS(i2s2, 333 DAILINK_COMP_ARRAY(COMP_CPU("I2S2")), 334 DAILINK_COMP_ARRAY(COMP_CODEC(DA7219_DEV_NAME, DA7219_CODEC_DAI)), 335 DAILINK_COMP_ARRAY(COMP_EMPTY())); 336 337 SND_SOC_DAILINK_DEFS(i2s3_max98357a, 338 DAILINK_COMP_ARRAY(COMP_CPU("I2S3")), 339 DAILINK_COMP_ARRAY(COMP_CODEC("max98357a", "HiFi"), 340 COMP_CODEC(DA7219_DEV_NAME, DA7219_CODEC_DAI)), 341 DAILINK_COMP_ARRAY(COMP_EMPTY())); 342 343 SND_SOC_DAILINK_DEFS(i2s3_rt1015, 344 DAILINK_COMP_ARRAY(COMP_CPU("I2S3")), 345 DAILINK_COMP_ARRAY(COMP_CODEC(RT1015_DEV0_NAME, RT1015_CODEC_DAI), 346 COMP_CODEC(RT1015_DEV1_NAME, RT1015_CODEC_DAI), 347 COMP_CODEC(DA7219_DEV_NAME, DA7219_CODEC_DAI)), 348 DAILINK_COMP_ARRAY(COMP_EMPTY())); 349 350 SND_SOC_DAILINK_DEFS(i2s3_rt1015p, 351 DAILINK_COMP_ARRAY(COMP_CPU("I2S3")), 352 DAILINK_COMP_ARRAY(COMP_CODEC("rt1015p", "HiFi"), 353 COMP_CODEC(DA7219_DEV_NAME, DA7219_CODEC_DAI)), 354 DAILINK_COMP_ARRAY(COMP_EMPTY())); 355 356 SND_SOC_DAILINK_DEFS(i2s5, 357 DAILINK_COMP_ARRAY(COMP_CPU("I2S5")), 358 DAILINK_COMP_ARRAY(COMP_CODEC("bt-sco", "bt-sco-pcm")), 359 DAILINK_COMP_ARRAY(COMP_EMPTY())); 360 361 SND_SOC_DAILINK_DEFS(tdm, 362 DAILINK_COMP_ARRAY(COMP_CPU("TDM")), 363 DAILINK_COMP_ARRAY(COMP_CODEC(NULL, "i2s-hifi")), 364 DAILINK_COMP_ARRAY(COMP_EMPTY())); 365 366 static int mt8183_da7219_max98357_hdmi_init(struct snd_soc_pcm_runtime *rtd) 367 { 368 struct mt8183_da7219_max98357_priv *priv = 369 snd_soc_card_get_drvdata(rtd->card); 370 int ret; 371 372 ret = snd_soc_card_jack_new(rtd->card, "HDMI Jack", SND_JACK_LINEOUT, 373 &priv->hdmi_jack, NULL, 0); 374 if (ret) 375 return ret; 376 377 return snd_soc_component_set_jack(asoc_rtd_to_codec(rtd, 0)->component, 378 &priv->hdmi_jack, NULL); 379 } 380 381 static struct snd_soc_dai_link mt8183_da7219_dai_links[] = { 382 /* FE */ 383 { 384 .name = "Playback_1", 385 .stream_name = "Playback_1", 386 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 387 SND_SOC_DPCM_TRIGGER_PRE}, 388 .dynamic = 1, 389 .dpcm_playback = 1, 390 .ops = &mt8183_da7219_max98357_ops, 391 SND_SOC_DAILINK_REG(playback1), 392 }, 393 { 394 .name = "Playback_2", 395 .stream_name = "Playback_2", 396 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 397 SND_SOC_DPCM_TRIGGER_PRE}, 398 .dynamic = 1, 399 .dpcm_playback = 1, 400 .ops = &mt8183_da7219_max98357_bt_sco_ops, 401 SND_SOC_DAILINK_REG(playback2), 402 }, 403 { 404 .name = "Playback_3", 405 .stream_name = "Playback_3", 406 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 407 SND_SOC_DPCM_TRIGGER_PRE}, 408 .dynamic = 1, 409 .dpcm_playback = 1, 410 SND_SOC_DAILINK_REG(playback3), 411 }, 412 { 413 .name = "Capture_1", 414 .stream_name = "Capture_1", 415 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 416 SND_SOC_DPCM_TRIGGER_PRE}, 417 .dynamic = 1, 418 .dpcm_capture = 1, 419 .ops = &mt8183_da7219_max98357_bt_sco_ops, 420 SND_SOC_DAILINK_REG(capture1), 421 }, 422 { 423 .name = "Capture_2", 424 .stream_name = "Capture_2", 425 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 426 SND_SOC_DPCM_TRIGGER_PRE}, 427 .dynamic = 1, 428 .dpcm_capture = 1, 429 SND_SOC_DAILINK_REG(capture2), 430 }, 431 { 432 .name = "Capture_3", 433 .stream_name = "Capture_3", 434 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 435 SND_SOC_DPCM_TRIGGER_PRE}, 436 .dynamic = 1, 437 .dpcm_capture = 1, 438 .ops = &mt8183_da7219_max98357_ops, 439 SND_SOC_DAILINK_REG(capture3), 440 }, 441 { 442 .name = "Capture_Mono_1", 443 .stream_name = "Capture_Mono_1", 444 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 445 SND_SOC_DPCM_TRIGGER_PRE}, 446 .dynamic = 1, 447 .dpcm_capture = 1, 448 SND_SOC_DAILINK_REG(capture_mono), 449 }, 450 { 451 .name = "Playback_HDMI", 452 .stream_name = "Playback_HDMI", 453 .trigger = {SND_SOC_DPCM_TRIGGER_PRE, 454 SND_SOC_DPCM_TRIGGER_PRE}, 455 .dynamic = 1, 456 .dpcm_playback = 1, 457 SND_SOC_DAILINK_REG(playback_hdmi), 458 }, 459 /* BE */ 460 { 461 .name = "Primary Codec", 462 .no_pcm = 1, 463 .dpcm_playback = 1, 464 .dpcm_capture = 1, 465 .ignore_suspend = 1, 466 SND_SOC_DAILINK_REG(primary_codec), 467 }, 468 { 469 .name = "PCM 1", 470 .no_pcm = 1, 471 .dpcm_playback = 1, 472 .dpcm_capture = 1, 473 .ignore_suspend = 1, 474 SND_SOC_DAILINK_REG(pcm1), 475 }, 476 { 477 .name = "PCM 2", 478 .no_pcm = 1, 479 .dpcm_playback = 1, 480 .dpcm_capture = 1, 481 .ignore_suspend = 1, 482 SND_SOC_DAILINK_REG(pcm2), 483 }, 484 { 485 .name = "I2S0", 486 .no_pcm = 1, 487 .dpcm_capture = 1, 488 .ignore_suspend = 1, 489 .be_hw_params_fixup = mt8183_i2s_hw_params_fixup, 490 .ops = &mt8183_mt6358_i2s_ops, 491 SND_SOC_DAILINK_REG(i2s0), 492 }, 493 { 494 .name = "I2S1", 495 .no_pcm = 1, 496 .dpcm_playback = 1, 497 .ignore_suspend = 1, 498 .be_hw_params_fixup = mt8183_i2s_hw_params_fixup, 499 .ops = &mt8183_mt6358_i2s_ops, 500 SND_SOC_DAILINK_REG(i2s1), 501 }, 502 { 503 .name = "I2S2", 504 .no_pcm = 1, 505 .dpcm_capture = 1, 506 .ignore_suspend = 1, 507 .be_hw_params_fixup = mt8183_i2s_hw_params_fixup, 508 .ops = &mt8183_da7219_i2s_ops, 509 SND_SOC_DAILINK_REG(i2s2), 510 }, 511 { 512 .name = "I2S3", 513 .no_pcm = 1, 514 .dpcm_playback = 1, 515 .ignore_suspend = 1, 516 }, 517 { 518 .name = "I2S5", 519 .no_pcm = 1, 520 .dpcm_playback = 1, 521 .ignore_suspend = 1, 522 .be_hw_params_fixup = mt8183_i2s_hw_params_fixup, 523 .ops = &mt8183_mt6358_i2s_ops, 524 SND_SOC_DAILINK_REG(i2s5), 525 }, 526 { 527 .name = "TDM", 528 .no_pcm = 1, 529 .dai_fmt = SND_SOC_DAIFMT_I2S | 530 SND_SOC_DAIFMT_IB_IF | 531 SND_SOC_DAIFMT_CBM_CFM, 532 .dpcm_playback = 1, 533 .ignore_suspend = 1, 534 .be_hw_params_fixup = mt8183_i2s_hw_params_fixup, 535 .init = mt8183_da7219_max98357_hdmi_init, 536 SND_SOC_DAILINK_REG(tdm), 537 }, 538 }; 539 540 static int 541 mt8183_da7219_max98357_headset_init(struct snd_soc_component *component) 542 { 543 int ret; 544 struct mt8183_da7219_max98357_priv *priv = 545 snd_soc_card_get_drvdata(component->card); 546 547 /* Enable Headset and 4 Buttons Jack detection */ 548 ret = snd_soc_card_jack_new(component->card, 549 "Headset Jack", 550 SND_JACK_HEADSET | 551 SND_JACK_BTN_0 | SND_JACK_BTN_1 | 552 SND_JACK_BTN_2 | SND_JACK_BTN_3 | 553 SND_JACK_LINEOUT, 554 &priv->headset_jack, 555 NULL, 0); 556 if (ret) 557 return ret; 558 559 snd_jack_set_key( 560 priv->headset_jack.jack, SND_JACK_BTN_0, KEY_PLAYPAUSE); 561 snd_jack_set_key( 562 priv->headset_jack.jack, SND_JACK_BTN_1, KEY_VOLUMEUP); 563 snd_jack_set_key( 564 priv->headset_jack.jack, SND_JACK_BTN_2, KEY_VOLUMEDOWN); 565 snd_jack_set_key( 566 priv->headset_jack.jack, SND_JACK_BTN_3, KEY_VOICECOMMAND); 567 568 da7219_aad_jack_det(component, &priv->headset_jack); 569 570 return 0; 571 } 572 573 static struct snd_soc_aux_dev mt8183_da7219_max98357_headset_dev = { 574 .dlc = COMP_EMPTY(), 575 .init = mt8183_da7219_max98357_headset_init, 576 }; 577 578 static struct snd_soc_codec_conf mt6358_codec_conf[] = { 579 { 580 .dlc = COMP_CODEC_CONF("mt6358-sound"), 581 .name_prefix = "Mt6358", 582 }, 583 }; 584 585 static const struct snd_kcontrol_new mt8183_da7219_max98357_snd_controls[] = { 586 SOC_DAPM_PIN_SWITCH("Speakers"), 587 }; 588 589 static const 590 struct snd_soc_dapm_widget mt8183_da7219_max98357_dapm_widgets[] = { 591 SND_SOC_DAPM_SPK("Speakers", NULL), 592 SND_SOC_DAPM_PINCTRL("TDM_OUT_PINCTRL", 593 "aud_tdm_out_on", "aud_tdm_out_off"), 594 }; 595 596 static const struct snd_soc_dapm_route mt8183_da7219_max98357_dapm_routes[] = { 597 {"Speakers", NULL, "Speaker"}, 598 {"I2S Playback", NULL, "TDM_OUT_PINCTRL"}, 599 }; 600 601 static struct snd_soc_card mt8183_da7219_max98357_card = { 602 .name = "mt8183_da7219_max98357", 603 .owner = THIS_MODULE, 604 .controls = mt8183_da7219_max98357_snd_controls, 605 .num_controls = ARRAY_SIZE(mt8183_da7219_max98357_snd_controls), 606 .dapm_widgets = mt8183_da7219_max98357_dapm_widgets, 607 .num_dapm_widgets = ARRAY_SIZE(mt8183_da7219_max98357_dapm_widgets), 608 .dapm_routes = mt8183_da7219_max98357_dapm_routes, 609 .num_dapm_routes = ARRAY_SIZE(mt8183_da7219_max98357_dapm_routes), 610 .dai_link = mt8183_da7219_dai_links, 611 .num_links = ARRAY_SIZE(mt8183_da7219_dai_links), 612 .aux_dev = &mt8183_da7219_max98357_headset_dev, 613 .num_aux_devs = 1, 614 .codec_conf = mt6358_codec_conf, 615 .num_configs = ARRAY_SIZE(mt6358_codec_conf), 616 }; 617 618 static struct snd_soc_codec_conf mt8183_da7219_rt1015_codec_conf[] = { 619 { 620 .dlc = COMP_CODEC_CONF("mt6358-sound"), 621 .name_prefix = "Mt6358", 622 }, 623 { 624 .dlc = COMP_CODEC_CONF(RT1015_DEV0_NAME), 625 .name_prefix = "Left", 626 }, 627 { 628 .dlc = COMP_CODEC_CONF(RT1015_DEV1_NAME), 629 .name_prefix = "Right", 630 }, 631 }; 632 633 static const struct snd_kcontrol_new mt8183_da7219_rt1015_snd_controls[] = { 634 SOC_DAPM_PIN_SWITCH("Left Spk"), 635 SOC_DAPM_PIN_SWITCH("Right Spk"), 636 }; 637 638 static const 639 struct snd_soc_dapm_widget mt8183_da7219_rt1015_dapm_widgets[] = { 640 SND_SOC_DAPM_SPK("Left Spk", NULL), 641 SND_SOC_DAPM_SPK("Right Spk", NULL), 642 SND_SOC_DAPM_PINCTRL("TDM_OUT_PINCTRL", 643 "aud_tdm_out_on", "aud_tdm_out_off"), 644 }; 645 646 static const struct snd_soc_dapm_route mt8183_da7219_rt1015_dapm_routes[] = { 647 {"Left Spk", NULL, "Left SPO"}, 648 {"Right Spk", NULL, "Right SPO"}, 649 {"I2S Playback", NULL, "TDM_OUT_PINCTRL"}, 650 }; 651 652 static struct snd_soc_card mt8183_da7219_rt1015_card = { 653 .name = "mt8183_da7219_rt1015", 654 .owner = THIS_MODULE, 655 .controls = mt8183_da7219_rt1015_snd_controls, 656 .num_controls = ARRAY_SIZE(mt8183_da7219_rt1015_snd_controls), 657 .dapm_widgets = mt8183_da7219_rt1015_dapm_widgets, 658 .num_dapm_widgets = ARRAY_SIZE(mt8183_da7219_rt1015_dapm_widgets), 659 .dapm_routes = mt8183_da7219_rt1015_dapm_routes, 660 .num_dapm_routes = ARRAY_SIZE(mt8183_da7219_rt1015_dapm_routes), 661 .dai_link = mt8183_da7219_dai_links, 662 .num_links = ARRAY_SIZE(mt8183_da7219_dai_links), 663 .aux_dev = &mt8183_da7219_max98357_headset_dev, 664 .num_aux_devs = 1, 665 .codec_conf = mt8183_da7219_rt1015_codec_conf, 666 .num_configs = ARRAY_SIZE(mt8183_da7219_rt1015_codec_conf), 667 }; 668 669 static struct snd_soc_card mt8183_da7219_rt1015p_card = { 670 .name = "mt8183_da7219_rt1015p", 671 .owner = THIS_MODULE, 672 .controls = mt8183_da7219_max98357_snd_controls, 673 .num_controls = ARRAY_SIZE(mt8183_da7219_max98357_snd_controls), 674 .dapm_widgets = mt8183_da7219_max98357_dapm_widgets, 675 .num_dapm_widgets = ARRAY_SIZE(mt8183_da7219_max98357_dapm_widgets), 676 .dapm_routes = mt8183_da7219_max98357_dapm_routes, 677 .num_dapm_routes = ARRAY_SIZE(mt8183_da7219_max98357_dapm_routes), 678 .dai_link = mt8183_da7219_dai_links, 679 .num_links = ARRAY_SIZE(mt8183_da7219_dai_links), 680 .aux_dev = &mt8183_da7219_max98357_headset_dev, 681 .num_aux_devs = 1, 682 .codec_conf = mt6358_codec_conf, 683 .num_configs = ARRAY_SIZE(mt6358_codec_conf), 684 }; 685 686 static int mt8183_da7219_max98357_dev_probe(struct platform_device *pdev) 687 { 688 struct snd_soc_card *card; 689 struct device_node *platform_node, *hdmi_codec; 690 struct snd_soc_dai_link *dai_link; 691 struct mt8183_da7219_max98357_priv *priv; 692 struct pinctrl *pinctrl; 693 const struct of_device_id *match; 694 int ret, i; 695 696 platform_node = of_parse_phandle(pdev->dev.of_node, 697 "mediatek,platform", 0); 698 if (!platform_node) { 699 dev_err(&pdev->dev, "Property 'platform' missing or invalid\n"); 700 return -EINVAL; 701 } 702 703 match = of_match_device(pdev->dev.driver->of_match_table, &pdev->dev); 704 if (!match || !match->data) 705 return -EINVAL; 706 707 card = (struct snd_soc_card *)match->data; 708 card->dev = &pdev->dev; 709 710 hdmi_codec = of_parse_phandle(pdev->dev.of_node, 711 "mediatek,hdmi-codec", 0); 712 713 for_each_card_prelinks(card, i, dai_link) { 714 if (strcmp(dai_link->name, "I2S3") == 0) { 715 if (card == &mt8183_da7219_max98357_card) { 716 dai_link->be_hw_params_fixup = 717 mt8183_i2s_hw_params_fixup; 718 dai_link->ops = &mt8183_da7219_i2s_ops; 719 dai_link->cpus = i2s3_max98357a_cpus; 720 dai_link->num_cpus = 721 ARRAY_SIZE(i2s3_max98357a_cpus); 722 dai_link->codecs = i2s3_max98357a_codecs; 723 dai_link->num_codecs = 724 ARRAY_SIZE(i2s3_max98357a_codecs); 725 dai_link->platforms = i2s3_max98357a_platforms; 726 dai_link->num_platforms = 727 ARRAY_SIZE(i2s3_max98357a_platforms); 728 } else if (card == &mt8183_da7219_rt1015_card) { 729 dai_link->be_hw_params_fixup = 730 mt8183_rt1015_i2s_hw_params_fixup; 731 dai_link->ops = &mt8183_da7219_rt1015_i2s_ops; 732 dai_link->cpus = i2s3_rt1015_cpus; 733 dai_link->num_cpus = 734 ARRAY_SIZE(i2s3_rt1015_cpus); 735 dai_link->codecs = i2s3_rt1015_codecs; 736 dai_link->num_codecs = 737 ARRAY_SIZE(i2s3_rt1015_codecs); 738 dai_link->platforms = i2s3_rt1015_platforms; 739 dai_link->num_platforms = 740 ARRAY_SIZE(i2s3_rt1015_platforms); 741 } else if (card == &mt8183_da7219_rt1015p_card) { 742 dai_link->be_hw_params_fixup = 743 mt8183_rt1015_i2s_hw_params_fixup; 744 dai_link->ops = &mt8183_da7219_i2s_ops; 745 dai_link->cpus = i2s3_rt1015p_cpus; 746 dai_link->num_cpus = 747 ARRAY_SIZE(i2s3_rt1015p_cpus); 748 dai_link->codecs = i2s3_rt1015p_codecs; 749 dai_link->num_codecs = 750 ARRAY_SIZE(i2s3_rt1015p_codecs); 751 dai_link->platforms = i2s3_rt1015p_platforms; 752 dai_link->num_platforms = 753 ARRAY_SIZE(i2s3_rt1015p_platforms); 754 } 755 } 756 757 if (hdmi_codec && strcmp(dai_link->name, "TDM") == 0) 758 dai_link->codecs->of_node = hdmi_codec; 759 760 if (!dai_link->platforms->name) 761 dai_link->platforms->of_node = platform_node; 762 } 763 764 mt8183_da7219_max98357_headset_dev.dlc.of_node = 765 of_parse_phandle(pdev->dev.of_node, 766 "mediatek,headset-codec", 0); 767 if (!mt8183_da7219_max98357_headset_dev.dlc.of_node) { 768 dev_err(&pdev->dev, 769 "Property 'mediatek,headset-codec' missing/invalid\n"); 770 return -EINVAL; 771 } 772 773 priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); 774 if (!priv) 775 return -ENOMEM; 776 777 snd_soc_card_set_drvdata(card, priv); 778 779 pinctrl = devm_pinctrl_get_select(&pdev->dev, PINCTRL_STATE_DEFAULT); 780 if (IS_ERR(pinctrl)) { 781 ret = PTR_ERR(pinctrl); 782 dev_err(&pdev->dev, "%s failed to select default state %d\n", 783 __func__, ret); 784 return ret; 785 } 786 787 return devm_snd_soc_register_card(&pdev->dev, card); 788 } 789 790 #ifdef CONFIG_OF 791 static const struct of_device_id mt8183_da7219_max98357_dt_match[] = { 792 { 793 .compatible = "mediatek,mt8183_da7219_max98357", 794 .data = &mt8183_da7219_max98357_card, 795 }, 796 { 797 .compatible = "mediatek,mt8183_da7219_rt1015", 798 .data = &mt8183_da7219_rt1015_card, 799 }, 800 { 801 .compatible = "mediatek,mt8183_da7219_rt1015p", 802 .data = &mt8183_da7219_rt1015p_card, 803 }, 804 {} 805 }; 806 #endif 807 808 static struct platform_driver mt8183_da7219_max98357_driver = { 809 .driver = { 810 .name = "mt8183_da7219", 811 #ifdef CONFIG_OF 812 .of_match_table = mt8183_da7219_max98357_dt_match, 813 #endif 814 .pm = &snd_soc_pm_ops, 815 }, 816 .probe = mt8183_da7219_max98357_dev_probe, 817 }; 818 819 module_platform_driver(mt8183_da7219_max98357_driver); 820 821 /* Module information */ 822 MODULE_DESCRIPTION("MT8183-DA7219-MAX98357 ALSA SoC machine driver"); 823 MODULE_AUTHOR("Shunli Wang <shunli.wang@mediatek.com>"); 824 MODULE_LICENSE("GPL v2"); 825 MODULE_ALIAS("mt8183_da7219_max98357 soc card"); 826