aboutsummaryrefslogtreecommitdiff
path: root/sound/pci/hda/patch_via.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/pci/hda/patch_via.c')
-rw-r--r--sound/pci/hda/patch_via.c50
1 files changed, 36 insertions, 14 deletions
diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c
index c35338a8771..778166259b3 100644
--- a/sound/pci/hda/patch_via.c
+++ b/sound/pci/hda/patch_via.c
@@ -136,7 +136,9 @@ static struct via_spec *via_new_spec(struct hda_codec *codec)
spec->codec_type = VT1708S;
spec->no_pin_power_ctl = 1;
spec->gen.indep_hp = 1;
+ spec->gen.keep_eapd_on = 1;
spec->gen.pcm_playback_hook = via_playback_pcm_hook;
+ spec->gen.add_stereo_mix_input = 1;
return spec;
}
@@ -206,9 +208,9 @@ static void vt1708_stop_hp_work(struct hda_codec *codec)
return;
if (spec->hp_work_active) {
snd_hda_codec_write(codec, 0x1, 0, 0xf81, 1);
+ codec->jackpoll_interval = 0;
cancel_delayed_work_sync(&codec->jackpoll_work);
spec->hp_work_active = false;
- codec->jackpoll_interval = 0;
}
}
@@ -231,9 +233,14 @@ static void vt1708_update_hp_work(struct hda_codec *codec)
static void set_widgets_power_state(struct hda_codec *codec)
{
+#if 0 /* FIXME: the assumed connections don't match always with the
+ * actual routes by the generic parser, so better to disable
+ * the control for safety.
+ */
struct via_spec *spec = codec->spec;
if (spec->set_widgets_power_state)
spec->set_widgets_power_state(codec);
+#endif
}
static void update_power_state(struct hda_codec *codec, hda_nid_t nid,
@@ -458,14 +465,8 @@ static void via_playback_pcm_hook(struct hda_pcm_stream *hinfo,
static void via_free(struct hda_codec *codec)
{
- struct via_spec *spec = codec->spec;
-
- if (!spec)
- return;
-
vt1708_stop_hp_work(codec);
- snd_hda_gen_spec_free(&spec->gen);
- kfree(spec);
+ snd_hda_gen_free(codec);
}
#ifdef CONFIG_PM
@@ -474,12 +475,9 @@ static int via_suspend(struct hda_codec *codec)
struct via_spec *spec = codec->spec;
vt1708_stop_hp_work(codec);
- if (spec->codec_type == VT1802) {
- /* Fix pop noise on headphones */
- int i;
- for (i = 0; i < spec->gen.autocfg.hp_outs; i++)
- snd_hda_set_pin_ctl(codec, spec->gen.autocfg.hp_pins[i], 0);
- }
+ /* Fix pop noise on headphones */
+ if (spec->codec_type == VT1802)
+ snd_hda_shutup_pins(codec);
return 0;
}
@@ -626,11 +624,31 @@ static void via_set_jack_unsol_events(struct hda_codec *codec)
}
}
+static const struct badness_table via_main_out_badness = {
+ .no_primary_dac = 0x10000,
+ .no_dac = 0x4000,
+ .shared_primary = 0x10000,
+ .shared_surr = 0x20,
+ .shared_clfe = 0x20,
+ .shared_surr_main = 0x20,
+};
+static const struct badness_table via_extra_out_badness = {
+ .no_primary_dac = 0x4000,
+ .no_dac = 0x4000,
+ .shared_primary = 0x12,
+ .shared_surr = 0x20,
+ .shared_clfe = 0x20,
+ .shared_surr_main = 0x10,
+};
+
static int via_parse_auto_config(struct hda_codec *codec)
{
struct via_spec *spec = codec->spec;
int err;
+ spec->gen.main_out_badness = &via_main_out_badness;
+ spec->gen.extra_out_badness = &via_extra_out_badness;
+
err = snd_hda_parse_pin_defcfg(codec, &spec->gen.autocfg, NULL, 0);
if (err < 0)
return err;
@@ -718,6 +736,8 @@ static int patch_vt1708(struct hda_codec *codec)
/* don't support the input jack switching due to lack of unsol event */
/* (it may work with polling, though, but it needs testing) */
spec->gen.suppress_auto_mic = 1;
+ /* Some machines show the broken speaker mute */
+ spec->gen.auto_mute_via_amp = 1;
/* Add HP and CD pin config connect bit re-config action */
vt1708_set_pinconfig_connect(codec, VT1708_HP_PIN_NID);
@@ -882,6 +902,8 @@ static const struct hda_verb vt1708S_init_verbs[] = {
static void override_mic_boost(struct hda_codec *codec, hda_nid_t pin,
int offset, int num_steps, int step_size)
{
+ snd_hda_override_wcaps(codec, pin,
+ get_wcaps(codec, pin) | AC_WCAP_IN_AMP);
snd_hda_override_amp_caps(codec, pin, HDA_INPUT,
(offset << AC_AMPCAP_OFFSET_SHIFT) |
(num_steps << AC_AMPCAP_NUM_STEPS_SHIFT) |