aboutsummaryrefslogtreecommitdiffstats
path: root/sound/pci
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2015-04-27 04:36:11 -0400
committerTakashi Iwai <tiwai@suse.de>2015-04-27 04:48:37 -0400
commitee52e56e7b12834476cd0031c5986254ba1b6317 (patch)
tree3076e3911b41026bfa1c9be368f721691f3adac6 /sound/pci
parent3e1b0c4a9d563d7fc6e22dc92613cd3237bb5ce0 (diff)
ALSA: hda - Fix mute-LED fixed mode
The mute-LED mode control has the fixed on/off states that are supposed to remain on/off regardless of the master switch. However, this doesn't work actually because the vmaster hook is called in the vmaster code itself. This patch fixes it by calling the hook indirectly after checking the mute LED mode. Reported-and-tested-by: Pali Rohár <pali.rohar@gmail.com> Cc: <stable@vger.kernel.org> Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound/pci')
-rw-r--r--sound/pci/hda/hda_codec.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c
index 873ed1bce12b..27333e0d8ebe 100644
--- a/sound/pci/hda/hda_codec.c
+++ b/sound/pci/hda/hda_codec.c
@@ -2082,6 +2082,16 @@ static struct snd_kcontrol_new vmaster_mute_mode = {
2082 .put = vmaster_mute_mode_put, 2082 .put = vmaster_mute_mode_put,
2083}; 2083};
2084 2084
2085/* meta hook to call each driver's vmaster hook */
2086static void vmaster_hook(void *private_data, int enabled)
2087{
2088 struct hda_vmaster_mute_hook *hook = private_data;
2089
2090 if (hook->mute_mode != HDA_VMUTE_FOLLOW_MASTER)
2091 enabled = hook->mute_mode;
2092 hook->hook(hook->codec, enabled);
2093}
2094
2085/** 2095/**
2086 * snd_hda_add_vmaster_hook - Add a vmaster hook for mute-LED 2096 * snd_hda_add_vmaster_hook - Add a vmaster hook for mute-LED
2087 * @codec: the HDA codec 2097 * @codec: the HDA codec
@@ -2100,9 +2110,9 @@ int snd_hda_add_vmaster_hook(struct hda_codec *codec,
2100 2110
2101 if (!hook->hook || !hook->sw_kctl) 2111 if (!hook->hook || !hook->sw_kctl)
2102 return 0; 2112 return 0;
2103 snd_ctl_add_vmaster_hook(hook->sw_kctl, hook->hook, codec);
2104 hook->codec = codec; 2113 hook->codec = codec;
2105 hook->mute_mode = HDA_VMUTE_FOLLOW_MASTER; 2114 hook->mute_mode = HDA_VMUTE_FOLLOW_MASTER;
2115 snd_ctl_add_vmaster_hook(hook->sw_kctl, vmaster_hook, hook);
2106 if (!expose_enum_ctl) 2116 if (!expose_enum_ctl)
2107 return 0; 2117 return 0;
2108 kctl = snd_ctl_new1(&vmaster_mute_mode, hook); 2118 kctl = snd_ctl_new1(&vmaster_mute_mode, hook);
@@ -2128,14 +2138,7 @@ void snd_hda_sync_vmaster_hook(struct hda_vmaster_mute_hook *hook)
2128 */ 2138 */
2129 if (hook->codec->bus->shutdown) 2139 if (hook->codec->bus->shutdown)
2130 return; 2140 return;
2131 switch (hook->mute_mode) { 2141 snd_ctl_sync_vmaster_hook(hook->sw_kctl);
2132 case HDA_VMUTE_FOLLOW_MASTER:
2133 snd_ctl_sync_vmaster_hook(hook->sw_kctl);
2134 break;
2135 default:
2136 hook->hook(hook->codec, hook->mute_mode);
2137 break;
2138 }
2139} 2142}
2140EXPORT_SYMBOL_GPL(snd_hda_sync_vmaster_hook); 2143EXPORT_SYMBOL_GPL(snd_hda_sync_vmaster_hook);
2141 2144