aboutsummaryrefslogtreecommitdiffstats
path: root/sound
diff options
context:
space:
mode:
authorDaniel Mack <daniel@caiaq.de>2009-03-12 06:27:49 -0400
committerMark Brown <broonie@opensource.wolfsonmicro.com>2009-03-13 09:23:34 -0400
commit72d7466468b471f99cefae3c5f4a414bbbaa0bdd (patch)
treef5cee2480802bd31efa066eb65c2bc9dfe0b3d2a /sound
parent77dd7e17b86bd81b3638e01d784a72652071508b (diff)
ASoC: switch PXA SSP driver from network mode to PSP
This switches the pxa ssp port usage from network mode to PSP mode. Removed some comments and checks for configured TDM channels. A special case is added to support configuration where BCLK = 64fs. We need to do some black magic in this case which doesn't look nice but there is unfortunately no other option than that. Diagnosed-by: Tim Ruetz <tim@caiaq.de> Signed-off-by: Daniel Mack <daniel@caiaq.de> Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
Diffstat (limited to 'sound')
-rw-r--r--sound/soc/pxa/pxa-ssp.c44
1 files changed, 33 insertions, 11 deletions
diff --git a/sound/soc/pxa/pxa-ssp.c b/sound/soc/pxa/pxa-ssp.c
index d3fa6357a9f..4dd0d7c5722 100644
--- a/sound/soc/pxa/pxa-ssp.c
+++ b/sound/soc/pxa/pxa-ssp.c
@@ -558,18 +558,17 @@ static int pxa_ssp_set_dai_fmt(struct snd_soc_dai *cpu_dai,
558 558
559 switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { 559 switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
560 case SND_SOC_DAIFMT_I2S: 560 case SND_SOC_DAIFMT_I2S:
561 sscr0 |= SSCR0_MOD | SSCR0_PSP; 561 sscr0 |= SSCR0_PSP;
562 sscr1 |= SSCR1_RWOT | SSCR1_TRAIL; 562 sscr1 |= SSCR1_RWOT | SSCR1_TRAIL;
563 563
564 switch (fmt & SND_SOC_DAIFMT_INV_MASK) { 564 switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
565 case SND_SOC_DAIFMT_NB_NF: 565 case SND_SOC_DAIFMT_NB_NF:
566 sspsp |= SSPSP_FSRT;
567 break; 566 break;
568 case SND_SOC_DAIFMT_NB_IF: 567 case SND_SOC_DAIFMT_NB_IF:
569 sspsp |= SSPSP_SFRMP | SSPSP_FSRT; 568 sspsp |= SSPSP_SFRMP;
570 break; 569 break;
571 case SND_SOC_DAIFMT_IB_IF: 570 case SND_SOC_DAIFMT_IB_IF:
572 sspsp |= SSPSP_SFRMP; 571 sspsp |= SSPSP_SFRMP | SSPSP_SCMODE(3);
573 break; 572 break;
574 default: 573 default:
575 return -EINVAL; 574 return -EINVAL;
@@ -655,33 +654,56 @@ static int pxa_ssp_hw_params(struct snd_pcm_substream *substream,
655 sscr0 |= SSCR0_FPCKE; 654 sscr0 |= SSCR0_FPCKE;
656#endif 655#endif
657 sscr0 |= SSCR0_DataSize(16); 656 sscr0 |= SSCR0_DataSize(16);
658 /* use network mode (2 slots) for 16 bit stereo */
659 break; 657 break;
660 case SNDRV_PCM_FORMAT_S24_LE: 658 case SNDRV_PCM_FORMAT_S24_LE:
661 sscr0 |= (SSCR0_EDSS | SSCR0_DataSize(8)); 659 sscr0 |= (SSCR0_EDSS | SSCR0_DataSize(8));
662 /* we must be in network mode (2 slots) for 24 bit stereo */
663 break; 660 break;
664 case SNDRV_PCM_FORMAT_S32_LE: 661 case SNDRV_PCM_FORMAT_S32_LE:
665 sscr0 |= (SSCR0_EDSS | SSCR0_DataSize(16)); 662 sscr0 |= (SSCR0_EDSS | SSCR0_DataSize(16));
666 /* we must be in network mode (2 slots) for 32 bit stereo */
667 break; 663 break;
668 } 664 }
669 ssp_write_reg(ssp, SSCR0, sscr0); 665 ssp_write_reg(ssp, SSCR0, sscr0);
670 666
671 switch (priv->dai_fmt & SND_SOC_DAIFMT_FORMAT_MASK) { 667 switch (priv->dai_fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
672 case SND_SOC_DAIFMT_I2S: 668 case SND_SOC_DAIFMT_I2S:
673 /* Cleared when the DAI format is set */ 669 sspsp = ssp_read_reg(ssp, SSPSP);
674 sspsp = ssp_read_reg(ssp, SSPSP) | SSPSP_SFRMWDTH(width); 670
671 if (((sscr0 & SSCR0_SCR) == SSCR0_SerClkDiv(4)) &&
672 (width == 16)) {
673 /* This is a special case where the bitclk is 64fs
674 * and we're not dealing with 2*32 bits of audio
675 * samples.
676 *
677 * The SSP values used for that are all found out by
678 * trying and failing a lot; some of the registers
679 * needed for that mode are only available on PXA3xx.
680 */
681
682#ifdef CONFIG_PXA3xx
683 if (!cpu_is_pxa3xx())
684 return -EINVAL;
685
686 sspsp |= SSPSP_SFRMWDTH(width * 2);
687 sspsp |= SSPSP_SFRMDLY(width * 4);
688 sspsp |= SSPSP_EDMYSTOP(3);
689 sspsp |= SSPSP_DMYSTOP(3);
690 sspsp |= SSPSP_DMYSTRT(1);
691#else
692 return -EINVAL;
693#endif
694 } else
695 sspsp |= SSPSP_SFRMWDTH(width);
696
675 ssp_write_reg(ssp, SSPSP, sspsp); 697 ssp_write_reg(ssp, SSPSP, sspsp);
676 break; 698 break;
677 default: 699 default:
678 break; 700 break;
679 } 701 }
680 702
681 /* We always use a network mode so we always require TDM slots 703 /* When we use a network mode, we always require TDM slots
682 * - complain loudly and fail if they've not been set up yet. 704 * - complain loudly and fail if they've not been set up yet.
683 */ 705 */
684 if (!(ssp_read_reg(ssp, SSTSA) & 0xf)) { 706 if ((sscr0 & SSCR0_MOD) && !(ssp_read_reg(ssp, SSTSA) & 0xf)) {
685 dev_err(&ssp->pdev->dev, "No TDM timeslot configured\n"); 707 dev_err(&ssp->pdev->dev, "No TDM timeslot configured\n");
686 return -EINVAL; 708 return -EINVAL;
687 } 709 }