static int cs4271_put_deemph(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol) { struct snd_soc_codec *codec = snd_soc_kcontrol_codec(kcontrol); struct cs4271_private *cs4271 = snd_soc_codec_get_drvdata(codec); cs4271->deemph = ucontrol->value.integer.value[0]; return cs4271_set_deemph(codec); }
static int cs4271_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) { struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_codec *codec = rtd->codec; struct cs4271_private *cs4271 = snd_soc_codec_get_drvdata(codec); int i, ret; unsigned int ratio, val; cs4271->rate = params_rate(params); /* Configure DAC */ if (cs4271->rate < 50000) val = CS4271_MODE1_MODE_1X; else if (cs4271->rate < 100000) val = CS4271_MODE1_MODE_2X; else val = CS4271_MODE1_MODE_4X; ratio = cs4271->mclk / cs4271->rate; for (i = 0; i < CS4171_NR_RATIOS; i++) if ((cs4271_clk_tab[i].master == cs4271->master) && (cs4271_clk_tab[i].speed_mode == val) && (cs4271_clk_tab[i].ratio == ratio)) break; if (i == CS4171_NR_RATIOS) { dev_err(codec->dev, "Invalid sample rate\n"); return -EINVAL; } val |= cs4271_clk_tab[i].ratio_mask; ret = snd_soc_update_bits(codec, CS4271_MODE1, CS4271_MODE1_MODE_MASK | CS4271_MODE1_DIV_MASK, val); if (ret < 0) return ret; return cs4271_set_deemph(codec); }
static int cs4271_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) { struct snd_soc_codec *codec = dai->codec; struct cs4271_private *cs4271 = snd_soc_codec_get_drvdata(codec); int i, ret; unsigned int ratio, val; if (cs4271->enable_soft_reset) { /* * Put the codec in soft reset and back again in case it's not * currently streaming data. This way of bringing the codec in * sync to the current clocks is not explicitly documented in * the data sheet, but it seems to work fine, and in contrast * to a read hardware reset, we don't have to sync back all * registers every time. */ if ((substream->stream == SNDRV_PCM_STREAM_PLAYBACK && !dai->capture_active) || (substream->stream == SNDRV_PCM_STREAM_CAPTURE && !dai->playback_active)) { ret = regmap_update_bits(cs4271->regmap, CS4271_MODE2, CS4271_MODE2_PDN, CS4271_MODE2_PDN); if (ret < 0) return ret; ret = regmap_update_bits(cs4271->regmap, CS4271_MODE2, CS4271_MODE2_PDN, 0); if (ret < 0) return ret; } } cs4271->rate = params_rate(params); /* Configure DAC */ if (cs4271->rate < 50000) val = CS4271_MODE1_MODE_1X; else if (cs4271->rate < 100000) val = CS4271_MODE1_MODE_2X; else val = CS4271_MODE1_MODE_4X; ratio = cs4271->mclk / cs4271->rate; for (i = 0; i < CS4171_NR_RATIOS; i++) if ((cs4271_clk_tab[i].master == cs4271->master) && (cs4271_clk_tab[i].speed_mode == val) && (cs4271_clk_tab[i].ratio == ratio)) break; if (i == CS4171_NR_RATIOS) { dev_err(codec->dev, "Invalid sample rate\n"); return -EINVAL; } val |= cs4271_clk_tab[i].ratio_mask; ret = regmap_update_bits(cs4271->regmap, CS4271_MODE1, CS4271_MODE1_MODE_MASK | CS4271_MODE1_DIV_MASK, val); if (ret < 0) return ret; return cs4271_set_deemph(codec); }