diff options
author | Matthew Ranostay <mranostay@embeddedalley.com> | 2008-02-22 11:55:05 -0500 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2008-04-24 06:00:15 -0400 |
commit | ae0afd81b34ce287ffda7dd4e33b5144de2ad39d (patch) | |
tree | 00111b0bed4bbe7e279fc5be11b8f458a4d94c6a /sound/pci | |
parent | 88d18ea2c2b40496b56efcb354e9eae1f09ef126 (diff) |
[ALSA] hda: Mic as output fix
Added logic to check if AUTO_PIN_FRONT_MIC is available for output
switch, if AUTO_PIN_MIC isn't.
Signed-off-by: Matthew Ranostay <mranostay@embeddedalley.com>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound/pci')
-rw-r--r-- | sound/pci/hda/patch_sigmatel.c | 58 |
1 files changed, 33 insertions, 25 deletions
diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index 314ea51538b7..ef86402d7e67 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c | |||
@@ -2307,6 +2307,29 @@ static int create_controls(struct sigmatel_spec *spec, const char *pfx, hda_nid_ | |||
2307 | return 0; | 2307 | return 0; |
2308 | } | 2308 | } |
2309 | 2309 | ||
2310 | static int add_spec_dacs(struct sigmatel_spec *spec, hda_nid_t nid) | ||
2311 | { | ||
2312 | if (!spec->multiout.hp_nid) | ||
2313 | spec->multiout.hp_nid = nid; | ||
2314 | else if (spec->multiout.num_dacs > 4) { | ||
2315 | printk(KERN_WARNING "stac92xx: No space for DAC 0x%x\n", nid); | ||
2316 | return 1; | ||
2317 | } else { | ||
2318 | spec->multiout.dac_nids[spec->multiout.num_dacs] = nid; | ||
2319 | spec->multiout.num_dacs++; | ||
2320 | } | ||
2321 | return 0; | ||
2322 | } | ||
2323 | |||
2324 | static int check_in_dac_nids(struct sigmatel_spec *spec, hda_nid_t nid) | ||
2325 | { | ||
2326 | if (is_in_dac_nids(spec, nid)) | ||
2327 | return 1; | ||
2328 | if (spec->multiout.hp_nid == nid) | ||
2329 | return 1; | ||
2330 | return 0; | ||
2331 | } | ||
2332 | |||
2310 | /* add playback controls from the parsed DAC table */ | 2333 | /* add playback controls from the parsed DAC table */ |
2311 | static int stac92xx_auto_create_multi_out_ctls(struct hda_codec *codec, | 2334 | static int stac92xx_auto_create_multi_out_ctls(struct hda_codec *codec, |
2312 | const struct auto_pin_cfg *cfg) | 2335 | const struct auto_pin_cfg *cfg) |
@@ -2369,10 +2392,11 @@ static int stac92xx_auto_create_multi_out_ctls(struct hda_codec *codec, | |||
2369 | 2392 | ||
2370 | if (spec->mic_switch) { | 2393 | if (spec->mic_switch) { |
2371 | unsigned int def_conf; | 2394 | unsigned int def_conf; |
2372 | nid = cfg->input_pins[AUTO_PIN_MIC]; | 2395 | unsigned int mic_pin = AUTO_PIN_MIC; |
2396 | again: | ||
2397 | nid = cfg->input_pins[mic_pin]; | ||
2373 | def_conf = snd_hda_codec_read(codec, nid, 0, | 2398 | def_conf = snd_hda_codec_read(codec, nid, 0, |
2374 | AC_VERB_GET_CONFIG_DEFAULT, 0); | 2399 | AC_VERB_GET_CONFIG_DEFAULT, 0); |
2375 | |||
2376 | /* some laptops have an internal analog microphone | 2400 | /* some laptops have an internal analog microphone |
2377 | * which can't be used as a output */ | 2401 | * which can't be used as a output */ |
2378 | if (get_defcfg_connect(def_conf) != AC_JACK_PORT_FIXED) { | 2402 | if (get_defcfg_connect(def_conf) != AC_JACK_PORT_FIXED) { |
@@ -2382,38 +2406,22 @@ static int stac92xx_auto_create_multi_out_ctls(struct hda_codec *codec, | |||
2382 | err = stac92xx_add_control(spec, | 2406 | err = stac92xx_add_control(spec, |
2383 | STAC_CTL_WIDGET_IO_SWITCH, | 2407 | STAC_CTL_WIDGET_IO_SWITCH, |
2384 | "Mic as Output Switch", (nid << 8) | 1); | 2408 | "Mic as Output Switch", (nid << 8) | 1); |
2409 | nid = snd_hda_codec_read(codec, nid, 0, | ||
2410 | AC_VERB_GET_CONNECT_LIST, 0) & 0xff; | ||
2411 | if (!check_in_dac_nids(spec, nid)) | ||
2412 | add_spec_dacs(spec, nid); | ||
2385 | if (err < 0) | 2413 | if (err < 0) |
2386 | return err; | 2414 | return err; |
2387 | } | 2415 | } |
2416 | } else if (mic_pin == AUTO_PIN_MIC) { | ||
2417 | mic_pin = AUTO_PIN_FRONT_MIC; | ||
2418 | goto again; | ||
2388 | } | 2419 | } |
2389 | } | 2420 | } |
2390 | 2421 | ||
2391 | return 0; | 2422 | return 0; |
2392 | } | 2423 | } |
2393 | 2424 | ||
2394 | static int check_in_dac_nids(struct sigmatel_spec *spec, hda_nid_t nid) | ||
2395 | { | ||
2396 | if (is_in_dac_nids(spec, nid)) | ||
2397 | return 1; | ||
2398 | if (spec->multiout.hp_nid == nid) | ||
2399 | return 1; | ||
2400 | return 0; | ||
2401 | } | ||
2402 | |||
2403 | static int add_spec_dacs(struct sigmatel_spec *spec, hda_nid_t nid) | ||
2404 | { | ||
2405 | if (!spec->multiout.hp_nid) | ||
2406 | spec->multiout.hp_nid = nid; | ||
2407 | else if (spec->multiout.num_dacs > 4) { | ||
2408 | printk(KERN_WARNING "stac92xx: No space for DAC 0x%x\n", nid); | ||
2409 | return 1; | ||
2410 | } else { | ||
2411 | spec->multiout.dac_nids[spec->multiout.num_dacs] = nid; | ||
2412 | spec->multiout.num_dacs++; | ||
2413 | } | ||
2414 | return 0; | ||
2415 | } | ||
2416 | |||
2417 | /* add playback controls for Speaker and HP outputs */ | 2425 | /* add playback controls for Speaker and HP outputs */ |
2418 | static int stac92xx_auto_create_hp_ctls(struct hda_codec *codec, | 2426 | static int stac92xx_auto_create_hp_ctls(struct hda_codec *codec, |
2419 | struct auto_pin_cfg *cfg) | 2427 | struct auto_pin_cfg *cfg) |