Thanks for the reply!
Some usb audio devices don't follow the standard specification. (1/256 dB) I think introducing the dB conversion factor may be a good idea. Also I think mixer_maps.c is a good place to do this.
By the way, I can't figure out the meanings of FU, MU, SU, ... etc. Could you tell me the meanings of them? (I guess FUs are units which have volume controls?)
The devices which I tested has only one volume control shown in alsamixer. I don't know if there are some devices have more than one volume factor.
thanks again,
Yao-Wen
On Tue, Jul 28, 2015 at 4:17 PM, Takashi Iwai tiwai@suse.de wrote:
On Tue, 28 Jul 2015 10:06:45 +0200, Yao-Wen Mao wrote:
Some usb audio devices don't follow the specification of the volume range. Add dB_mapping_quirks to fix some devices' dB ranges so that the function snd_mixer_selem_set_playback_dB in alsa-lib can set the correct value for those devices.
Signed-off-by: Yao-Wen Mao yaowen@google.com
This can be done also by adding to mixer_maps.c. The map doesn't have to contain the name string but only with a dB entry (I think).
OTOH, this patch shows the value factor to be corrected, so it may make more sense -- people can look at these as a reference.
One thing I wonder, though: can it be simplified by introducing the dB conversion factor instead? Do these devices have other FUs that have a different volume factor?
thanks,
Takashi
sound/usb/mixer.c | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+)
diff --git a/sound/usb/mixer.c b/sound/usb/mixer.c index 6b3acba..b6b27dc 100644 --- a/sound/usb/mixer.c +++ b/sound/usb/mixer.c @@ -933,6 +933,32 @@ static void volume_control_quirks(struct
usb_mixer_elem_info *cval,
}
}
+/* dB mapping quirks */ +static void dB_mapping_quirks(struct usb_mixer_elem_info *cval,
struct snd_kcontrol *kctl)
+{
switch (cval->mixer->chip->usb_id) {
case USB_ID(0x05a7, 0x1020): /* Bose Companion 5 */
if (strcmp(kctl->id.name, "PCM Playback Volume") == 0) {
cval->dBmin = (convert_signed_value(cval,
cval->min) * 100) / 16;
cval->dBmax = (convert_signed_value(cval,
cval->max) * 100) / 16;
}
break;
case USB_ID(0x21b4, 0x0081): /* Dragonfly DAC 1.2 */
if (strcmp(kctl->id.name, "PCM Playback Volume") == 0) {
cval->dBmin = convert_signed_value(cval,
cval->min) * 100;
cval->dBmax = convert_signed_value(cval,
cval->max) * 100;
}
break;
case USB_ID(0x046d, 0x0a29): /* Logitech H800 */
if (strcmp(kctl->id.name, "PCM Playback Volume") == 0) {
cval->dBmin = convert_signed_value(cval,
cval->min);
cval->dBmax = convert_signed_value(cval,
cval->max);
}
break;
}
+}
/*
- retrieve the minimum and maximum values for the specified control
*/ @@ -1027,6 +1053,10 @@ static int get_min_max_with_quirks(struct
usb_mixer_elem_info *cval,
*/ cval->dBmin = (convert_signed_value(cval, cval->min) * 100) / 256; cval->dBmax = (convert_signed_value(cval, cval->max) * 100) / 256;
if (kctl)
dB_mapping_quirks(cval, kctl);
if (cval->dBmin > cval->dBmax) { /* something is wrong; assume it's either from/to 0dB */ if (cval->dBmin < 0)
-- 2.5.0.rc2.392.g76e840b