aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2012-01-11 06:34:11 -0500
committerTakashi Iwai <tiwai@suse.de>2012-01-11 06:34:11 -0500
commitf2cbba7602383cd9cdd21f0a5d0b8bd1aad47b33 (patch)
treed2585c3c5dde41bd28450f784e5824484cfac77a
parent4808d12d1dddb046ec86425e5f6766f02e950292 (diff)
ALSA: hda - Fix the lost power-setup of seconary pins after PM resume
When multiple headphone or other detectable output pins are present, the power-map has to be updated after resume appropriately, but the current driver doesn't check all pins but only the first pin (since it's enough to check it for the mute-behavior). This resulted in the silent output from the secondary outputs after PM resume. This patch fixes the problem by checking all pins at (re-)init time. Bugzilla: https://bugzilla.novell.com/show_bug.cgi?id=740347 Cc: <stable@kernel.org> Signed-off-by: Takashi Iwai <tiwai@suse.de>
-rw-r--r--sound/pci/hda/patch_sigmatel.c36
1 files changed, 23 insertions, 13 deletions
diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c
index 03145aec65f1..87e684fa830f 100644
--- a/sound/pci/hda/patch_sigmatel.c
+++ b/sound/pci/hda/patch_sigmatel.c
@@ -4236,6 +4236,27 @@ static void stac_store_hints(struct hda_codec *codec)
4236 } 4236 }
4237} 4237}
4238 4238
4239static void stac_issue_unsol_events(struct hda_codec *codec, int num_pins,
4240 const hda_nid_t *pins)
4241{
4242 while (num_pins--)
4243 stac_issue_unsol_event(codec, *pins++);
4244}
4245
4246/* fake event to set up pins */
4247static void stac_fake_hp_events(struct hda_codec *codec)
4248{
4249 struct sigmatel_spec *spec = codec->spec;
4250
4251 if (spec->autocfg.hp_outs)
4252 stac_issue_unsol_events(codec, spec->autocfg.hp_outs,
4253 spec->autocfg.hp_pins);
4254 if (spec->autocfg.line_outs &&
4255 spec->autocfg.line_out_pins[0] != spec->autocfg.hp_pins[0])
4256 stac_issue_unsol_events(codec, spec->autocfg.line_outs,
4257 spec->autocfg.line_out_pins);
4258}
4259
4239static int stac92xx_init(struct hda_codec *codec) 4260static int stac92xx_init(struct hda_codec *codec)
4240{ 4261{
4241 struct sigmatel_spec *spec = codec->spec; 4262 struct sigmatel_spec *spec = codec->spec;
@@ -4286,10 +4307,7 @@ static int stac92xx_init(struct hda_codec *codec)
4286 stac92xx_auto_set_pinctl(codec, spec->autocfg.line_out_pins[0], 4307 stac92xx_auto_set_pinctl(codec, spec->autocfg.line_out_pins[0],
4287 AC_PINCTL_OUT_EN); 4308 AC_PINCTL_OUT_EN);
4288 /* fake event to set up pins */ 4309 /* fake event to set up pins */
4289 if (cfg->hp_pins[0]) 4310 stac_fake_hp_events(codec);
4290 stac_issue_unsol_event(codec, cfg->hp_pins[0]);
4291 else if (cfg->line_out_pins[0])
4292 stac_issue_unsol_event(codec, cfg->line_out_pins[0]);
4293 } else { 4311 } else {
4294 stac92xx_auto_init_multi_out(codec); 4312 stac92xx_auto_init_multi_out(codec);
4295 stac92xx_auto_init_hp_out(codec); 4313 stac92xx_auto_init_hp_out(codec);
@@ -4948,19 +4966,11 @@ static void stac927x_proc_hook(struct snd_info_buffer *buffer,
4948#ifdef CONFIG_PM 4966#ifdef CONFIG_PM
4949static int stac92xx_resume(struct hda_codec *codec) 4967static int stac92xx_resume(struct hda_codec *codec)
4950{ 4968{
4951 struct sigmatel_spec *spec = codec->spec;
4952
4953 stac92xx_init(codec); 4969 stac92xx_init(codec);
4954 snd_hda_codec_resume_amp(codec); 4970 snd_hda_codec_resume_amp(codec);
4955 snd_hda_codec_resume_cache(codec); 4971 snd_hda_codec_resume_cache(codec);
4956 /* fake event to set up pins again to override cached values */ 4972 /* fake event to set up pins again to override cached values */
4957 if (spec->hp_detect) { 4973 stac_fake_hp_events(codec);
4958 if (spec->autocfg.hp_pins[0])
4959 stac_issue_unsol_event(codec, spec->autocfg.hp_pins[0]);
4960 else if (spec->autocfg.line_out_pins[0])
4961 stac_issue_unsol_event(codec,
4962 spec->autocfg.line_out_pins[0]);
4963 }
4964 return 0; 4974 return 0;
4965} 4975}
4966 4976