aboutsummaryrefslogtreecommitdiffstats
path: root/sound/pci
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2013-08-12 08:44:59 -0400
committerTakashi Iwai <tiwai@suse.de>2013-08-13 03:11:04 -0400
commite80c60f3cbe76fa95029abc53b1a29172b51b96a (patch)
tree80ece245698dc8e88da0eae405009af5e03d1e53 /sound/pci
parentbc2eee29fc8224ffad495d0c68ead0ce603309e3 (diff)
ALSA: hda - Mute the right widget in auto_mute_via_amp mode
The current generic parser code assumes that always a pin widget controls the mute for an output blindly although it might be a different widget in the middle. Instead of the fixed assumption, check each parsed path and just pick up the right widget that has been already defined as a mute control. Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound/pci')
-rw-r--r--sound/pci/hda/hda_generic.c31
1 files changed, 25 insertions, 6 deletions
diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c
index 6ed2209c9142..fd1965c8cda9 100644
--- a/sound/pci/hda/hda_generic.c
+++ b/sound/pci/hda/hda_generic.c
@@ -3768,7 +3768,7 @@ static bool detect_jacks(struct hda_codec *codec, int num_pins, hda_nid_t *pins)
3768 3768
3769/* standard HP/line-out auto-mute helper */ 3769/* standard HP/line-out auto-mute helper */
3770static void do_automute(struct hda_codec *codec, int num_pins, hda_nid_t *pins, 3770static void do_automute(struct hda_codec *codec, int num_pins, hda_nid_t *pins,
3771 bool mute) 3771 int *paths, bool mute)
3772{ 3772{
3773 struct hda_gen_spec *spec = codec->spec; 3773 struct hda_gen_spec *spec = codec->spec;
3774 int i; 3774 int i;
@@ -3780,10 +3780,19 @@ static void do_automute(struct hda_codec *codec, int num_pins, hda_nid_t *pins,
3780 break; 3780 break;
3781 3781
3782 if (spec->auto_mute_via_amp) { 3782 if (spec->auto_mute_via_amp) {
3783 struct nid_path *path;
3784 hda_nid_t mute_nid;
3785
3786 path = snd_hda_get_path_from_idx(codec, paths[i]);
3787 if (!path)
3788 continue;
3789 mute_nid = get_amp_nid_(path->ctls[NID_PATH_MUTE_CTL]);
3790 if (!mute_nid)
3791 continue;
3783 if (mute) 3792 if (mute)
3784 spec->mute_bits |= (1ULL << nid); 3793 spec->mute_bits |= (1ULL << mute_nid);
3785 else 3794 else
3786 spec->mute_bits &= ~(1ULL << nid); 3795 spec->mute_bits &= ~(1ULL << mute_nid);
3787 set_pin_eapd(codec, nid, !mute); 3796 set_pin_eapd(codec, nid, !mute);
3788 continue; 3797 continue;
3789 } 3798 }
@@ -3814,14 +3823,19 @@ static void do_automute(struct hda_codec *codec, int num_pins, hda_nid_t *pins,
3814void snd_hda_gen_update_outputs(struct hda_codec *codec) 3823void snd_hda_gen_update_outputs(struct hda_codec *codec)
3815{ 3824{
3816 struct hda_gen_spec *spec = codec->spec; 3825 struct hda_gen_spec *spec = codec->spec;
3826 int *paths;
3817 int on; 3827 int on;
3818 3828
3819 /* Control HP pins/amps depending on master_mute state; 3829 /* Control HP pins/amps depending on master_mute state;
3820 * in general, HP pins/amps control should be enabled in all cases, 3830 * in general, HP pins/amps control should be enabled in all cases,
3821 * but currently set only for master_mute, just to be safe 3831 * but currently set only for master_mute, just to be safe
3822 */ 3832 */
3833 if (spec->autocfg.line_out_type == AUTO_PIN_HP_OUT)
3834 paths = spec->out_paths;
3835 else
3836 paths = spec->hp_paths;
3823 do_automute(codec, ARRAY_SIZE(spec->autocfg.hp_pins), 3837 do_automute(codec, ARRAY_SIZE(spec->autocfg.hp_pins),
3824 spec->autocfg.hp_pins, spec->master_mute); 3838 spec->autocfg.hp_pins, paths, spec->master_mute);
3825 3839
3826 if (!spec->automute_speaker) 3840 if (!spec->automute_speaker)
3827 on = 0; 3841 on = 0;
@@ -3829,8 +3843,12 @@ void snd_hda_gen_update_outputs(struct hda_codec *codec)
3829 on = spec->hp_jack_present | spec->line_jack_present; 3843 on = spec->hp_jack_present | spec->line_jack_present;
3830 on |= spec->master_mute; 3844 on |= spec->master_mute;
3831 spec->speaker_muted = on; 3845 spec->speaker_muted = on;
3846 if (spec->autocfg.line_out_type == AUTO_PIN_SPEAKER_OUT)
3847 paths = spec->out_paths;
3848 else
3849 paths = spec->speaker_paths;
3832 do_automute(codec, ARRAY_SIZE(spec->autocfg.speaker_pins), 3850 do_automute(codec, ARRAY_SIZE(spec->autocfg.speaker_pins),
3833 spec->autocfg.speaker_pins, on); 3851 spec->autocfg.speaker_pins, paths, on);
3834 3852
3835 /* toggle line-out mutes if needed, too */ 3853 /* toggle line-out mutes if needed, too */
3836 /* if LO is a copy of either HP or Speaker, don't need to handle it */ 3854 /* if LO is a copy of either HP or Speaker, don't need to handle it */
@@ -3843,8 +3861,9 @@ void snd_hda_gen_update_outputs(struct hda_codec *codec)
3843 on = spec->hp_jack_present; 3861 on = spec->hp_jack_present;
3844 on |= spec->master_mute; 3862 on |= spec->master_mute;
3845 spec->line_out_muted = on; 3863 spec->line_out_muted = on;
3864 paths = spec->out_paths;
3846 do_automute(codec, ARRAY_SIZE(spec->autocfg.line_out_pins), 3865 do_automute(codec, ARRAY_SIZE(spec->autocfg.line_out_pins),
3847 spec->autocfg.line_out_pins, on); 3866 spec->autocfg.line_out_pins, paths, on);
3848} 3867}
3849EXPORT_SYMBOL_HDA(snd_hda_gen_update_outputs); 3868EXPORT_SYMBOL_HDA(snd_hda_gen_update_outputs);
3850 3869