Skip to content

Commit

Permalink
ASoC: Update WM9081 for tdm_slot() API change
Browse files Browse the repository at this point in the history
Store the TDM slot width then if it's set use that rather than the
sample size to calculate BCLK. Leave imposing constraints to the
core (which should do this but doesn't yet) or machine driver.

Also allow 0 TDM slots to be configure (for use when disabling TDM).

Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
  • Loading branch information
Mark Brown committed Aug 11, 2009
1 parent 1921bab commit e0026be
Showing 1 changed file with 35 additions and 25 deletions.
60 changes: 35 additions & 25 deletions sound/soc/codecs/wm9081.c
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,7 @@ struct wm9081_priv {
int master;
int fll_fref;
int fll_fout;
int tdm_width;
struct wm9081_retune_mobile_config *retune;
};

Expand Down Expand Up @@ -981,33 +982,37 @@ static int wm9081_hw_params(struct snd_pcm_substream *substream,
aif4 = snd_soc_read(codec, WM9081_AUDIO_INTERFACE_4);
aif4 &= ~WM9081_LRCLK_RATE_MASK;

/* What BCLK do we need? */
wm9081->fs = params_rate(params);
wm9081->bclk = 2 * wm9081->fs;
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
wm9081->bclk *= 16;
break;
case SNDRV_PCM_FORMAT_S20_3LE:
wm9081->bclk *= 20;
aif2 |= 0x4;
break;
case SNDRV_PCM_FORMAT_S24_LE:
wm9081->bclk *= 24;
aif2 |= 0x8;
break;
case SNDRV_PCM_FORMAT_S32_LE:
wm9081->bclk *= 32;
aif2 |= 0xc;
break;
default:
return -EINVAL;
}

if (aif1 & WM9081_AIFDAC_TDM_MODE_MASK) {
if (wm9081->tdm_width) {
/* If TDM is set up then that fixes our BCLK. */
int slots = ((aif1 & WM9081_AIFDAC_TDM_MODE_MASK) >>
WM9081_AIFDAC_TDM_MODE_SHIFT) + 1;
wm9081->bclk *= slots;

wm9081->bclk = wm9081->fs * wm9081->tdm_width * slots;
} else {
/* Otherwise work out a BCLK from the sample size */
wm9081->bclk = 2 * wm9081->fs;

switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
wm9081->bclk *= 16;
break;
case SNDRV_PCM_FORMAT_S20_3LE:
wm9081->bclk *= 20;
aif2 |= 0x4;
break;
case SNDRV_PCM_FORMAT_S24_LE:
wm9081->bclk *= 24;
aif2 |= 0x8;
break;
case SNDRV_PCM_FORMAT_S32_LE:
wm9081->bclk *= 32;
aif2 |= 0xc;
break;
default:
return -EINVAL;
}
}

dev_dbg(codec->dev, "Target BCLK is %dHz\n", wm9081->bclk);
Expand Down Expand Up @@ -1149,18 +1154,23 @@ static int wm9081_set_sysclk(struct snd_soc_dai *codec_dai,
return 0;
}

/* FIXME: Needs to handle slot_width */
static int wm9081_set_tdm_slot(struct snd_soc_dai *dai,
unsigned int tx_mask, unsigned int rx_mask, int slots, int slot_width)
{
struct snd_soc_codec *codec = dai->codec;
struct wm9081_priv *wm9081 = codec->private_data;
unsigned int aif1 = snd_soc_read(codec, WM9081_AUDIO_INTERFACE_1);

aif1 &= ~(WM9081_AIFDAC_TDM_SLOT_MASK | WM9081_AIFDAC_TDM_MODE_MASK);

if (slots < 1 || slots > 4)
if (slots < 0 || slots > 4)
return -EINVAL;

wm9081->tdm_width = slot_width;

if (slots == 0)
slots = 1;

aif1 |= (slots - 1) << WM9081_AIFDAC_TDM_MODE_SHIFT;

switch (rx_mask) {
Expand Down

0 comments on commit e0026be

Please sign in to comment.