OSDN Git Service

ASoC: ops: Fix stereo change notifications in snd_soc_put_volsw_range()
authorMark Brown <broonie@kernel.org>
Tue, 1 Feb 2022 15:56:28 +0000 (15:56 +0000)
committerMark Brown <broonie@kernel.org>
Wed, 2 Feb 2022 16:09:19 +0000 (16:09 +0000)
When writing out a stereo control we discard the change notification from
the first channel, meaning that events are only generated based on changes
to the second channel. Ensure that we report a change if either channel
has changed.

Signed-off-by: Mark Brown <broonie@kernel.org>
Cc: stable@vger.kernel.org
Link: https://lore.kernel.org/r/20220201155629.120510-4-broonie@kernel.org
Signed-off-by: Mark Brown <broonie@kernel.org>
sound/soc/soc-ops.c

index 4987c58..2e57f81 100644 (file)
@@ -519,7 +519,7 @@ int snd_soc_put_volsw_range(struct snd_kcontrol *kcontrol,
        unsigned int mask = (1 << fls(max)) - 1;
        unsigned int invert = mc->invert;
        unsigned int val, val_mask;
-       int ret;
+       int err, ret;
 
        if (invert)
                val = (max - ucontrol->value.integer.value[0]) & mask;
@@ -528,9 +528,10 @@ int snd_soc_put_volsw_range(struct snd_kcontrol *kcontrol,
        val_mask = mask << shift;
        val = val << shift;
 
-       ret = snd_soc_component_update_bits(component, reg, val_mask, val);
-       if (ret < 0)
-               return ret;
+       err = snd_soc_component_update_bits(component, reg, val_mask, val);
+       if (err < 0)
+               return err;
+       ret = err;
 
        if (snd_soc_volsw_is_stereo(mc)) {
                if (invert)
@@ -540,8 +541,12 @@ int snd_soc_put_volsw_range(struct snd_kcontrol *kcontrol,
                val_mask = mask << shift;
                val = val << shift;
 
-               ret = snd_soc_component_update_bits(component, rreg, val_mask,
+               err = snd_soc_component_update_bits(component, rreg, val_mask,
                        val);
+               /* Don't discard any error code or drop change flag */
+               if (ret == 0 || err < 0) {
+                       ret = err;
+               }
        }
 
        return ret;