summaryrefslogtreecommitdiff
path: root/sound/soc/tegra/tegra_wm8903.c
diff options
context:
space:
mode:
authorSumit Bhattacharya <sumitb@nvidia.com>2011-10-24 21:14:39 +0530
committerDan Willemsen <dwillemsen@nvidia.com>2011-11-30 21:50:05 -0800
commit3ce4caadde83d0951c36c66ecffb22df8b7a96c9 (patch)
tree4758f57ea80877ab3bc98f64e95b41185df706d8 /sound/soc/tegra/tegra_wm8903.c
parentf15ba4f7d9e4ecf598ca31d25afbb00685990346 (diff)
ASoC: Tegra WM8903 machine: Add suppport for Tegra20 BT SCO
Add a new dai-link interface to wm8903 machine driver which can be used for BT SCO playback and record on Tegra20. Also add code to program Tegra20 DAS controller depending on active dai-link. Bug 872652 Change-Id: I006a2542b20cfd94c246d19770aa836c2bbf4198 Signed-off-by: Sumit Bhattacharya <sumitb@nvidia.com> Reviewed-on: http://git-master/r/59060 Reviewed-by: Scott Peterson <speterson@nvidia.com> Rebase-Id: R36dfd3082c6119a452c0bab8858637b3f139f5e5
Diffstat (limited to 'sound/soc/tegra/tegra_wm8903.c')
-rw-r--r--sound/soc/tegra/tegra_wm8903.c107
1 files changed, 106 insertions, 1 deletions
diff --git a/sound/soc/tegra/tegra_wm8903.c b/sound/soc/tegra/tegra_wm8903.c
index 8ef9da6e2789..ad2be41af4d6 100644
--- a/sound/soc/tegra/tegra_wm8903.c
+++ b/sound/soc/tegra/tegra_wm8903.c
@@ -49,6 +49,10 @@
#include "tegra_pcm.h"
#include "tegra_asoc_utils.h"
+#ifdef CONFIG_ARCH_TEGRA_2x_SOC
+#include "tegra20_das.h"
+#endif
+
#define DRV_NAME "tegra-snd-wm8903"
#define GPIO_SPKR_EN BIT(0)
@@ -134,6 +138,91 @@ static int tegra_wm8903_hw_params(struct snd_pcm_substream *substream,
return err;
}
+#ifdef CONFIG_ARCH_TEGRA_2x_SOC
+ err = tegra20_das_connect_dac_to_dap(TEGRA20_DAS_DAP_SEL_DAC1,
+ TEGRA20_DAS_DAP_ID_1);
+ if (err < 0) {
+ dev_err(card->dev, "failed to set dap-dac path\n");
+ return err;
+ }
+
+ err = tegra20_das_connect_dap_to_dac(TEGRA20_DAS_DAP_ID_1,
+ TEGRA20_DAS_DAP_SEL_DAC1);
+ if (err < 0) {
+ dev_err(card->dev, "failed to set dac-dap path\n");
+ return err;
+ }
+#endif
+ return 0;
+}
+
+static int tegra_bt_sco_hw_params(struct snd_pcm_substream *substream,
+ struct snd_pcm_hw_params *params)
+{
+ struct snd_soc_pcm_runtime *rtd = substream->private_data;
+ struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
+ struct snd_soc_card *card = rtd->card;
+ struct tegra_wm8903 *machine = snd_soc_card_get_drvdata(card);
+ int srate, mclk, min_mclk;
+ int err;
+
+ srate = params_rate(params);
+ switch (srate) {
+ case 11025:
+ case 22050:
+ case 44100:
+ case 88200:
+ mclk = 11289600;
+ break;
+ case 8000:
+ case 16000:
+ case 32000:
+ case 48000:
+ case 64000:
+ case 96000:
+ mclk = 12288000;
+ break;
+ default:
+ return -EINVAL;
+ }
+ min_mclk = 64 * srate;
+
+ err = tegra_asoc_utils_set_rate(&machine->util_data, srate, mclk);
+ if (err < 0) {
+ if (!(machine->util_data.set_mclk % min_mclk))
+ mclk = machine->util_data.set_mclk;
+ else {
+ dev_err(card->dev, "Can't configure clocks\n");
+ return err;
+ }
+ }
+
+ tegra_asoc_utils_lock_clk_rate(&machine->util_data, 1);
+
+ err = snd_soc_dai_set_fmt(cpu_dai,
+ SND_SOC_DAIFMT_DSP_A |
+ SND_SOC_DAIFMT_NB_NF |
+ SND_SOC_DAIFMT_CBS_CFS);
+ if (err < 0) {
+ dev_err(card->dev, "cpu_dai fmt not set\n");
+ return err;
+ }
+
+#ifdef CONFIG_ARCH_TEGRA_2x_SOC
+ err = tegra20_das_connect_dac_to_dap(TEGRA20_DAS_DAP_SEL_DAC2,
+ TEGRA20_DAS_DAP_ID_4);
+ if (err < 0) {
+ dev_err(card->dev, "failed to set dac-dap path\n");
+ return err;
+ }
+
+ err = tegra20_das_connect_dap_to_dac(TEGRA20_DAS_DAP_ID_4,
+ TEGRA20_DAS_DAP_SEL_DAC2);
+ if (err < 0) {
+ dev_err(card->dev, "failed to set dac-dap path\n");
+ return err;
+ }
+#endif
return 0;
}
@@ -197,6 +286,11 @@ static struct snd_soc_ops tegra_wm8903_ops = {
.hw_free = tegra_hw_free,
};
+static struct snd_soc_ops tegra_wm8903_bt_sco_ops = {
+ .hw_params = tegra_bt_sco_hw_params,
+ .hw_free = tegra_hw_free,
+};
+
static struct snd_soc_ops tegra_spdif_ops = {
.hw_params = tegra_spdif_hw_params,
.hw_free = tegra_hw_free,
@@ -522,7 +616,18 @@ static struct snd_soc_dai_link tegra_wm8903_dai[] = {
.cpu_dai_name = "tegra20-spdif",
.codec_dai_name = "dit-hifi",
.ops = &tegra_spdif_ops,
- }
+ },
+#ifdef CONFIG_ARCH_TEGRA_2x_SOC
+ {
+ .name = "BT-SCO",
+ .stream_name = "BT SCO PCM",
+ .codec_name = "spdif-dit.1",
+ .platform_name = "tegra-pcm-audio",
+ .cpu_dai_name = "tegra20-i2s.1",
+ .codec_dai_name = "dit-hifi",
+ .ops = &tegra_wm8903_bt_sco_ops,
+ },
+#endif
};
static struct snd_soc_card snd_soc_tegra_wm8903 = {