summaryrefslogtreecommitdiff
path: root/sound
diff options
context:
space:
mode:
authorLiam Girdwood <lrg@slimlogic.co.uk>2011-05-31 09:23:02 +0100
committerAndy Green <andy.green@linaro.org>2011-05-31 11:04:32 +0100
commit6aa5e928cdb4c8d5f5036b40c0adcce3086ad0ef (patch)
treeb5f3a1bc2e519b330e0a0fca7d57e4f79f32ce1f /sound
parent8528812967c0f50815849abb9dc936d6a5473359 (diff)
ASoC: sdp4430: Add all ABE backend DAIs
SDP4430 implements the following DAI links: - SDP4430 Media: Frontend connecting MM_UL and MM_DL Supported backends are PDM_DL1, PDM_DL2, PDM_UL, BT_VX, MM_EXT, DMIC0, DMIC1 and DMIC2 - SDP4430 Media Capture: Frontend for MM_UL2 Supported backends are PDM_UL, BT_VX, MM_EXT, DMIC0, DMIC1 and DMIC2 - SDP4430 Voice: Frontend connecting VX_UL and VX_DL Supports all media backends - SDP4430 Tones Playback: Frontend for TONES_DL Supported backends are PDM_DL1, PDM_DL2, BT_VX and MM_EXT - SDP4430 Vibra Playback: Frontend for VIB_DL Only supported backend is PDM_VIB - SDP4430 MODEM: Frontend connecting MODEM with McBSP2 Supported backends are the same as in media links - SDP4430 Media LP: Frontend for MM_DL with ping-pong buffer. Supported backends are PDM_DL1, PDM_DL2, BT_VX and MM_EXT - HDMI: Frontend for HDMI - Legacy McBSP: Direct link between processor and MM_EXT (McBSP2) - Legacy McPDM: Direct link between processor and PDM_DL1 - Legacy DMIC: Direct link between DMIC0 and processor Change-Id: Ib3a8c844be5c4fa6f6b6a6371086f8e4a0e1fe7b Signed-off-by: Liam Girdwood <lrg@slimlogic.co.uk> Signed-off-by: Margarita Olaya Cabrera <magi.olaya@ti.com> Signed-off-by: Jorge Eduardo Candelaria <jorge.candelaria@ti.com> Signed-off-by: Misael Lopez Cruz <misael.lopez@ti.com> Signed-off-by: Chris Kelly <c-kelly@ti.com>
Diffstat (limited to 'sound')
-rw-r--r--sound/soc/omap/Kconfig5
-rw-r--r--sound/soc/omap/sdp4430.c520
2 files changed, 518 insertions, 7 deletions
diff --git a/sound/soc/omap/Kconfig b/sound/soc/omap/Kconfig
index 1bf8ea7f9fd..0b35ef38d83 100644
--- a/sound/soc/omap/Kconfig
+++ b/sound/soc/omap/Kconfig
@@ -110,8 +110,13 @@ config SND_OMAP_SOC_SDP3430
config SND_OMAP_SOC_SDP4430
tristate "SoC Audio support for Texas Instruments SDP4430"
depends on TWL4030_CORE && SND_OMAP_SOC && MACH_OMAP_4430SDP
+ select SND_OMAP_SOC_ABE
select SND_OMAP_SOC_MCPDM
select SND_SOC_TWL6040
+ select SND_OMAP_SOC_MCBSP
+ select SND_SOC_DMIC
+ select SND_OMAP_SOC_DMIC
+ select SND_OMAP_SOC_ABE_DSP
help
Say Y if you want to add support for SoC audio on Texas Instruments
SDP4430.
diff --git a/sound/soc/omap/sdp4430.c b/sound/soc/omap/sdp4430.c
index cacc3faa885..4a519a38b11 100644
--- a/sound/soc/omap/sdp4430.c
+++ b/sound/soc/omap/sdp4430.c
@@ -30,15 +30,22 @@
#include <plat/hardware.h>
#include <plat/mux.h>
-#include "mcpdm.h"
+#include "omap-mcpdm.h"
+#include "omap-abe.h"
#include "omap-pcm.h"
+#include "omap-mcbsp.h"
+#include "omap-dmic.h"
#include "../codecs/twl6040.h"
#define SDP4430_SND_DEV_ID 0
+#ifdef CONFIG_SND_OMAP_SOC_HDMI
+#include "omap-hdmi.h"
+#endif
+
static int twl6040_power_mode;
-static int sdp4430_hw_params(struct snd_pcm_substream *substream,
+static int sdp4430_mcpdm_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params)
{
struct snd_soc_pcm_runtime *rtd = substream->private_data;
@@ -64,8 +71,82 @@ static int sdp4430_hw_params(struct snd_pcm_substream *substream,
return ret;
}
-static struct snd_soc_ops sdp4430_ops = {
- .hw_params = sdp4430_hw_params,
+static struct snd_soc_ops sdp4430_mcpdm_ops = {
+ .hw_params = sdp4430_mcpdm_hw_params,
+};
+
+static int sdp4430_mcbsp_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;
+ int ret = 0;
+ unsigned int be_id;
+
+ be_id = rtd->dai_link->be_id;
+
+ if (be_id == OMAP_ABE_DAI_MM_FM) {
+ /* Set cpu DAI configuration */
+ ret = snd_soc_dai_set_fmt(cpu_dai,
+ SND_SOC_DAIFMT_I2S |
+ SND_SOC_DAIFMT_NB_NF |
+ SND_SOC_DAIFMT_CBM_CFM);
+ } else if (be_id == OMAP_ABE_DAI_BT_VX) {
+ ret = snd_soc_dai_set_fmt(cpu_dai,
+ SND_SOC_DAIFMT_DSP_B |
+ SND_SOC_DAIFMT_NB_IF |
+ SND_SOC_DAIFMT_CBM_CFM);
+ }
+
+ if (ret < 0) {
+ printk(KERN_ERR "can't set cpu DAI configuration\n");
+ return ret;
+ }
+
+ /*
+ * TODO: where does this clock come from (external source??) -
+ * do we need to enable it.
+ */
+ /* Set McBSP clock to external */
+ ret = snd_soc_dai_set_sysclk(cpu_dai, OMAP_MCBSP_SYSCLK_CLKS_FCLK,
+ 64 * params_rate(params),
+ SND_SOC_CLOCK_IN);
+ if (ret < 0) {
+ printk(KERN_ERR "can't set cpu system clock\n");
+ return ret;
+ }
+ return 0;
+}
+
+static struct snd_soc_ops sdp4430_mcbsp_ops = {
+ .hw_params = sdp4430_mcbsp_hw_params,
+};
+
+static int sdp4430_dmic_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;
+ int ret = 0;
+
+ ret = snd_soc_dai_set_sysclk(cpu_dai, OMAP_DMIC_SYSCLK_PAD_CLKS,
+ 19200000, SND_SOC_CLOCK_IN);
+ if (ret < 0) {
+ printk(KERN_ERR "can't set DMIC cpu system clock\n");
+ return ret;
+ }
+
+ ret = snd_soc_dai_set_clkdiv(cpu_dai, OMAP_DMIC_CLKDIV, 8);
+ if (ret < 0) {
+ printk(KERN_ERR "can't set DMIC cpu clock divider\n");
+ return ret;
+ }
+
+ return 0;
+}
+
+static struct snd_soc_ops sdp4430_dmic_ops = {
+ .hw_params = sdp4430_dmic_hw_params,
};
/* Headset jack */
@@ -529,14 +610,437 @@ static struct snd_soc_dai_link sdp4430_dai[] = {
.be_id = OMAP_ABE_DAI_DMIC2,
.ignore_suspend = 1,
},
->>>>>>> patched
+
+/* TODO: make this a separate BT CODEC driver or DUMMY */
+static struct snd_soc_dai_driver dai[] = {
+{
+ .name = "Bluetooth",
+ .playback = {
+ .stream_name = "Playback",
+ .channels_min = 1,
+ .channels_max = 2,
+ .rates = SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000 |
+ SNDRV_PCM_RATE_48000,
+ .formats = SNDRV_PCM_FMTBIT_S16_LE,
+ },
+ .capture = {
+ .stream_name = "Capture",
+ .channels_min = 1,
+ .channels_max = 2,
+ .rates = SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000 |
+ SNDRV_PCM_RATE_48000,
+ .formats = SNDRV_PCM_FMTBIT_S16_LE,
+ },
+},
+/* TODO: make this a separate FM CODEC driver or DUMMY */
+{
+ .name = "FM Digital",
+ .playback = {
+ .stream_name = "Playback",
+ .channels_min = 1,
+ .channels_max = 2,
+ .rates = SNDRV_PCM_RATE_48000,
+ .formats = SNDRV_PCM_FMTBIT_S16_LE,
+ },
+ .capture = {
+ .stream_name = "Capture",
+ .channels_min = 1,
+ .channels_max = 2,
+ .rates = SNDRV_PCM_RATE_48000,
+ .formats = SNDRV_PCM_FMTBIT_S16_LE,
+ },
+},
+{
+ .name = "HDMI",
+ .playback = {
+ .stream_name = "Playback",
+ .channels_min = 2,
+ .channels_max = 8,
+ .rates = SNDRV_PCM_RATE_48000,
+ .formats = SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S32_LE,
+ },
+},
+};
+
+static const char *mm1_be[] = {
+ OMAP_ABE_BE_PDM_DL1,
+ OMAP_ABE_BE_PDM_UL1,
+ OMAP_ABE_BE_PDM_DL2,
+ OMAP_ABE_BE_BT_VX,
+ OMAP_ABE_BE_MM_EXT0,
+ OMAP_ABE_BE_DMIC0,
+ OMAP_ABE_BE_DMIC1,
+ OMAP_ABE_BE_DMIC2,
+};
+
+static const char *mm2_be[] = {
+ OMAP_ABE_BE_PDM_UL1,
+ OMAP_ABE_BE_BT_VX,
+ OMAP_ABE_BE_MM_EXT0,
+ OMAP_ABE_BE_DMIC0,
+ OMAP_ABE_BE_DMIC1,
+ OMAP_ABE_BE_DMIC2,
+};
+
+static const char *tones_be[] = {
+ OMAP_ABE_BE_PDM_DL1,
+ OMAP_ABE_BE_PDM_DL2,
+ OMAP_ABE_BE_BT_VX,
+ OMAP_ABE_BE_MM_EXT0,
+};
+
+static const char *vib_be[] = {
+ OMAP_ABE_BE_PDM_VIB,
+};
+
+static const char *modem_be[] = {
+ OMAP_ABE_BE_PDM_DL1,
+ OMAP_ABE_BE_PDM_UL1,
+ OMAP_ABE_BE_PDM_DL2,
+ OMAP_ABE_BE_BT_VX,
+ OMAP_ABE_BE_DMIC0,
+ OMAP_ABE_BE_DMIC1,
+ OMAP_ABE_BE_DMIC2,
+};
+
+static const char *mm_lp_be[] = {
+ OMAP_ABE_BE_PDM_DL1,
+ OMAP_ABE_BE_PDM_DL2,
+ OMAP_ABE_BE_BT_VX,
+ OMAP_ABE_BE_MM_EXT0,
+};
+
+/* Digital audio interface glue - connects codec <--> CPU */
+static struct snd_soc_dai_link sdp4430_dai[] = {
+
+/*
+ * Frontend DAIs - i.e. userspace visible interfaces (ALSA PCMs)
+ */
+
+ {
+ .name = "SDP4430 Media",
+ .stream_name = "Multimedia",
+
+ /* ABE components - MM-UL & MM_DL */
+ .cpu_dai_name = "MultiMedia1",
+ .platform_name = "omap-pcm-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = mm1_be,
+ .num_be = ARRAY_SIZE(mm1_be),
+ .fe_playback_channels = 2,
+ .fe_capture_channels = 8,
+ },
+ {
+ .name = "SDP4430 Media Capture",
+ .stream_name = "Multimedia Capture",
+
+ /* ABE components - MM-UL2 */
+ .cpu_dai_name = "MultiMedia2",
+ .platform_name = "omap-pcm-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = mm2_be,
+ .num_be = ARRAY_SIZE(mm2_be),
+ .fe_capture_channels = 2,
+ },
+ {
+ .name = "SDP4430 Voice",
+ .stream_name = "Voice",
+
+ /* ABE components - VX-UL & VX-DL */
+ .cpu_dai_name = "Voice",
+ .platform_name = "omap-pcm-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = mm1_be,
+ .num_be = ARRAY_SIZE(mm1_be),
+ .fe_playback_channels = 2,
+ .fe_capture_channels = 2,
+ },
+ {
+ .name = "SDP4430 Tones Playback",
+ .stream_name = "Tone Playback",
+
+ /* ABE components - TONES_DL */
+ .cpu_dai_name = "Tones",
+ .platform_name = "omap-pcm-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = tones_be,
+ .num_be = ARRAY_SIZE(tones_be),
+ .fe_playback_channels = 2,
+ },
+ {
+ .name = "SDP4430 Vibra Playback",
+ .stream_name = "VIB-DL",
+
+ .cpu_dai_name = "Vibra",
+ .platform_name = "omap-pcm-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = vib_be,
+ .num_be = ARRAY_SIZE(vib_be),
+ .fe_playback_channels = 2,
+ },
+ {
+ .name = "SDP4430 MODEM",
+ .stream_name = "MODEM",
+
+ /* ABE components - MODEM <-> McBSP2 */
+ .cpu_dai_name = "MODEM",
+ .platform_name = "omap-aess-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = modem_be,
+ .num_be = ARRAY_SIZE(modem_be),
+ .fe_playback_channels = 2,
+ .fe_capture_channels = 2,
+ },
+ {
+ .name = "SDP4430 Media LP",
+ .stream_name = "Multimedia",
+
+ /* ABE components - MM-DL (mmap) */
+ .cpu_dai_name = "MultiMedia1 LP",
+ .platform_name = "omap-aess-audio",
+
+ .dynamic = 1, /* BE is dynamic */
+ .supported_be = mm_lp_be,
+ .num_be = ARRAY_SIZE(mm_lp_be),
+ .fe_playback_channels = 2,
+ },
+#ifdef CONFIG_SND_OMAP_SOC_HDMI
+ {
+ .name = "hdmi",
+ .stream_name = "HDMI",
+
+ .cpu_dai_name = "hdmi-dai",
+ .platform_name = "omap-pcm-audio",
+
+ /* HDMI*/
+ .codec_dai_name = "HDMI",
+
+ .no_codec = 1,
+ },
+#endif
+ {
+ .name = "Legacy McBSP",
+ .stream_name = "Multimedia",
+
+ /* ABE components - MCBSP2 - MM-EXT */
+ .cpu_dai_name = "omap-mcbsp-dai.1",
+ .platform_name = "omap-pcm-audio",
+
+ /* FM */
+ .codec_dai_name = "FM Digital",
+
+ .no_codec = 1, /* TODO: have a dummy CODEC */
+ .ops = &sdp4430_mcbsp_ops,
+ },
+ {
+ .name = "Legacy McPDM",
+ .stream_name = "Headset Playback",
+
+ /* ABE components - DL1 */
+ .cpu_dai_name = "mcpdm-dl",
+ .platform_name = "omap-pcm-audio",
+
+ /* Phoenix - DL1 DAC */
+ .codec_dai_name = "twl6040-dl1",
+ .codec_name = "twl6040-codec",
+
+ .ops = &sdp4430_mcpdm_ops,
+ },
+ {
+ .name = "Legacy DMIC",
+ .stream_name = "DMIC Capture",
+
+ /* ABE components - DMIC0 */
+ .cpu_dai_name = "omap-dmic-dai-0",
+ .platform_name = "omap-pcm-audio",
+
+ /* DMIC codec */
+ .codec_dai_name = "dmic-hifi",
+ .codec_name = "dmic-codec.0",
+
+ .ops = &sdp4430_dmic_ops,
+ },
+
+/*
+ * Backend DAIs - i.e. dynamically matched interfaces, invisible to userspace.
+ * Matched to above interfaces at runtime, based upon use case.
+ */
+
+ {
+ .name = OMAP_ABE_BE_PDM_DL1,
+ .stream_name = "HS Playback",
+
+ /* ABE components - DL1 */
+ .cpu_dai_name = "mcpdm-dl1",
+ .platform_name = "omap-aess-audio",
+
+ /* Phoenix - DL1 DAC */
+ .codec_dai_name = "twl6040-dl1",
+ .codec_name = "twl6040-codec",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .init = sdp4430_twl6040_init,
+ .ops = &sdp4430_mcpdm_ops,
+ .be_id = OMAP_ABE_DAI_PDM_DL1,
+ },
+ {
+ .name = OMAP_ABE_BE_PDM_UL1,
+ .stream_name = "Analog Capture",
+
+ /* ABE components - UL1 */
+ .cpu_dai_name = "mcpdm-ul1",
+ .platform_name = "omap-aess-audio",
+
+ /* Phoenix - UL ADC */
+ .codec_dai_name = "twl6040-ul",
+ .codec_name = "twl6040-codec",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .ops = &sdp4430_mcpdm_ops,
+ .be_id = OMAP_ABE_DAI_PDM_UL,
+ },
+ {
+ .name = OMAP_ABE_BE_PDM_DL2,
+ .stream_name = "HF Playback",
+
+ /* ABE components - DL2 */
+ .cpu_dai_name = "mcpdm-dl2",
+ .platform_name = "omap-aess-audio",
+
+ /* Phoenix - DL2 DAC */
+ .codec_dai_name = "twl6040-dl2",
+ .codec_name = "twl6040-codec",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .ops = &sdp4430_mcpdm_ops,
+ .be_id = OMAP_ABE_DAI_PDM_DL2,
+ },
+ {
+ .name = OMAP_ABE_BE_PDM_VIB,
+ .stream_name = "Vibra",
+
+ /* ABE components - VIB1 DL */
+ .cpu_dai_name = "mcpdm-vib",
+ .platform_name = "omap-aess-audio",
+
+ /* Phoenix - PDM to PWM */
+ .codec_dai_name = "twl6040-vib",
+ .codec_name = "twl6040-codec",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .ops = &sdp4430_mcpdm_ops,
+ .be_id = OMAP_ABE_DAI_PDM_VIB,
+ },
+ {
+ .name = OMAP_ABE_BE_BT_VX,
+ .stream_name = "BT",
+
+ /* ABE components - MCBSP1 - BT-VX */
+ .cpu_dai_name = "omap-mcbsp-dai.0",
+ .platform_name = "omap-aess-audio",
+
+ /* Bluetooth */
+ .codec_dai_name = "Bluetooth",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .no_codec = 1, /* TODO: have a dummy CODEC */
+ .ops = &sdp4430_mcbsp_ops,
+ .be_id = OMAP_ABE_DAI_BT_VX,
+ },
+ {
+ .name = OMAP_ABE_BE_MM_EXT0,
+ .stream_name = "FM",
+
+ /* ABE components - MCBSP2 - MM-EXT */
+ .cpu_dai_name = "omap-mcbsp-dai.1",
+ .platform_name = "omap-aess-audio",
+
+ /* FM */
+ .codec_dai_name = "FM Digital",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .no_codec = 1, /* TODO: have a dummy CODEC */
+ .ops = &sdp4430_mcbsp_ops,
+ .be_id = OMAP_ABE_DAI_MM_FM,
+ },
+ {
+ .name = OMAP_ABE_BE_MM_EXT1,
+ .stream_name = "MODEM",
+
+ /* ABE components - MCBSP2 - MM-EXT */
+ .cpu_dai_name = "omap-mcbsp-dai.1",
+ .platform_name = "omap-aess-audio",
+
+ /* MODEM */
+ .codec_dai_name = "MODEM",
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .no_codec = 1, /* TODO: have a dummy CODEC */
+ .ops = &sdp4430_mcbsp_ops,
+ .be_id = OMAP_ABE_DAI_MODEM,
+ },
+ {
+ .name = OMAP_ABE_BE_DMIC0,
+ .stream_name = "DMIC0",
+
+ /* ABE components - DMIC UL 1 */
+ .cpu_dai_name = "omap-dmic-abe-dai-0",
+ .platform_name = "omap-aess-audio",
+
+ /* DMIC 0 */
+ .codec_dai_name = "dmic-hifi",
+ .codec_name = "dmic-codec.0",
+ .ops = &sdp4430_dmic_ops,
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .be_id = OMAP_ABE_DAI_DMIC0,
+ },
+ {
+ .name = OMAP_ABE_BE_DMIC1,
+ .stream_name = "DMIC1",
+
+ /* ABE components - DMIC UL 1 */
+ .cpu_dai_name = "omap-dmic-abe-dai-1",
+ .platform_name = "omap-aess-audio",
+
+ /* DMIC 1 */
+ .codec_dai_name = "dmic-hifi",
+ .codec_name = "dmic-codec.1",
+ .ops = &sdp4430_dmic_ops,
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .be_id = OMAP_ABE_DAI_DMIC1,
+ },
+ {
+ .name = OMAP_ABE_BE_DMIC2,
+ .stream_name = "DMIC2",
+
+ /* ABE components - DMIC UL 2 */
+ .cpu_dai_name = "omap-dmic-abe-dai-2",
+ .platform_name = "omap-aess-audio",
+
+ /* DMIC 2 */
+ .codec_dai_name = "dmic-hifi",
+ .codec_name = "dmic-codec.2",
+ .ops = &sdp4430_dmic_ops,
+
+ .no_pcm = 1, /* don't create ALSA pcm for this */
+ .be_id = OMAP_ABE_DAI_DMIC2,
+ },
};
/* Audio machine driver */
static struct snd_soc_card snd_soc_sdp4430 = {
.name = "SDP4430",
- .dai_link = &sdp4430_dai,
- .num_links = 1,
+ .long_name = "TI OMAP4 SDP4430 Board",
+ .dai_link = sdp4430_dai,
+ .num_links = ARRAY_SIZE(sdp4430_dai),
};
static struct platform_device *sdp4430_snd_device;
@@ -556,6 +1060,8 @@ static int __init sdp4430_soc_init(void)
return -ENOMEM;
}
+ snd_soc_register_dais(&sdp4430_snd_device->dev, dai, ARRAY_SIZE(dai));
+
platform_set_drvdata(sdp4430_snd_device, &snd_soc_sdp4430);
ret = platform_device_add(sdp4430_snd_device);