For correct operation of the digital filtering and other processing on the WM8741, the user must ensure the correct value of OSR[1:0] is set at all times.[1] Hence, depending the selected sampling rate, set the OSR (over- sampling rate) mode in hw_params().
References: [1] https://d3uzseaevmutz1.cloudfront.net/pubs/proDatasheet/WM8741_v4.3.pdf "WM8741 Data Sheet"
Signed-off-by: Sergej Sawazki sergej@taudac.com --- sound/soc/codecs/wm8741.c | 8 ++++++++ 1 file changed, 8 insertions(+)
diff --git a/sound/soc/codecs/wm8741.c b/sound/soc/codecs/wm8741.c index d552a8a..7e8a7fe 100644 --- a/sound/soc/codecs/wm8741.c +++ b/sound/soc/codecs/wm8741.c @@ -197,6 +197,7 @@ static int wm8741_hw_params(struct snd_pcm_substream *substream, struct snd_soc_codec *codec = dai->codec; struct wm8741_priv *wm8741 = snd_soc_codec_get_drvdata(codec); u16 iface = snd_soc_read(codec, WM8741_FORMAT_CONTROL) & 0x1FC; + u16 mode = snd_soc_read(codec, WM8741_MODE_CONTROL_1) & 0x183; int i;
/* The set of sample rates that can be supported depends on the @@ -220,6 +221,12 @@ static int wm8741_hw_params(struct snd_pcm_substream *substream, return -EINVAL; }
+ /* oversampling rate */ + if (params_rate(params) > 96000) + mode |= 0x0040; + else if (params_rate(params) > 48000) + mode |= 0x0020; + /* bit size */ switch (params_width(params)) { case 16: @@ -243,6 +250,7 @@ static int wm8741_hw_params(struct snd_pcm_substream *substream, params_width(params), params_rate(params));
snd_soc_write(codec, WM8741_FORMAT_CONTROL, iface); + snd_soc_write(codec, WM8741_MODE_CONTROL_1, mode); return 0; }