smdk_wm8994pcm.c 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. // SPDX-License-Identifier: GPL-2.0+
  2. //
  3. // Copyright (c) 2011 Samsung Electronics Co., Ltd
  4. // http://www.samsung.com
  5. #include <linux/module.h>
  6. #include <sound/soc.h>
  7. #include <sound/pcm.h>
  8. #include <sound/pcm_params.h>
  9. #include "../codecs/wm8994.h"
  10. #include "pcm.h"
  11. /*
  12. * Board Settings:
  13. * o '1' means 'ON'
  14. * o '0' means 'OFF'
  15. * o 'X' means 'Don't care'
  16. *
  17. * SMDKC210, SMDKV310: CFG3- 1001, CFG5-1000, CFG7-111111
  18. */
  19. /*
  20. * Configure audio route as :-
  21. * $ amixer sset 'DAC1' on,on
  22. * $ amixer sset 'Right Headphone Mux' 'DAC'
  23. * $ amixer sset 'Left Headphone Mux' 'DAC'
  24. * $ amixer sset 'DAC1R Mixer AIF1.1' on
  25. * $ amixer sset 'DAC1L Mixer AIF1.1' on
  26. * $ amixer sset 'IN2L' on
  27. * $ amixer sset 'IN2L PGA IN2LN' on
  28. * $ amixer sset 'MIXINL IN2L' on
  29. * $ amixer sset 'AIF1ADC1L Mixer ADC/DMIC' on
  30. * $ amixer sset 'IN2R' on
  31. * $ amixer sset 'IN2R PGA IN2RN' on
  32. * $ amixer sset 'MIXINR IN2R' on
  33. * $ amixer sset 'AIF1ADC1R Mixer ADC/DMIC' on
  34. */
  35. /* SMDK has a 16.9344MHZ crystal attached to WM8994 */
  36. #define SMDK_WM8994_FREQ 16934400
  37. static int smdk_wm8994_pcm_hw_params(struct snd_pcm_substream *substream,
  38. struct snd_pcm_hw_params *params)
  39. {
  40. struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
  41. struct snd_soc_dai *codec_dai = snd_soc_rtd_to_codec(rtd, 0);
  42. struct snd_soc_dai *cpu_dai = snd_soc_rtd_to_cpu(rtd, 0);
  43. unsigned long mclk_freq;
  44. int rfs, ret;
  45. switch(params_rate(params)) {
  46. case 8000:
  47. rfs = 512;
  48. break;
  49. default:
  50. dev_err(cpu_dai->dev, "%s:%d Sampling Rate %u not supported!\n",
  51. __func__, __LINE__, params_rate(params));
  52. return -EINVAL;
  53. }
  54. mclk_freq = params_rate(params) * rfs;
  55. ret = snd_soc_dai_set_sysclk(codec_dai, WM8994_SYSCLK_FLL1,
  56. mclk_freq, SND_SOC_CLOCK_IN);
  57. if (ret < 0)
  58. return ret;
  59. ret = snd_soc_dai_set_pll(codec_dai, WM8994_FLL1, WM8994_FLL_SRC_MCLK1,
  60. SMDK_WM8994_FREQ, mclk_freq);
  61. if (ret < 0)
  62. return ret;
  63. /* Set PCM source clock on CPU */
  64. ret = snd_soc_dai_set_sysclk(cpu_dai, S3C_PCM_CLKSRC_MUX,
  65. mclk_freq, SND_SOC_CLOCK_IN);
  66. if (ret < 0)
  67. return ret;
  68. /* Set SCLK_DIV for making bclk */
  69. ret = snd_soc_dai_set_clkdiv(cpu_dai, S3C_PCM_SCLK_PER_FS, rfs);
  70. if (ret < 0)
  71. return ret;
  72. return 0;
  73. }
  74. static const struct snd_soc_ops smdk_wm8994_pcm_ops = {
  75. .hw_params = smdk_wm8994_pcm_hw_params,
  76. };
  77. SND_SOC_DAILINK_DEFS(paif_pcm,
  78. DAILINK_COMP_ARRAY(COMP_CPU("samsung-pcm.0")),
  79. DAILINK_COMP_ARRAY(COMP_CODEC("wm8994-codec", "wm8994-aif1")),
  80. DAILINK_COMP_ARRAY(COMP_PLATFORM("samsung-pcm.0")));
  81. static struct snd_soc_dai_link smdk_dai[] = {
  82. {
  83. .name = "WM8994 PAIF PCM",
  84. .stream_name = "Primary PCM",
  85. .dai_fmt = SND_SOC_DAIFMT_DSP_B | SND_SOC_DAIFMT_IB_NF |
  86. SND_SOC_DAIFMT_CBS_CFS,
  87. .ops = &smdk_wm8994_pcm_ops,
  88. SND_SOC_DAILINK_REG(paif_pcm),
  89. },
  90. };
  91. static struct snd_soc_card smdk_pcm = {
  92. .name = "SMDK-PCM",
  93. .owner = THIS_MODULE,
  94. .dai_link = smdk_dai,
  95. .num_links = 1,
  96. };
  97. static int snd_smdk_probe(struct platform_device *pdev)
  98. {
  99. int ret = 0;
  100. smdk_pcm.dev = &pdev->dev;
  101. ret = devm_snd_soc_register_card(&pdev->dev, &smdk_pcm);
  102. if (ret)
  103. dev_err_probe(&pdev->dev, ret, "snd_soc_register_card failed\n");
  104. return ret;
  105. }
  106. static struct platform_driver snd_smdk_driver = {
  107. .driver = {
  108. .name = "samsung-smdk-pcm",
  109. },
  110. .probe = snd_smdk_probe,
  111. };
  112. module_platform_driver(snd_smdk_driver);
  113. MODULE_AUTHOR("Sangbeom Kim, <sbkim73@samsung.com>");
  114. MODULE_DESCRIPTION("ALSA SoC SMDK WM8994 for PCM");
  115. MODULE_LICENSE("GPL");