diff options
author | Takashi Iwai <tiwai@suse.de> | 2009-10-03 18:31:22 +0200 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2009-10-03 18:31:22 +0200 |
commit | a1cb9cd69750d6d62251393738efc02d252b67d3 (patch) | |
tree | 5c68b23180e6ca127d1048cdbf723ca447551123 /sound | |
parent | 08d1e635089f41e28fec644a8620a0e8d66b1235 (diff) | |
parent | 834eb6c599a8efa1fe9b77d469562e0c78c876e1 (diff) |
Merge branch 'fix/asoc' into for-linus
Diffstat (limited to 'sound')
-rw-r--r-- | sound/soc/blackfin/Kconfig | 98 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-ac97.c | 8 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-ac97.h | 2 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-i2s.c | 30 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-i2s.h | 2 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-sport.c | 2 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-tdm.c | 8 | ||||
-rw-r--r-- | sound/soc/codecs/ad1836.c | 3 | ||||
-rw-r--r-- | sound/soc/codecs/ad1938.c | 2 | ||||
-rw-r--r-- | sound/soc/codecs/wm8753.c | 1 | ||||
-rw-r--r-- | sound/soc/davinci/davinci-i2s.c | 37 | ||||
-rw-r--r-- | sound/soc/davinci/davinci-mcasp.c | 104 | ||||
-rw-r--r-- | sound/soc/davinci/davinci-mcasp.h | 7 | ||||
-rw-r--r-- | sound/soc/davinci/davinci-pcm.c | 13 | ||||
-rw-r--r-- | sound/soc/davinci/davinci-pcm.h | 1 | ||||
-rw-r--r-- | sound/soc/pxa/Kconfig | 2 |
16 files changed, 155 insertions, 165 deletions
diff --git a/sound/soc/blackfin/Kconfig b/sound/soc/blackfin/Kconfig index ac927ffdc96..97f1a251e44 100644 --- a/sound/soc/blackfin/Kconfig +++ b/sound/soc/blackfin/Kconfig @@ -7,15 +7,6 @@ config SND_BF5XX_I2S mode (supports single stereo In/Out). You will also need to select the audio interfaces to support below. -config SND_BF5XX_TDM - tristate "SoC I2S(TDM mode) Audio for the ADI BF5xx chip" - depends on (BLACKFIN && SND_SOC) - help - Say Y or M if you want to add support for codecs attached to - the Blackfin SPORT (synchronous serial ports) interface in TDM - mode. - You will also need to select the audio interfaces to support below. - config SND_BF5XX_SOC_SSM2602 tristate "SoC SSM2602 Audio support for BF52x ezkit" depends on SND_BF5XX_I2S @@ -41,6 +32,31 @@ config SND_BFIN_AD73311_SE Enter the GPIO used to control AD73311's SE pin. Acceptable values are 0 to 7 +config SND_BF5XX_TDM + tristate "SoC I2S(TDM mode) Audio for the ADI BF5xx chip" + depends on (BLACKFIN && SND_SOC) + help + Say Y or M if you want to add support for codecs attached to + the Blackfin SPORT (synchronous serial ports) interface in TDM + mode. + You will also need to select the audio interfaces to support below. + +config SND_BF5XX_SOC_AD1836 + tristate "SoC AD1836 Audio support for BF5xx" + depends on SND_BF5XX_TDM + select SND_BF5XX_SOC_TDM + select SND_SOC_AD1836 + help + Say Y if you want to add support for SoC audio on BF5xx STAMP/EZKIT. + +config SND_BF5XX_SOC_AD1938 + tristate "SoC AD1938 Audio support for Blackfin" + depends on SND_BF5XX_TDM + select SND_BF5XX_SOC_TDM + select SND_SOC_AD1938 + help + Say Y if you want to add support for AD1938 codec on Blackfin. + config SND_BF5XX_AC97 tristate "SoC AC97 Audio for the ADI BF5xx chip" depends on BLACKFIN @@ -71,6 +87,30 @@ config SND_BF5XX_MULTICHAN_SUPPORT Say y if you want AC97 driver to support up to 5.1 channel audio. this mode will consume much more memory for DMA. +config SND_BF5XX_HAVE_COLD_RESET + bool "BOARD has COLD Reset GPIO" + depends on SND_BF5XX_AC97 + default y if BFIN548_EZKIT + default n if !BFIN548_EZKIT + +config SND_BF5XX_RESET_GPIO_NUM + int "Set a GPIO for cold reset" + depends on SND_BF5XX_HAVE_COLD_RESET + range 0 159 + default 19 if BFIN548_EZKIT + default 5 if BFIN537_STAMP + default 0 + help + Set the correct GPIO for RESET the sound chip. + +config SND_BF5XX_SOC_AD1980 + tristate "SoC AD1980/1 Audio support for BF5xx" + depends on SND_BF5XX_AC97 + select SND_BF5XX_SOC_AC97 + select SND_SOC_AD1980 + help + Say Y if you want to add support for SoC audio on BF5xx STAMP/EZKIT. + config SND_BF5XX_SOC_SPORT tristate @@ -88,30 +128,6 @@ config SND_BF5XX_SOC_AC97 select SND_SOC_AC97_BUS select SND_BF5XX_SOC_SPORT -config SND_BF5XX_SOC_AD1836 - tristate "SoC AD1836 Audio support for BF5xx" - depends on SND_BF5XX_TDM - select SND_BF5XX_SOC_TDM - select SND_SOC_AD1836 - help - Say Y if you want to add support for SoC audio on BF5xx STAMP/EZKIT. - -config SND_BF5XX_SOC_AD1980 - tristate "SoC AD1980/1 Audio support for BF5xx" - depends on SND_BF5XX_AC97 - select SND_BF5XX_SOC_AC97 - select SND_SOC_AD1980 - help - Say Y if you want to add support for SoC audio on BF5xx STAMP/EZKIT. - -config SND_BF5XX_SOC_AD1938 - tristate "SoC AD1938 Audio support for Blackfin" - depends on SND_BF5XX_TDM - select SND_BF5XX_SOC_TDM - select SND_SOC_AD1938 - help - Say Y if you want to add support for AD1938 codec on Blackfin. - config SND_BF5XX_SPORT_NUM int "Set a SPORT for Sound chip" depends on (SND_BF5XX_I2S || SND_BF5XX_AC97 || SND_BF5XX_TDM) @@ -120,19 +136,3 @@ config SND_BF5XX_SPORT_NUM default 0 help Set the correct SPORT for sound chip. - -config SND_BF5XX_HAVE_COLD_RESET - bool "BOARD has COLD Reset GPIO" - depends on SND_BF5XX_AC97 - default y if BFIN548_EZKIT - default n if !BFIN548_EZKIT - -config SND_BF5XX_RESET_GPIO_NUM - int "Set a GPIO for cold reset" - depends on SND_BF5XX_HAVE_COLD_RESET - range 0 159 - default 19 if BFIN548_EZKIT - default 5 if BFIN537_STAMP - default 0 - help - Set the correct GPIO for RESET the sound chip. diff --git a/sound/soc/blackfin/bf5xx-ac97.c b/sound/soc/blackfin/bf5xx-ac97.c index 2758b9017a7..e6932297873 100644 --- a/sound/soc/blackfin/bf5xx-ac97.c +++ b/sound/soc/blackfin/bf5xx-ac97.c @@ -277,7 +277,11 @@ static int bf5xx_ac97_resume(struct snd_soc_dai *dai) if (!dai->active) return 0; +#if defined(CONFIG_SND_BF5XX_MULTICHAN_SUPPORT) + ret = sport_set_multichannel(sport, 16, 0x3FF, 1); +#else ret = sport_set_multichannel(sport, 16, 0x1F, 1); +#endif if (ret) { pr_err("SPORT is busy!\n"); return -EBUSY; @@ -334,7 +338,11 @@ static int bf5xx_ac97_probe(struct platform_device *pdev, goto sport_err; } /*SPORT works in TDM mode to simulate AC97 transfers*/ +#if defined(CONFIG_SND_BF5XX_MULTICHAN_SUPPORT) + ret = sport_set_multichannel(sport_handle, 16, 0x3FF, 1); +#else ret = sport_set_multichannel(sport_handle, 16, 0x1F, 1); +#endif if (ret) { pr_err("SPORT is busy!\n"); ret = -EBUSY; diff --git a/sound/soc/blackfin/bf5xx-ac97.h b/sound/soc/blackfin/bf5xx-ac97.h index 3f2a911fe0c..a1f97dd809d 100644 --- a/sound/soc/blackfin/bf5xx-ac97.h +++ b/sound/soc/blackfin/bf5xx-ac97.h @@ -1,5 +1,5 @@ /* - * linux/sound/arm/bf5xx-ac97.h + * sound/soc/blackfin/bf5xx-ac97.h * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as diff --git a/sound/soc/blackfin/bf5xx-i2s.c b/sound/soc/blackfin/bf5xx-i2s.c index 876abade27e..084b68884ad 100644 --- a/sound/soc/blackfin/bf5xx-i2s.c +++ b/sound/soc/blackfin/bf5xx-i2s.c @@ -77,12 +77,12 @@ static struct sport_param sport_params[2] = { * TFS. When Port G is selected and EMAC then there is a conflict between * the PHY interrupt line and TFS. Current settings prevent the conflict * by ignoring the TFS pin when Port G is selected. This allows both - * ssm2602 using Port G and EMAC concurrently. + * codecs and EMAC using Port G concurrently. */ -#ifdef CONFIG_BF527_SPORT0_PORTF -#define LOCAL_SPORT0_TFS (P_SPORT0_TFS) -#else +#ifdef CONFIG_BF527_SPORT0_PORTG #define LOCAL_SPORT0_TFS (0) +#else +#define LOCAL_SPORT0_TFS (P_SPORT0_TFS) #endif static u16 sport_req[][7] = { {P_SPORT0_DTPRI, P_SPORT0_TSCLK, P_SPORT0_RFS, @@ -227,7 +227,8 @@ static int bf5xx_i2s_probe(struct platform_device *pdev, return 0; } -static void bf5xx_i2s_remove(struct snd_soc_dai *dai) +static void bf5xx_i2s_remove(struct platform_device *pdev, + struct snd_soc_dai *dai) { pr_debug("%s enter\n", __func__); peripheral_free_list(&sport_req[sport_num][0]); @@ -236,36 +237,31 @@ static void bf5xx_i2s_remove(struct snd_soc_dai *dai) #ifdef CONFIG_PM static int bf5xx_i2s_suspend(struct snd_soc_dai *dai) { - struct sport_device *sport = - (struct sport_device *)dai->private_data; pr_debug("%s : sport %d\n", __func__, dai->id); - if (!dai->active) - return 0; + if (dai->capture.active) - sport_rx_stop(sport); + sport_rx_stop(sport_handle); if (dai->playback.active) - sport_tx_stop(sport); + sport_tx_stop(sport_handle); return 0; } static int bf5xx_i2s_resume(struct snd_soc_dai *dai) { int ret; - struct sport_device *sport = - (struct sport_device *)dai->private_data; pr_debug("%s : sport %d\n", __func__, dai->id); - if (!dai->active) - return 0; - ret = sport_config_rx(sport, RFSR | RCKFE, RSFSE|0x1f, 0, 0); + ret = sport_config_rx(sport_handle, bf5xx_i2s.rcr1, + bf5xx_i2s.rcr2, 0, 0); if (ret) { pr_err("SPORT is busy!\n"); return -EBUSY; } - ret = sport_config_tx(sport, TFSR | TCKFE, TSFSE|0x1f, 0, 0); + ret = sport_config_tx(sport_handle, bf5xx_i2s.tcr1, + bf5xx_i2s.tcr2, 0, 0); if (ret) { pr_err("SPORT is busy!\n"); return -EBUSY; diff --git a/sound/soc/blackfin/bf5xx-i2s.h b/sound/soc/blackfin/bf5xx-i2s.h index 7107d1a0b06..264ecdcba35 100644 --- a/sound/soc/blackfin/bf5xx-i2s.h +++ b/sound/soc/blackfin/bf5xx-i2s.h @@ -1,5 +1,5 @@ /* - * linux/sound/arm/bf5xx-i2s.h + * sound/soc/blackfin/bf5xx-i2s.h * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as diff --git a/sound/soc/blackfin/bf5xx-sport.c b/sound/soc/blackfin/bf5xx-sport.c index 469ce7fab20..99051ff0954 100644 --- a/sound/soc/blackfin/bf5xx-sport.c +++ b/sound/soc/blackfin/bf5xx-sport.c @@ -326,7 +326,7 @@ static inline int sport_hook_tx_dummy(struct sport_device *sport) int sport_tx_start(struct sport_device *sport) { - unsigned flags; + unsigned long flags; pr_debug("%s: tx_run:%d, rx_run:%d\n", __func__, sport->tx_run, sport->rx_run); if (sport->tx_run) diff --git a/sound/soc/blackfin/bf5xx-tdm.c b/sound/soc/blackfin/bf5xx-tdm.c index 3096badf09a..ff546e91a22 100644 --- a/sound/soc/blackfin/bf5xx-tdm.c +++ b/sound/soc/blackfin/bf5xx-tdm.c @@ -78,12 +78,12 @@ static struct sport_param sport_params[2] = { * TFS. When Port G is selected and EMAC then there is a conflict between * the PHY interrupt line and TFS. Current settings prevent the conflict * by ignoring the TFS pin when Port G is selected. This allows both - * ssm2602 using Port G and EMAC concurrently. + * codecs and EMAC using Port G concurrently. */ -#ifdef CONFIG_BF527_SPORT0_PORTF -#define LOCAL_SPORT0_TFS (P_SPORT0_TFS) -#else +#ifdef CONFIG_BF527_SPORT0_PORTG #define LOCAL_SPORT0_TFS (0) +#else +#define LOCAL_SPORT0_TFS (P_SPORT0_TFS) #endif static u16 sport_req[][7] = { {P_SPORT0_DTPRI, P_SPORT0_TSCLK, P_SPORT0_RFS, diff --git a/sound/soc/codecs/ad1836.c b/sound/soc/codecs/ad1836.c index 01343dc984f..c48485f2c55 100644 --- a/sound/soc/codecs/ad1836.c +++ b/sound/soc/codecs/ad1836.c @@ -251,8 +251,7 @@ static int __devexit ad1836_spi_remove(struct spi_device *spi) static struct spi_driver ad1836_spi_driver = { .driver = { - .name = "ad1836-spi", - .bus = &spi_bus_type, + .name = "ad1836", .owner = THIS_MODULE, }, .probe = ad1836_spi_probe, diff --git a/sound/soc/codecs/ad1938.c b/sound/soc/codecs/ad1938.c index 9a049a1995a..34b30efc3cb 100644 --- a/sound/soc/codecs/ad1938.c +++ b/sound/soc/codecs/ad1938.c @@ -456,7 +456,6 @@ static int __devexit ad1938_spi_remove(struct spi_device *spi) static struct spi_driver ad1938_spi_driver = { .driver = { .name = "ad1938", - .bus = &spi_bus_type, .owner = THIS_MODULE, }, .probe = ad1938_spi_probe, @@ -515,6 +514,7 @@ static int ad1938_register(struct ad1938_priv *ad1938) codec->num_dai = 1; codec->write = ad1938_write_reg; codec->read = ad1938_read_reg_cache; + codec->set_bias_level = ad1938_set_bias_level; INIT_LIST_HEAD(&codec->dapm_widgets); INIT_LIST_HEAD(&codec->dapm_paths); diff --git a/sound/soc/codecs/wm8753.c b/sound/soc/codecs/wm8753.c index d80d414cfbb..5ad677ce80d 100644 --- a/sound/soc/codecs/wm8753.c +++ b/sound/soc/codecs/wm8753.c @@ -595,6 +595,7 @@ static const struct snd_soc_dapm_route audio_map[] = { /* Mono Capture mixer-mux */ {"Capture Right Mixer", "Stereo", "Capture Right Mux"}, + {"Capture Left Mixer", "Stereo", "Capture Left Mux"}, {"Capture Left Mixer", "Analogue Mix Left", "Capture Left Mux"}, {"Capture Left Mixer", "Analogue Mix Left", "Capture Right Mux"}, {"Capture Right Mixer", "Analogue Mix Right", "Capture Left Mux"}, diff --git a/sound/soc/davinci/davinci-i2s.c b/sound/soc/davinci/davinci-i2s.c index 12a6c549ee6..4ae70704802 100644 --- a/sound/soc/davinci/davinci-i2s.c +++ b/sound/soc/davinci/davinci-i2s.c @@ -97,22 +97,19 @@ enum { DAVINCI_MCBSP_WORD_32, }; -static struct davinci_pcm_dma_params davinci_i2s_pcm_out = { - .name = "I2S PCM Stereo out", -}; - -static struct davinci_pcm_dma_params davinci_i2s_pcm_in = { - .name = "I2S PCM Stereo in", -}; - struct davinci_mcbsp_dev { + /* + * dma_params must be first because rtd->dai->cpu_dai->private_data + * is cast to a pointer of an array of struct davinci_pcm_dma_params in + * davinci_pcm_open. + */ + struct davinci_pcm_dma_params dma_params[2]; void __iomem *base; #define MOD_DSP_A 0 #define MOD_DSP_B 1 int mode; u32 pcr; struct clk *clk; - struct davinci_pcm_dma_params *dma_params[2]; }; static inline void davinci_mcbsp_write_reg(struct davinci_mcbsp_dev *dev, @@ -215,14 +212,6 @@ static void davinci_mcbsp_stop(struct davinci_mcbsp_dev *dev, int playback) toggle_clock(dev, playback); } -static int davinci_i2s_startup(struct snd_pcm_substream *substream, - struct snd_soc_dai *cpu_dai) -{ - struct davinci_mcbsp_dev *dev = cpu_dai->private_data; - cpu_dai->dma_data = dev->dma_params[substream->stream]; - return 0; -} - #define DEFAULT_BITPERSAMPLE 16 static int davinci_i2s_set_dai_fmt(struct snd_soc_dai *cpu_dai, @@ -353,8 +342,9 @@ static int davinci_i2s_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) { - struct davinci_pcm_dma_params *dma_params = dai->dma_data; struct davinci_mcbsp_dev *dev = dai->private_data; + struct davinci_pcm_dma_params *dma_params = + &dev->dma_params[substream->stream]; struct snd_interval *i = NULL; int mcbsp_word_length; unsigned int rcr, xcr, srgr; @@ -472,7 +462,6 @@ static void davinci_i2s_shutdown(struct snd_pcm_substream *substream, #define DAVINCI_I2S_RATES SNDRV_PCM_RATE_8000_96000 static struct snd_soc_dai_ops davinci_i2s_dai_ops = { - .startup = davinci_i2s_startup, .shutdown = davinci_i2s_shutdown, .prepare = davinci_i2s_prepare, .trigger = davinci_i2s_trigger, @@ -534,12 +523,10 @@ static int davinci_i2s_probe(struct platform_device *pdev) dev->base = (void __iomem *)IO_ADDRESS(mem->start); - dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK] = &davinci_i2s_pcm_out; - dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK]->dma_addr = + dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK].dma_addr = (dma_addr_t)(io_v2p(dev->base) + DAVINCI_MCBSP_DXR_REG); - dev->dma_params[SNDRV_PCM_STREAM_CAPTURE] = &davinci_i2s_pcm_in; - dev->dma_params[SNDRV_PCM_STREAM_CAPTURE]->dma_addr = + dev->dma_params[SNDRV_PCM_STREAM_CAPTURE].dma_addr = (dma_addr_t)(io_v2p(dev->base) + DAVINCI_MCBSP_DRR_REG); /* first TX, then RX */ @@ -549,7 +536,7 @@ static int davinci_i2s_probe(struct platform_device *pdev) ret = -ENXIO; goto err_free_mem; } - dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK]->channel = res->start; + dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK].channel = res->start; res = platform_get_resource(pdev, IORESOURCE_DMA, 1); if (!res) { @@ -557,7 +544,7 @@ static int davinci_i2s_probe(struct platform_device *pdev) ret = -ENXIO; goto err_free_mem; } - dev->dma_params[SNDRV_PCM_STREAM_CAPTURE]->channel = res->start; + dev->dma_params[SNDRV_PCM_STREAM_CAPTURE].channel = res->start; davinci_i2s_dai.private_data = dev; ret = snd_soc_register_dai(&davinci_i2s_dai); diff --git a/sound/soc/davinci/davinci-mcasp.c b/sound/soc/davinci/davinci-mcasp.c index eca22d7829d..5d1f98a4c97 100644 --- a/sound/soc/davinci/davinci-mcasp.c +++ b/sound/soc/davinci/davinci-mcasp.c @@ -332,14 +332,6 @@ static inline void mcasp_set_ctl_reg(void __iomem *regs, u32 val) printk(KERN_ERR "GBLCTL write error\n"); } -static int davinci_mcasp_startup(struct snd_pcm_substream *substream, - struct snd_soc_dai *cpu_dai) -{ - struct davinci_audio_dev *dev = cpu_dai->private_data; - cpu_dai->dma_data = dev->dma_params[substream->stream]; - return 0; -} - static void mcasp_start_rx(struct davinci_audio_dev *dev) { mcasp_set_ctl_reg(dev->base + DAVINCI_MCASP_GBLCTLR_REG, RXHCLKRST); @@ -386,17 +378,17 @@ static void mcasp_start_tx(struct davinci_audio_dev *dev) static void davinci_mcasp_start(struct davinci_audio_dev *dev, int stream) { - if (stream == SNDRV_PCM_STREAM_PLAYBACK) + if (stream == SNDRV_PCM_STREAM_PLAYBACK) { + if (dev->txnumevt) /* enable FIFO */ + mcasp_set_bits(dev->base + DAVINCI_MCASP_WFIFOCTL, + FIFO_ENABLE); mcasp_start_tx(dev); - else + } else { + if (dev->rxnumevt) /* enable FIFO */ + mcasp_set_bits(dev->base + DAVINCI_MCASP_RFIFOCTL, + FIFO_ENABLE); mcasp_start_rx(dev); - - /* enable FIFO */ - if (dev->txnumevt) - mcasp_set_bits(dev->base + DAVINCI_MCASP_WFIFOCTL, FIFO_ENABLE); - - if (dev->rxnumevt) - mcasp_set_bits(dev->base + DAVINCI_MCASP_RFIFOCTL, FIFO_ENABLE); + } } static void mcasp_stop_rx(struct davinci_audio_dev *dev) @@ -413,17 +405,17 @@ static void mcasp_stop_tx(struct davinci_audio_dev *dev) static void davinci_mcasp_stop(struct davinci_audio_dev *dev, int stream) { - if (stream == SNDRV_PCM_STREAM_PLAYBACK) + if (stream == SNDRV_PCM_STREAM_PLAYBACK) { + if (dev->txnumevt) /* disable FIFO */ + mcasp_clr_bits(dev->base + DAVINCI_MCASP_WFIFOCTL, + FIFO_ENABLE); mcasp_stop_tx(dev); - else + } else { + if (dev->rxnumevt) /* disable FIFO */ + mcasp_clr_bits(dev->base + DAVINCI_MCASP_RFIFOCTL, + FIFO_ENABLE); mcasp_stop_rx(dev); - - /* disable FIFO */ - if (dev->txnumevt) - mcasp_clr_bits(dev->base + DAVINCI_MCASP_WFIFOCTL, FIFO_ENABLE); - - if (dev->rxnumevt) - mcasp_clr_bits(dev->base + DAVINCI_MCASP_RFIFOCTL, FIFO_ENABLE); + } } static int davinci_mcasp_set_dai_fmt(struct snd_soc_dai *cpu_dai, @@ -512,34 +504,49 @@ static int davinci_config_channel_size(struct davinci_audio_dev *dev, int channel_size) { u32 fmt = 0; + u32 mask, rotate; switch (channel_size) { case DAVINCI_AUDIO_WORD_8: fmt = 0x03; + rotate = 6; + mask = 0x000000ff; break; case DAVINCI_AUDIO_WORD_12: fmt = 0x05; + rotate = 5; + mask = 0x00000fff; break; case DAVINCI_AUDIO_WORD_16: fmt = 0x07; + rotate = 4; + mask = 0x0000ffff; break; case DAVINCI_AUDIO_WORD_20: fmt = 0x09; + rotate = 3; + mask = 0x000fffff; break; case DAVINCI_AUDIO_WORD_24: fmt = 0x0B; + rotate = 2; + mask = 0x00ffffff; break; case DAVINCI_AUDIO_WORD_28: fmt = 0x0D; + rotate = 1; + mask = 0x0fffffff; break; case DAVINCI_AUDIO_WORD_32: fmt = 0x0F; + rotate = 0; + mask = 0xffffffff; break; default: @@ -550,6 +557,13 @@ static int davinci_config_channel_size(struct davinci_audio_dev *dev, RXSSZ(fmt), RXSSZ(0x0F)); mcasp_mod_bits(dev->base + DAVINCI_MCASP_TXFMT_REG, TXSSZ(fmt), TXSSZ(0x0F)); + mcasp_mod_bits(dev->base + DAVINCI_MCASP_TXFMT_REG, TXROT(rotate), + TXROT(7)); + mcasp_mod_bits(dev->base + DAVINCI_MCASP_RXFMT_REG, RXROT(rotate), + RXROT(7)); + mcasp_set_reg(dev->base + DAVINCI_MCASP_TXMASK_REG, mask); + mcasp_set_reg(dev->base + DAVINCI_MCASP_RXMASK_REG, mask); + return 0; } @@ -638,7 +652,6 @@ static void davinci_hw_param(struct davinci_audio_dev *dev, int stream) printk(KERN_ERR "playback tdm slot %d not supported\n", dev->tdm_slots); - mcasp_set_reg(dev->base + DAVINCI_MCASP_TXMASK_REG, 0xFFFFFFFF); mcasp_clr_bits(dev->base + DAVINCI_MCASP_TXFMCTL_REG, FSXDUR); } else { /* bit stream is MSB first with no delay */ @@ -655,7 +668,6 @@ static void davinci_hw_param(struct davinci_audio_dev *dev, int stream) printk(KERN_ERR "capture tdm slot %d not supported\n", dev->tdm_slots); - mcasp_set_reg(dev->base + DAVINCI_MCASP_RXMASK_REG, 0xFFFFFFFF); mcasp_clr_bits(dev->base + DAVINCI_MCASP_RXFMCTL_REG, FSRDUR); } } @@ -700,7 +712,7 @@ static int davinci_mcasp_hw_params(struct snd_pcm_substream *substream, { struct davinci_audio_dev *dev = cpu_dai->private_data; struct davinci_pcm_dma_params *dma_params = - dev->dma_params[substream->stream]; + &dev->dma_params[substream->stream]; int word_length; u8 numevt; @@ -778,7 +790,6 @@ static int davinci_mcasp_trigger(struct snd_pcm_substream *substream, } static struct snd_soc_dai_ops davinci_mcasp_dai_ops = { - .startup = davinci_mcasp_startup, .trigger = davinci_mcasp_trigger, .hw_params = davinci_mcasp_hw_params, .set_fmt = davinci_mcasp_set_dai_fmt, @@ -829,20 +840,12 @@ static int davinci_mcasp_probe(struct platform_device *pdev) struct resource *mem, *ioarea, *res; struct snd_platform_data *pdata; struct davinci_audio_dev *dev; - int count = 0; int ret = 0; dev = kzalloc(sizeof(struct davinci_audio_dev), GFP_KERNEL); if (!dev) return -ENOMEM; - dma_data = kzalloc(sizeof(struct davinci_pcm_dma_params) * 2, - GFP_KERNEL); - if (!dma_data) { - ret = -ENOMEM; - goto err_release_dev; - } - mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (!mem) { dev_err(&pdev->dev, "no mem resource?\n"); @@ -877,11 +880,10 @@ static int davinci_mcasp_probe(struct platform_device *pdev) dev->txnumevt = pdata->txnumevt; dev->rxnumevt = pdata->rxnumevt; - dma_data[count].name = "I2S PCM Stereo out"; - dma_data[count].eventq_no = pdata->eventq_no; - dma_data[count].dma_addr = (dma_addr_t) (pdata->tx_dma_offset + + dma_data = &dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK]; + dma_data->eventq_no = pdata->eventq_no; + dma_data->dma_addr = (dma_addr_t) (pdata->tx_dma_offset + io_v2p(dev->base)); - dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK] = &dma_data[count]; /* first TX, then RX */ res = platform_get_resource(pdev, IORESOURCE_DMA, 0); @@ -890,13 +892,12 @@ static int davinci_mcasp_probe(struct platform_device *pdev) goto err_release_region; } - dma_data[count].channel = res->start; - count++; - dma_data[count].name = "I2S PCM Stereo in"; - dma_data[count].eventq_no = pdata->eventq_no; - dma_data[count].dma_addr = (dma_addr_t)(pdata->rx_dma_offset + + dma_data->channel = res->start; + + dma_data = &dev->dma_params[SNDRV_PCM_STREAM_CAPTURE]; + dma_data->eventq_no = pdata->eventq_no; + dma_data->dma_addr = (dma_addr_t)(pdata->rx_dma_offset + io_v2p(dev->base)); - dev->dma_params[SNDRV_PCM_STREAM_CAPTURE] = &dma_data[count]; res = platform_get_resource(pdev, IORESOURCE_DMA, 1); if (!res) { @@ -904,7 +905,7 @@ static int davinci_mcasp_probe(struct platform_device *pdev) goto err_release_region; } - dma_data[count].channel = res->start; + dma_data->channel = res->start; davinci_mcasp_dai[pdata->op_mode].private_data = dev; davinci_mcasp_dai[pdata->op_mode].dev = &pdev->dev; ret = snd_soc_register_dai(&davinci_mcasp_dai[pdata->op_mode]); @@ -916,8 +917,6 @@ static int davinci_mcasp_probe(struct platform_device *pdev) err_release_region: release_mem_region(mem->start, (mem->end - mem->start) + 1); err_release_data: - kfree(dma_data); -err_release_dev: kfree(dev); return ret; @@ -926,7 +925,6 @@ err_release_dev: static int davinci_mcasp_remove(struct platform_device *pdev) { struct snd_platform_data *pdata = pdev->dev.platform_data; - struct davinci_pcm_dma_params *dma_data; struct davinci_audio_dev *dev; struct resource *mem; @@ -939,8 +937,6 @@ static int davinci_mcasp_remove(struct platform_device *pdev) mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); release_mem_region(mem->start, (mem->end - mem->start) + 1); - dma_data = dev->dma_params[SNDRV_PCM_STREAM_PLAYBACK]; - kfree(dma_data); kfree(dev); return 0; diff --git a/sound/soc/davinci/davinci-mcasp.h b/sound/soc/davinci/davinci-mcasp.h index 554354c1cc2..9d179cc88f7 100644 --- a/sound/soc/davinci/davinci-mcasp.h +++ b/sound/soc/davinci/davinci-mcasp.h @@ -39,10 +39,15 @@ enum { }; struct davinci_audio_dev { + /* + * dma_params must be first because rtd->dai->cpu_dai->private_data + * is cast to a pointer of an array of struct davinci_pcm_dma_params in + * davinci_pcm_open. + */ + struct davinci_pcm_dma_params dma_params[2]; void __iomem *base; int sample_rate; struct clk *clk; - struct davinci_pcm_dma_params *dma_params[2]; unsigned int codec_fmt; /* McASP specific data */ diff --git a/sound/soc/davinci/davinci-pcm.c b/sound/soc/davinci/davinci-pcm.c index 091dacb78b4..359e99ec724 100644 --- a/sound/soc/davinci/davinci-pcm.c +++ b/sound/soc/davinci/davinci-pcm.c @@ -126,16 +126,9 @@ static void davinci_pcm_dma_irq(unsigned lch, u16 ch_status, void *data) static int davinci_pcm_dma_request(struct snd_pcm_substream *substream) { struct davinci_runtime_data *prtd = substream->runtime->private_data; - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct davinci_pcm_dma_params *dma_data = rtd->dai->cpu_dai->dma_data; struct edmacc_param p_ram; int ret; - if (!dma_data) - return -ENODEV; - - prtd->params = dma_data; - /* Request master DMA channel */ ret = edma_alloc_channel(prtd->params->channel, davinci_pcm_dma_irq, substream, @@ -244,6 +237,11 @@ static int davinci_pcm_open(struct snd_pcm_substream *substream) struct snd_pcm_runtime *runtime = substream->runtime; struct davinci_runtime_data *prtd; int ret = 0; + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct davinci_pcm_dma_params *pa = rtd->dai->cpu_dai->private_data; + struct davinci_pcm_dma_params *params = &pa[substream->stream]; + if (!params) + return -ENODEV; snd_soc_set_runtime_hwparams(substream, &davinci_pcm_hardware); /* ensure that buffer size is a multiple of period size */ @@ -257,6 +255,7 @@ static int davinci_pcm_open(struct snd_pcm_substream *substream) return -ENOMEM; spin_lock_init(&prtd->lock); + prtd->params = params; runtime->private_data = prtd; diff --git a/sound/soc/davinci/davinci-pcm.h b/sound/soc/davinci/davinci-pcm.h index 63d96253c73..8746606efc8 100644 --- a/sound/soc/davinci/davinci-pcm.h +++ b/sound/soc/davinci/davinci-pcm.h @@ -17,7 +17,6 @@ struct davinci_pcm_dma_params { - char *name; /* stream identifier */ int channel; /* sync dma channel ID */ unsigned short acnt; dma_addr_t dma_addr; /* device physical address for DMA */ diff --git a/sound/soc/pxa/Kconfig b/sound/soc/pxa/Kconfig index 6375b4ea525..dcb3181bb34 100644 --- a/sound/soc/pxa/Kconfig +++ b/sound/soc/pxa/Kconfig @@ -138,7 +138,7 @@ config SND_PXA2XX_SOC_MIOA701 config SND_PXA2XX_SOC_IMOTE2 tristate "SoC Audio support for IMote 2" - depends on SND_PXA2XX_SOC && MACH_INTELMOTE2 + depends on SND_PXA2XX_SOC && MACH_INTELMOTE2 && I2C select SND_PXA2XX_SOC_I2S select SND_SOC_WM8940 help |