Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

ASoC: SDCA: Export Q7.8 volume control helpers

Export the Q7.8 volume control helpers to allow reuse
by other ASoC drivers. These functions handle 16-bit
signed Q7.8 fixed-point format values for volume controls.

Changes include:
- Rename q78_get_volsw to sdca_asoc_q78_get_volsw
- Rename q78_put_volsw to sdca_asoc_q78_put_volsw
- Add a convenience macro SDCA_SINGLE_Q78_TLV and
SDCA_DOUBLE_Q78_TLV for creating mixer controls

This allows other ASoC drivers to easily implement controls
using the Q7.8 fixed-point format without duplicating code.

Signed-off-by: Niranjan H Y <niranjan.hy@ti.com>
Reviewed-by: Charles Keepax <ckeepax@opensource.cirrus.com>
Link: https://patch.msgid.link/20260401132148.2367-1-niranjan.hy@ti.com
Signed-off-by: Mark Brown <broonie@kernel.org>

authored by

Niranjan H Y and committed by
Mark Brown
ba2a0e81 04cc4762

+50 -7
+42 -1
include/sound/sdca_asoc.h
··· 13 13 struct device; 14 14 struct regmap; 15 15 struct sdca_function_data; 16 + struct snd_ctl_elem_value; 17 + struct snd_kcontrol; 16 18 struct snd_kcontrol_new; 17 19 struct snd_pcm_hw_params; 18 20 struct snd_pcm_substream; ··· 24 22 struct snd_soc_dai_ops; 25 23 struct snd_soc_dapm_route; 26 24 struct snd_soc_dapm_widget; 25 + 26 + /* convenient macro to handle the mono volume in 7.8 fixed format representation */ 27 + #define SDCA_SINGLE_Q78_TLV(xname, xreg, xmin, xmax, xstep, tlv_array) \ 28 + { \ 29 + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \ 30 + .name = (xname), \ 31 + .access = SNDRV_CTL_ELEM_ACCESS_TLV_READ | SNDRV_CTL_ELEM_ACCESS_READWRITE, \ 32 + .tlv.p = (tlv_array), \ 33 + .info = snd_soc_info_volsw, \ 34 + .get = sdca_asoc_q78_get_volsw, \ 35 + .put = sdca_asoc_q78_put_volsw, \ 36 + .private_value = (unsigned long)&(struct soc_mixer_control) { \ 37 + .reg = (xreg), .rreg = (xreg), \ 38 + .min = (xmin), .max = (xmax), \ 39 + .shift = (xstep), .rshift = (xstep), \ 40 + .sign_bit = 15 \ 41 + } \ 42 + } 43 + 44 + /* convenient macro for stereo volume in 7.8 fixed format with separate registers for L/R */ 45 + #define SDCA_DOUBLE_Q78_TLV(xname, xreg_l, xreg_r, xmin, xmax, xstep, tlv_array) \ 46 + { \ 47 + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \ 48 + .name = (xname), \ 49 + .access = SNDRV_CTL_ELEM_ACCESS_TLV_READ | SNDRV_CTL_ELEM_ACCESS_READWRITE, \ 50 + .tlv.p = (tlv_array), \ 51 + .info = snd_soc_info_volsw, \ 52 + .get = sdca_asoc_q78_get_volsw, \ 53 + .put = sdca_asoc_q78_put_volsw, \ 54 + .private_value = (unsigned long)&(struct soc_mixer_control) { \ 55 + .reg = (xreg_l), .rreg = (xreg_r), \ 56 + .min = (xmin), .max = (xmax), \ 57 + .shift = (xstep), .rshift = (xstep), \ 58 + .sign_bit = 15 \ 59 + } \ 60 + } 27 61 28 62 int sdca_asoc_count_component(struct device *dev, struct sdca_function_data *function, 29 63 int *num_widgets, int *num_routes, int *num_controls, ··· 95 57 struct snd_pcm_substream *substream, 96 58 struct snd_pcm_hw_params *params, 97 59 struct snd_soc_dai *dai); 98 - 60 + int sdca_asoc_q78_put_volsw(struct snd_kcontrol *kcontrol, 61 + struct snd_ctl_elem_value *ucontrol); 62 + int sdca_asoc_q78_get_volsw(struct snd_kcontrol *kcontrol, 63 + struct snd_ctl_elem_value *ucontrol); 99 64 #endif // __SDCA_ASOC_H__
+8 -6
sound/soc/sdca/sdca_asoc.c
··· 820 820 return snd_soc_component_update_bits(component, reg, mask, reg_val); 821 821 } 822 822 823 - static int q78_put_volsw(struct snd_kcontrol *kcontrol, 824 - struct snd_ctl_elem_value *ucontrol) 823 + int sdca_asoc_q78_put_volsw(struct snd_kcontrol *kcontrol, 824 + struct snd_ctl_elem_value *ucontrol) 825 825 { 826 826 struct soc_mixer_control *mc = (struct soc_mixer_control *)kcontrol->private_value; 827 827 struct snd_soc_component *component = snd_kcontrol_chip(kcontrol); ··· 841 841 842 842 return ret; 843 843 } 844 + EXPORT_SYMBOL_NS(sdca_asoc_q78_put_volsw, "SND_SOC_SDCA"); 844 845 845 846 static int q78_read(struct snd_soc_component *component, 846 847 struct soc_mixer_control *mc, unsigned int reg) ··· 856 855 return val & GENMASK(mc->sign_bit, 0); 857 856 } 858 857 859 - static int q78_get_volsw(struct snd_kcontrol *kcontrol, 860 - struct snd_ctl_elem_value *ucontrol) 858 + int sdca_asoc_q78_get_volsw(struct snd_kcontrol *kcontrol, 859 + struct snd_ctl_elem_value *ucontrol) 861 860 { 862 861 struct soc_mixer_control *mc = (struct soc_mixer_control *)kcontrol->private_value; 863 862 struct snd_soc_component *component = snd_kcontrol_chip(kcontrol); ··· 869 868 870 869 return 0; 871 870 } 871 + EXPORT_SYMBOL_NS(sdca_asoc_q78_get_volsw, "SND_SOC_SDCA"); 872 872 873 873 static int control_limit_kctl(struct device *dev, 874 874 struct sdca_entity *entity, ··· 914 912 915 913 kctl->tlv.p = tlv; 916 914 kctl->access |= SNDRV_CTL_ELEM_ACCESS_TLV_READ; 917 - kctl->get = q78_get_volsw; 918 - kctl->put = q78_put_volsw; 915 + kctl->get = sdca_asoc_q78_get_volsw; 916 + kctl->put = sdca_asoc_q78_put_volsw; 919 917 920 918 return 0; 921 919 }