diff options
Diffstat (limited to 'sound/pci')
-rw-r--r-- | sound/pci/au88x0/au88x0_core.c | 14 | ||||
-rw-r--r-- | sound/pci/azt3328.c | 38 | ||||
-rw-r--r-- | sound/pci/hda/hda_eld.c | 2 | ||||
-rw-r--r-- | sound/pci/hda/hda_intel.c | 3 | ||||
-rw-r--r-- | sound/pci/hda/patch_conexant.c | 212 | ||||
-rw-r--r-- | sound/pci/hda/patch_hdmi.c | 2 | ||||
-rw-r--r-- | sound/pci/hda/patch_realtek.c | 33 | ||||
-rw-r--r-- | sound/pci/hda/patch_via.c | 2 | ||||
-rw-r--r-- | sound/pci/oxygen/oxygen.h | 2 | ||||
-rw-r--r-- | sound/pci/oxygen/oxygen_mixer.c | 2 | ||||
-rw-r--r-- | sound/pci/oxygen/xonar_dg.c | 36 |
11 files changed, 237 insertions, 109 deletions
diff --git a/sound/pci/au88x0/au88x0_core.c b/sound/pci/au88x0/au88x0_core.c index 23f49f356e0f..16c0bdfbb164 100644 --- a/sound/pci/au88x0/au88x0_core.c +++ b/sound/pci/au88x0/au88x0_core.c | |||
@@ -1252,11 +1252,19 @@ static void vortex_adbdma_resetup(vortex_t *vortex, int adbdma) { | |||
1252 | static int inline vortex_adbdma_getlinearpos(vortex_t * vortex, int adbdma) | 1252 | static int inline vortex_adbdma_getlinearpos(vortex_t * vortex, int adbdma) |
1253 | { | 1253 | { |
1254 | stream_t *dma = &vortex->dma_adb[adbdma]; | 1254 | stream_t *dma = &vortex->dma_adb[adbdma]; |
1255 | int temp; | 1255 | int temp, page, delta; |
1256 | 1256 | ||
1257 | temp = hwread(vortex->mmio, VORTEX_ADBDMA_STAT + (adbdma << 2)); | 1257 | temp = hwread(vortex->mmio, VORTEX_ADBDMA_STAT + (adbdma << 2)); |
1258 | temp = (dma->period_virt * dma->period_bytes) + (temp & (dma->period_bytes - 1)); | 1258 | page = (temp & ADB_SUBBUF_MASK) >> ADB_SUBBUF_SHIFT; |
1259 | return temp; | 1259 | if (dma->nr_periods >= 4) |
1260 | delta = (page - dma->period_real) & 3; | ||
1261 | else { | ||
1262 | delta = (page - dma->period_real); | ||
1263 | if (delta < 0) | ||
1264 | delta += dma->nr_periods; | ||
1265 | } | ||
1266 | return (dma->period_virt + delta) * dma->period_bytes | ||
1267 | + (temp & (dma->period_bytes - 1)); | ||
1260 | } | 1268 | } |
1261 | 1269 | ||
1262 | static void vortex_adbdma_startfifo(vortex_t * vortex, int adbdma) | 1270 | static void vortex_adbdma_startfifo(vortex_t * vortex, int adbdma) |
diff --git a/sound/pci/azt3328.c b/sound/pci/azt3328.c index bb84bb68a776..5715c4d05573 100644 --- a/sound/pci/azt3328.c +++ b/sound/pci/azt3328.c | |||
@@ -1317,31 +1317,25 @@ snd_azf3328_codec_setfmt(struct snd_azf3328_codec_data *codec, | |||
1317 | 1317 | ||
1318 | snd_azf3328_dbgcallenter(); | 1318 | snd_azf3328_dbgcallenter(); |
1319 | switch (bitrate) { | 1319 | switch (bitrate) { |
1320 | #define AZF_FMT_XLATE(in_freq, out_bits) \ | 1320 | case AZF_FREQ_4000: freq = SOUNDFORMAT_FREQ_SUSPECTED_4000; break; |
1321 | do { \ | 1321 | case AZF_FREQ_4800: freq = SOUNDFORMAT_FREQ_SUSPECTED_4800; break; |
1322 | case AZF_FREQ_ ## in_freq: \ | 1322 | case AZF_FREQ_5512: |
1323 | freq = SOUNDFORMAT_FREQ_ ## out_bits; \ | 1323 | /* the AZF3328 names it "5510" for some strange reason */ |
1324 | break; \ | 1324 | freq = SOUNDFORMAT_FREQ_5510; break; |
1325 | } while (0); | 1325 | case AZF_FREQ_6620: freq = SOUNDFORMAT_FREQ_6620; break; |
1326 | AZF_FMT_XLATE(4000, SUSPECTED_4000) | 1326 | case AZF_FREQ_8000: freq = SOUNDFORMAT_FREQ_8000; break; |
1327 | AZF_FMT_XLATE(4800, SUSPECTED_4800) | 1327 | case AZF_FREQ_9600: freq = SOUNDFORMAT_FREQ_9600; break; |
1328 | /* the AZF3328 names it "5510" for some strange reason: */ | 1328 | case AZF_FREQ_11025: freq = SOUNDFORMAT_FREQ_11025; break; |
1329 | AZF_FMT_XLATE(5512, 5510) | 1329 | case AZF_FREQ_13240: freq = SOUNDFORMAT_FREQ_SUSPECTED_13240; break; |
1330 | AZF_FMT_XLATE(6620, 6620) | 1330 | case AZF_FREQ_16000: freq = SOUNDFORMAT_FREQ_16000; break; |
1331 | AZF_FMT_XLATE(8000, 8000) | 1331 | case AZF_FREQ_22050: freq = SOUNDFORMAT_FREQ_22050; break; |
1332 | AZF_FMT_XLATE(9600, 9600) | 1332 | case AZF_FREQ_32000: freq = SOUNDFORMAT_FREQ_32000; break; |
1333 | AZF_FMT_XLATE(11025, 11025) | ||
1334 | AZF_FMT_XLATE(13240, SUSPECTED_13240) | ||
1335 | AZF_FMT_XLATE(16000, 16000) | ||
1336 | AZF_FMT_XLATE(22050, 22050) | ||
1337 | AZF_FMT_XLATE(32000, 32000) | ||
1338 | default: | 1333 | default: |
1339 | snd_printk(KERN_WARNING "unknown bitrate %d, assuming 44.1kHz!\n", bitrate); | 1334 | snd_printk(KERN_WARNING "unknown bitrate %d, assuming 44.1kHz!\n", bitrate); |
1340 | /* fall-through */ | 1335 | /* fall-through */ |
1341 | AZF_FMT_XLATE(44100, 44100) | 1336 | case AZF_FREQ_44100: freq = SOUNDFORMAT_FREQ_44100; break; |
1342 | AZF_FMT_XLATE(48000, 48000) | 1337 | case AZF_FREQ_48000: freq = SOUNDFORMAT_FREQ_48000; break; |
1343 | AZF_FMT_XLATE(66200, SUSPECTED_66200) | 1338 | case AZF_FREQ_66200: freq = SOUNDFORMAT_FREQ_SUSPECTED_66200; break; |
1344 | #undef AZF_FMT_XLATE | ||
1345 | } | 1339 | } |
1346 | /* val = 0xff07; 3m27.993s (65301Hz; -> 64000Hz???) hmm, 66120, 65967, 66123 */ | 1340 | /* val = 0xff07; 3m27.993s (65301Hz; -> 64000Hz???) hmm, 66120, 65967, 66123 */ |
1347 | /* val = 0xff09; 17m15.098s (13123,478Hz; -> 12000Hz???) hmm, 13237.2Hz? */ | 1341 | /* val = 0xff09; 17m15.098s (13123,478Hz; -> 12000Hz???) hmm, 13237.2Hz? */ |
diff --git a/sound/pci/hda/hda_eld.c b/sound/pci/hda/hda_eld.c index 4a663471dadc..74b0560289c0 100644 --- a/sound/pci/hda/hda_eld.c +++ b/sound/pci/hda/hda_eld.c | |||
@@ -381,7 +381,7 @@ static void hdmi_show_short_audio_desc(struct cea_sad *a) | |||
381 | snd_print_pcm_rates(a->rates, buf, sizeof(buf)); | 381 | snd_print_pcm_rates(a->rates, buf, sizeof(buf)); |
382 | 382 | ||
383 | if (a->format == AUDIO_CODING_TYPE_LPCM) | 383 | if (a->format == AUDIO_CODING_TYPE_LPCM) |
384 | snd_print_pcm_bits(a->sample_bits, buf2 + 8, sizeof(buf2 - 8)); | 384 | snd_print_pcm_bits(a->sample_bits, buf2 + 8, sizeof(buf2) - 8); |
385 | else if (a->max_bitrate) | 385 | else if (a->max_bitrate) |
386 | snprintf(buf2, sizeof(buf2), | 386 | snprintf(buf2, sizeof(buf2), |
387 | ", max bitrate = %d", a->max_bitrate); | 387 | ", max bitrate = %d", a->max_bitrate); |
diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index 2e91a991eb15..fcedad9a5fef 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c | |||
@@ -2308,6 +2308,7 @@ static struct snd_pci_quirk position_fix_list[] __devinitdata = { | |||
2308 | SND_PCI_QUIRK(0x1043, 0x813d, "ASUS P5AD2", POS_FIX_LPIB), | 2308 | SND_PCI_QUIRK(0x1043, 0x813d, "ASUS P5AD2", POS_FIX_LPIB), |
2309 | SND_PCI_QUIRK(0x1043, 0x81b3, "ASUS", POS_FIX_LPIB), | 2309 | SND_PCI_QUIRK(0x1043, 0x81b3, "ASUS", POS_FIX_LPIB), |
2310 | SND_PCI_QUIRK(0x1043, 0x81e7, "ASUS M2V", POS_FIX_LPIB), | 2310 | SND_PCI_QUIRK(0x1043, 0x81e7, "ASUS M2V", POS_FIX_LPIB), |
2311 | SND_PCI_QUIRK(0x1043, 0x8410, "ASUS", POS_FIX_LPIB), | ||
2311 | SND_PCI_QUIRK(0x104d, 0x9069, "Sony VPCS11V9E", POS_FIX_LPIB), | 2312 | SND_PCI_QUIRK(0x104d, 0x9069, "Sony VPCS11V9E", POS_FIX_LPIB), |
2312 | SND_PCI_QUIRK(0x1106, 0x3288, "ASUS M2V-MX SE", POS_FIX_LPIB), | 2313 | SND_PCI_QUIRK(0x1106, 0x3288, "ASUS M2V-MX SE", POS_FIX_LPIB), |
2313 | SND_PCI_QUIRK(0x1179, 0xff10, "Toshiba A100-259", POS_FIX_LPIB), | 2314 | SND_PCI_QUIRK(0x1179, 0xff10, "Toshiba A100-259", POS_FIX_LPIB), |
@@ -2703,7 +2704,7 @@ static int __devinit azx_probe(struct pci_dev *pci, | |||
2703 | if (err < 0) | 2704 | if (err < 0) |
2704 | goto out_free; | 2705 | goto out_free; |
2705 | #ifdef CONFIG_SND_HDA_PATCH_LOADER | 2706 | #ifdef CONFIG_SND_HDA_PATCH_LOADER |
2706 | if (patch[dev]) { | 2707 | if (patch[dev] && *patch[dev]) { |
2707 | snd_printk(KERN_ERR SFX "Applying patch firmware '%s'\n", | 2708 | snd_printk(KERN_ERR SFX "Applying patch firmware '%s'\n", |
2708 | patch[dev]); | 2709 | patch[dev]); |
2709 | err = snd_hda_load_patch(chip->bus, patch[dev]); | 2710 | err = snd_hda_load_patch(chip->bus, patch[dev]); |
diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c index 9bb030a469cd..dd7c5c12225d 100644 --- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c | |||
@@ -85,6 +85,7 @@ struct conexant_spec { | |||
85 | unsigned int auto_mic; | 85 | unsigned int auto_mic; |
86 | int auto_mic_ext; /* autocfg.inputs[] index for ext mic */ | 86 | int auto_mic_ext; /* autocfg.inputs[] index for ext mic */ |
87 | unsigned int need_dac_fix; | 87 | unsigned int need_dac_fix; |
88 | hda_nid_t slave_dig_outs[2]; | ||
88 | 89 | ||
89 | /* capture */ | 90 | /* capture */ |
90 | unsigned int num_adc_nids; | 91 | unsigned int num_adc_nids; |
@@ -127,6 +128,7 @@ struct conexant_spec { | |||
127 | unsigned int ideapad:1; | 128 | unsigned int ideapad:1; |
128 | unsigned int thinkpad:1; | 129 | unsigned int thinkpad:1; |
129 | unsigned int hp_laptop:1; | 130 | unsigned int hp_laptop:1; |
131 | unsigned int asus:1; | ||
130 | 132 | ||
131 | unsigned int ext_mic_present; | 133 | unsigned int ext_mic_present; |
132 | unsigned int recording; | 134 | unsigned int recording; |
@@ -352,6 +354,8 @@ static int conexant_build_pcms(struct hda_codec *codec) | |||
352 | info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = | 354 | info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = |
353 | spec->dig_in_nid; | 355 | spec->dig_in_nid; |
354 | } | 356 | } |
357 | if (spec->slave_dig_outs[0]) | ||
358 | codec->slave_dig_outs = spec->slave_dig_outs; | ||
355 | } | 359 | } |
356 | 360 | ||
357 | return 0; | 361 | return 0; |
@@ -403,10 +407,16 @@ static int conexant_add_jack(struct hda_codec *codec, | |||
403 | struct conexant_spec *spec; | 407 | struct conexant_spec *spec; |
404 | struct conexant_jack *jack; | 408 | struct conexant_jack *jack; |
405 | const char *name; | 409 | const char *name; |
406 | int err; | 410 | int i, err; |
407 | 411 | ||
408 | spec = codec->spec; | 412 | spec = codec->spec; |
409 | snd_array_init(&spec->jacks, sizeof(*jack), 32); | 413 | snd_array_init(&spec->jacks, sizeof(*jack), 32); |
414 | |||
415 | jack = spec->jacks.list; | ||
416 | for (i = 0; i < spec->jacks.used; i++, jack++) | ||
417 | if (jack->nid == nid) | ||
418 | return 0 ; /* already present */ | ||
419 | |||
410 | jack = snd_array_new(&spec->jacks); | 420 | jack = snd_array_new(&spec->jacks); |
411 | name = (type == SND_JACK_HEADPHONE) ? "Headphone" : "Mic" ; | 421 | name = (type == SND_JACK_HEADPHONE) ? "Headphone" : "Mic" ; |
412 | 422 | ||
@@ -2100,7 +2110,7 @@ static int patch_cxt5051(struct hda_codec *codec) | |||
2100 | static hda_nid_t cxt5066_dac_nids[1] = { 0x10 }; | 2110 | static hda_nid_t cxt5066_dac_nids[1] = { 0x10 }; |
2101 | static hda_nid_t cxt5066_adc_nids[3] = { 0x14, 0x15, 0x16 }; | 2111 | static hda_nid_t cxt5066_adc_nids[3] = { 0x14, 0x15, 0x16 }; |
2102 | static hda_nid_t cxt5066_capsrc_nids[1] = { 0x17 }; | 2112 | static hda_nid_t cxt5066_capsrc_nids[1] = { 0x17 }; |
2103 | #define CXT5066_SPDIF_OUT 0x21 | 2113 | static hda_nid_t cxt5066_digout_pin_nids[2] = { 0x20, 0x22 }; |
2104 | 2114 | ||
2105 | /* OLPC's microphone port is DC coupled for use with external sensors, | 2115 | /* OLPC's microphone port is DC coupled for use with external sensors, |
2106 | * therefore we use a 50% mic bias in order to center the input signal with | 2116 | * therefore we use a 50% mic bias in order to center the input signal with |
@@ -2312,6 +2322,19 @@ static void cxt5066_ideapad_automic(struct hda_codec *codec) | |||
2312 | } | 2322 | } |
2313 | } | 2323 | } |
2314 | 2324 | ||
2325 | |||
2326 | /* toggle input of built-in digital mic and mic jack appropriately */ | ||
2327 | static void cxt5066_asus_automic(struct hda_codec *codec) | ||
2328 | { | ||
2329 | unsigned int present; | ||
2330 | |||
2331 | present = snd_hda_jack_detect(codec, 0x1b); | ||
2332 | snd_printdd("CXT5066: external microphone present=%d\n", present); | ||
2333 | snd_hda_codec_write(codec, 0x17, 0, AC_VERB_SET_CONNECT_SEL, | ||
2334 | present ? 1 : 0); | ||
2335 | } | ||
2336 | |||
2337 | |||
2315 | /* toggle input of built-in digital mic and mic jack appropriately */ | 2338 | /* toggle input of built-in digital mic and mic jack appropriately */ |
2316 | static void cxt5066_hp_laptop_automic(struct hda_codec *codec) | 2339 | static void cxt5066_hp_laptop_automic(struct hda_codec *codec) |
2317 | { | 2340 | { |
@@ -2387,79 +2410,55 @@ static void cxt5066_hp_automute(struct hda_codec *codec) | |||
2387 | cxt5066_update_speaker(codec); | 2410 | cxt5066_update_speaker(codec); |
2388 | } | 2411 | } |
2389 | 2412 | ||
2390 | /* unsolicited event for jack sensing */ | 2413 | /* Dispatch the right mic autoswitch function */ |
2391 | static void cxt5066_olpc_unsol_event(struct hda_codec *codec, unsigned int res) | 2414 | static void cxt5066_automic(struct hda_codec *codec) |
2392 | { | 2415 | { |
2393 | struct conexant_spec *spec = codec->spec; | 2416 | struct conexant_spec *spec = codec->spec; |
2394 | snd_printdd("CXT5066: unsol event %x (%x)\n", res, res >> 26); | ||
2395 | switch (res >> 26) { | ||
2396 | case CONEXANT_HP_EVENT: | ||
2397 | cxt5066_hp_automute(codec); | ||
2398 | break; | ||
2399 | case CONEXANT_MIC_EVENT: | ||
2400 | /* ignore mic events in DC mode; we're always using the jack */ | ||
2401 | if (!spec->dc_enable) | ||
2402 | cxt5066_olpc_automic(codec); | ||
2403 | break; | ||
2404 | } | ||
2405 | } | ||
2406 | 2417 | ||
2407 | /* unsolicited event for jack sensing */ | 2418 | if (spec->dell_vostro) |
2408 | static void cxt5066_vostro_event(struct hda_codec *codec, unsigned int res) | ||
2409 | { | ||
2410 | snd_printdd("CXT5066_vostro: unsol event %x (%x)\n", res, res >> 26); | ||
2411 | switch (res >> 26) { | ||
2412 | case CONEXANT_HP_EVENT: | ||
2413 | cxt5066_hp_automute(codec); | ||
2414 | break; | ||
2415 | case CONEXANT_MIC_EVENT: | ||
2416 | cxt5066_vostro_automic(codec); | 2419 | cxt5066_vostro_automic(codec); |
2417 | break; | 2420 | else if (spec->ideapad) |
2418 | } | ||
2419 | } | ||
2420 | |||
2421 | /* unsolicited event for jack sensing */ | ||
2422 | static void cxt5066_ideapad_event(struct hda_codec *codec, unsigned int res) | ||
2423 | { | ||
2424 | snd_printdd("CXT5066_ideapad: unsol event %x (%x)\n", res, res >> 26); | ||
2425 | switch (res >> 26) { | ||
2426 | case CONEXANT_HP_EVENT: | ||
2427 | cxt5066_hp_automute(codec); | ||
2428 | break; | ||
2429 | case CONEXANT_MIC_EVENT: | ||
2430 | cxt5066_ideapad_automic(codec); | 2421 | cxt5066_ideapad_automic(codec); |
2431 | break; | 2422 | else if (spec->thinkpad) |
2432 | } | 2423 | cxt5066_thinkpad_automic(codec); |
2424 | else if (spec->hp_laptop) | ||
2425 | cxt5066_hp_laptop_automic(codec); | ||
2426 | else if (spec->asus) | ||
2427 | cxt5066_asus_automic(codec); | ||
2433 | } | 2428 | } |
2434 | 2429 | ||
2435 | /* unsolicited event for jack sensing */ | 2430 | /* unsolicited event for jack sensing */ |
2436 | static void cxt5066_hp_laptop_event(struct hda_codec *codec, unsigned int res) | 2431 | static void cxt5066_olpc_unsol_event(struct hda_codec *codec, unsigned int res) |
2437 | { | 2432 | { |
2438 | snd_printdd("CXT5066_hp_laptop: unsol event %x (%x)\n", res, res >> 26); | 2433 | struct conexant_spec *spec = codec->spec; |
2434 | snd_printdd("CXT5066: unsol event %x (%x)\n", res, res >> 26); | ||
2439 | switch (res >> 26) { | 2435 | switch (res >> 26) { |
2440 | case CONEXANT_HP_EVENT: | 2436 | case CONEXANT_HP_EVENT: |
2441 | cxt5066_hp_automute(codec); | 2437 | cxt5066_hp_automute(codec); |
2442 | break; | 2438 | break; |
2443 | case CONEXANT_MIC_EVENT: | 2439 | case CONEXANT_MIC_EVENT: |
2444 | cxt5066_hp_laptop_automic(codec); | 2440 | /* ignore mic events in DC mode; we're always using the jack */ |
2441 | if (!spec->dc_enable) | ||
2442 | cxt5066_olpc_automic(codec); | ||
2445 | break; | 2443 | break; |
2446 | } | 2444 | } |
2447 | } | 2445 | } |
2448 | 2446 | ||
2449 | /* unsolicited event for jack sensing */ | 2447 | /* unsolicited event for jack sensing */ |
2450 | static void cxt5066_thinkpad_event(struct hda_codec *codec, unsigned int res) | 2448 | static void cxt5066_unsol_event(struct hda_codec *codec, unsigned int res) |
2451 | { | 2449 | { |
2452 | snd_printdd("CXT5066_thinkpad: unsol event %x (%x)\n", res, res >> 26); | 2450 | snd_printdd("CXT5066: unsol event %x (%x)\n", res, res >> 26); |
2453 | switch (res >> 26) { | 2451 | switch (res >> 26) { |
2454 | case CONEXANT_HP_EVENT: | 2452 | case CONEXANT_HP_EVENT: |
2455 | cxt5066_hp_automute(codec); | 2453 | cxt5066_hp_automute(codec); |
2456 | break; | 2454 | break; |
2457 | case CONEXANT_MIC_EVENT: | 2455 | case CONEXANT_MIC_EVENT: |
2458 | cxt5066_thinkpad_automic(codec); | 2456 | cxt5066_automic(codec); |
2459 | break; | 2457 | break; |
2460 | } | 2458 | } |
2461 | } | 2459 | } |
2462 | 2460 | ||
2461 | |||
2463 | static const struct hda_input_mux cxt5066_analog_mic_boost = { | 2462 | static const struct hda_input_mux cxt5066_analog_mic_boost = { |
2464 | .num_items = 5, | 2463 | .num_items = 5, |
2465 | .items = { | 2464 | .items = { |
@@ -2633,6 +2632,27 @@ static void cxt5066_olpc_capture_cleanup(struct hda_codec *codec) | |||
2633 | spec->recording = 0; | 2632 | spec->recording = 0; |
2634 | } | 2633 | } |
2635 | 2634 | ||
2635 | static void conexant_check_dig_outs(struct hda_codec *codec, | ||
2636 | hda_nid_t *dig_pins, | ||
2637 | int num_pins) | ||
2638 | { | ||
2639 | struct conexant_spec *spec = codec->spec; | ||
2640 | hda_nid_t *nid_loc = &spec->multiout.dig_out_nid; | ||
2641 | int i; | ||
2642 | |||
2643 | for (i = 0; i < num_pins; i++, dig_pins++) { | ||
2644 | unsigned int cfg = snd_hda_codec_get_pincfg(codec, *dig_pins); | ||
2645 | if (get_defcfg_connect(cfg) == AC_JACK_PORT_NONE) | ||
2646 | continue; | ||
2647 | if (snd_hda_get_connections(codec, *dig_pins, nid_loc, 1) != 1) | ||
2648 | continue; | ||
2649 | if (spec->slave_dig_outs[0]) | ||
2650 | nid_loc++; | ||
2651 | else | ||
2652 | nid_loc = spec->slave_dig_outs; | ||
2653 | } | ||
2654 | } | ||
2655 | |||
2636 | static struct hda_input_mux cxt5066_capture_source = { | 2656 | static struct hda_input_mux cxt5066_capture_source = { |
2637 | .num_items = 4, | 2657 | .num_items = 4, |
2638 | .items = { | 2658 | .items = { |
@@ -3039,20 +3059,11 @@ static struct hda_verb cxt5066_init_verbs_hp_laptop[] = { | |||
3039 | /* initialize jack-sensing, too */ | 3059 | /* initialize jack-sensing, too */ |
3040 | static int cxt5066_init(struct hda_codec *codec) | 3060 | static int cxt5066_init(struct hda_codec *codec) |
3041 | { | 3061 | { |
3042 | struct conexant_spec *spec = codec->spec; | ||
3043 | |||
3044 | snd_printdd("CXT5066: init\n"); | 3062 | snd_printdd("CXT5066: init\n"); |
3045 | conexant_init(codec); | 3063 | conexant_init(codec); |
3046 | if (codec->patch_ops.unsol_event) { | 3064 | if (codec->patch_ops.unsol_event) { |
3047 | cxt5066_hp_automute(codec); | 3065 | cxt5066_hp_automute(codec); |
3048 | if (spec->dell_vostro) | 3066 | cxt5066_automic(codec); |
3049 | cxt5066_vostro_automic(codec); | ||
3050 | else if (spec->ideapad) | ||
3051 | cxt5066_ideapad_automic(codec); | ||
3052 | else if (spec->thinkpad) | ||
3053 | cxt5066_thinkpad_automic(codec); | ||
3054 | else if (spec->hp_laptop) | ||
3055 | cxt5066_hp_laptop_automic(codec); | ||
3056 | } | 3067 | } |
3057 | cxt5066_set_mic_boost(codec); | 3068 | cxt5066_set_mic_boost(codec); |
3058 | return 0; | 3069 | return 0; |
@@ -3080,6 +3091,7 @@ enum { | |||
3080 | CXT5066_DELL_VOSTRO, /* Dell Vostro 1015i */ | 3091 | CXT5066_DELL_VOSTRO, /* Dell Vostro 1015i */ |
3081 | CXT5066_IDEAPAD, /* Lenovo IdeaPad U150 */ | 3092 | CXT5066_IDEAPAD, /* Lenovo IdeaPad U150 */ |
3082 | CXT5066_THINKPAD, /* Lenovo ThinkPad T410s, others? */ | 3093 | CXT5066_THINKPAD, /* Lenovo ThinkPad T410s, others? */ |
3094 | CXT5066_ASUS, /* Asus K52JU, Lenovo G560 - Int mic at 0x1a and Ext mic at 0x1b */ | ||
3083 | CXT5066_HP_LAPTOP, /* HP Laptop */ | 3095 | CXT5066_HP_LAPTOP, /* HP Laptop */ |
3084 | CXT5066_MODELS | 3096 | CXT5066_MODELS |
3085 | }; | 3097 | }; |
@@ -3091,6 +3103,7 @@ static const char * const cxt5066_models[CXT5066_MODELS] = { | |||
3091 | [CXT5066_DELL_VOSTRO] = "dell-vostro", | 3103 | [CXT5066_DELL_VOSTRO] = "dell-vostro", |
3092 | [CXT5066_IDEAPAD] = "ideapad", | 3104 | [CXT5066_IDEAPAD] = "ideapad", |
3093 | [CXT5066_THINKPAD] = "thinkpad", | 3105 | [CXT5066_THINKPAD] = "thinkpad", |
3106 | [CXT5066_ASUS] = "asus", | ||
3094 | [CXT5066_HP_LAPTOP] = "hp-laptop", | 3107 | [CXT5066_HP_LAPTOP] = "hp-laptop", |
3095 | }; | 3108 | }; |
3096 | 3109 | ||
@@ -3102,7 +3115,9 @@ static struct snd_pci_quirk cxt5066_cfg_tbl[] = { | |||
3102 | SND_PCI_QUIRK(0x1028, 0x0402, "Dell Vostro", CXT5066_DELL_VOSTRO), | 3115 | SND_PCI_QUIRK(0x1028, 0x0402, "Dell Vostro", CXT5066_DELL_VOSTRO), |
3103 | SND_PCI_QUIRK(0x1028, 0x0408, "Dell Inspiron One 19T", CXT5066_IDEAPAD), | 3116 | SND_PCI_QUIRK(0x1028, 0x0408, "Dell Inspiron One 19T", CXT5066_IDEAPAD), |
3104 | SND_PCI_QUIRK(0x103c, 0x360b, "HP G60", CXT5066_HP_LAPTOP), | 3117 | SND_PCI_QUIRK(0x103c, 0x360b, "HP G60", CXT5066_HP_LAPTOP), |
3105 | SND_PCI_QUIRK(0x1043, 0x13f3, "Asus A52J", CXT5066_HP_LAPTOP), | 3118 | SND_PCI_QUIRK(0x1043, 0x13f3, "Asus A52J", CXT5066_ASUS), |
3119 | SND_PCI_QUIRK(0x1043, 0x1643, "Asus K52JU", CXT5066_ASUS), | ||
3120 | SND_PCI_QUIRK(0x1043, 0x1993, "Asus U50F", CXT5066_ASUS), | ||
3106 | SND_PCI_QUIRK(0x1179, 0xff1e, "Toshiba Satellite C650D", CXT5066_IDEAPAD), | 3121 | SND_PCI_QUIRK(0x1179, 0xff1e, "Toshiba Satellite C650D", CXT5066_IDEAPAD), |
3107 | SND_PCI_QUIRK(0x1179, 0xff50, "Toshiba Satellite P500-PSPGSC-01800T", CXT5066_OLPC_XO_1_5), | 3122 | SND_PCI_QUIRK(0x1179, 0xff50, "Toshiba Satellite P500-PSPGSC-01800T", CXT5066_OLPC_XO_1_5), |
3108 | SND_PCI_QUIRK(0x1179, 0xffe0, "Toshiba Satellite Pro T130-15F", CXT5066_OLPC_XO_1_5), | 3123 | SND_PCI_QUIRK(0x1179, 0xffe0, "Toshiba Satellite Pro T130-15F", CXT5066_OLPC_XO_1_5), |
@@ -3111,7 +3126,9 @@ static struct snd_pci_quirk cxt5066_cfg_tbl[] = { | |||
3111 | SND_PCI_QUIRK(0x152d, 0x0833, "OLPC XO-1.5", CXT5066_OLPC_XO_1_5), | 3126 | SND_PCI_QUIRK(0x152d, 0x0833, "OLPC XO-1.5", CXT5066_OLPC_XO_1_5), |
3112 | SND_PCI_QUIRK(0x17aa, 0x20f2, "Lenovo T400s", CXT5066_THINKPAD), | 3127 | SND_PCI_QUIRK(0x17aa, 0x20f2, "Lenovo T400s", CXT5066_THINKPAD), |
3113 | SND_PCI_QUIRK(0x17aa, 0x21c5, "Thinkpad Edge 13", CXT5066_THINKPAD), | 3128 | SND_PCI_QUIRK(0x17aa, 0x21c5, "Thinkpad Edge 13", CXT5066_THINKPAD), |
3129 | SND_PCI_QUIRK(0x17aa, 0x21c6, "Thinkpad Edge 13", CXT5066_ASUS), | ||
3114 | SND_PCI_QUIRK(0x17aa, 0x215e, "Lenovo Thinkpad", CXT5066_THINKPAD), | 3130 | SND_PCI_QUIRK(0x17aa, 0x215e, "Lenovo Thinkpad", CXT5066_THINKPAD), |
3131 | SND_PCI_QUIRK(0x17aa, 0x38af, "Lenovo G560", CXT5066_ASUS), | ||
3115 | SND_PCI_QUIRK_VENDOR(0x17aa, "Lenovo", CXT5066_IDEAPAD), /* Fallback for Lenovos without dock mic */ | 3132 | SND_PCI_QUIRK_VENDOR(0x17aa, "Lenovo", CXT5066_IDEAPAD), /* Fallback for Lenovos without dock mic */ |
3116 | {} | 3133 | {} |
3117 | }; | 3134 | }; |
@@ -3133,7 +3150,8 @@ static int patch_cxt5066(struct hda_codec *codec) | |||
3133 | spec->multiout.max_channels = 2; | 3150 | spec->multiout.max_channels = 2; |
3134 | spec->multiout.num_dacs = ARRAY_SIZE(cxt5066_dac_nids); | 3151 | spec->multiout.num_dacs = ARRAY_SIZE(cxt5066_dac_nids); |
3135 | spec->multiout.dac_nids = cxt5066_dac_nids; | 3152 | spec->multiout.dac_nids = cxt5066_dac_nids; |
3136 | spec->multiout.dig_out_nid = CXT5066_SPDIF_OUT; | 3153 | conexant_check_dig_outs(codec, cxt5066_digout_pin_nids, |
3154 | ARRAY_SIZE(cxt5066_digout_pin_nids)); | ||
3137 | spec->num_adc_nids = 1; | 3155 | spec->num_adc_nids = 1; |
3138 | spec->adc_nids = cxt5066_adc_nids; | 3156 | spec->adc_nids = cxt5066_adc_nids; |
3139 | spec->capsrc_nids = cxt5066_capsrc_nids; | 3157 | spec->capsrc_nids = cxt5066_capsrc_nids; |
@@ -3167,17 +3185,20 @@ static int patch_cxt5066(struct hda_codec *codec) | |||
3167 | spec->num_init_verbs++; | 3185 | spec->num_init_verbs++; |
3168 | spec->dell_automute = 1; | 3186 | spec->dell_automute = 1; |
3169 | break; | 3187 | break; |
3188 | case CXT5066_ASUS: | ||
3170 | case CXT5066_HP_LAPTOP: | 3189 | case CXT5066_HP_LAPTOP: |
3171 | codec->patch_ops.init = cxt5066_init; | 3190 | codec->patch_ops.init = cxt5066_init; |
3172 | codec->patch_ops.unsol_event = cxt5066_hp_laptop_event; | 3191 | codec->patch_ops.unsol_event = cxt5066_unsol_event; |
3173 | spec->init_verbs[spec->num_init_verbs] = | 3192 | spec->init_verbs[spec->num_init_verbs] = |
3174 | cxt5066_init_verbs_hp_laptop; | 3193 | cxt5066_init_verbs_hp_laptop; |
3175 | spec->num_init_verbs++; | 3194 | spec->num_init_verbs++; |
3176 | spec->hp_laptop = 1; | 3195 | spec->hp_laptop = board_config == CXT5066_HP_LAPTOP; |
3196 | spec->asus = board_config == CXT5066_ASUS; | ||
3177 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; | 3197 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; |
3178 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; | 3198 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; |
3179 | /* no S/PDIF out */ | 3199 | /* no S/PDIF out */ |
3180 | spec->multiout.dig_out_nid = 0; | 3200 | if (board_config == CXT5066_HP_LAPTOP) |
3201 | spec->multiout.dig_out_nid = 0; | ||
3181 | /* input source automatically selected */ | 3202 | /* input source automatically selected */ |
3182 | spec->input_mux = NULL; | 3203 | spec->input_mux = NULL; |
3183 | spec->port_d_mode = 0; | 3204 | spec->port_d_mode = 0; |
@@ -3207,7 +3228,7 @@ static int patch_cxt5066(struct hda_codec *codec) | |||
3207 | break; | 3228 | break; |
3208 | case CXT5066_DELL_VOSTRO: | 3229 | case CXT5066_DELL_VOSTRO: |
3209 | codec->patch_ops.init = cxt5066_init; | 3230 | codec->patch_ops.init = cxt5066_init; |
3210 | codec->patch_ops.unsol_event = cxt5066_vostro_event; | 3231 | codec->patch_ops.unsol_event = cxt5066_unsol_event; |
3211 | spec->init_verbs[0] = cxt5066_init_verbs_vostro; | 3232 | spec->init_verbs[0] = cxt5066_init_verbs_vostro; |
3212 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master_olpc; | 3233 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master_olpc; |
3213 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; | 3234 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; |
@@ -3224,7 +3245,7 @@ static int patch_cxt5066(struct hda_codec *codec) | |||
3224 | break; | 3245 | break; |
3225 | case CXT5066_IDEAPAD: | 3246 | case CXT5066_IDEAPAD: |
3226 | codec->patch_ops.init = cxt5066_init; | 3247 | codec->patch_ops.init = cxt5066_init; |
3227 | codec->patch_ops.unsol_event = cxt5066_ideapad_event; | 3248 | codec->patch_ops.unsol_event = cxt5066_unsol_event; |
3228 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; | 3249 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; |
3229 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; | 3250 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; |
3230 | spec->init_verbs[0] = cxt5066_init_verbs_ideapad; | 3251 | spec->init_verbs[0] = cxt5066_init_verbs_ideapad; |
@@ -3240,7 +3261,7 @@ static int patch_cxt5066(struct hda_codec *codec) | |||
3240 | break; | 3261 | break; |
3241 | case CXT5066_THINKPAD: | 3262 | case CXT5066_THINKPAD: |
3242 | codec->patch_ops.init = cxt5066_init; | 3263 | codec->patch_ops.init = cxt5066_init; |
3243 | codec->patch_ops.unsol_event = cxt5066_thinkpad_event; | 3264 | codec->patch_ops.unsol_event = cxt5066_unsol_event; |
3244 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; | 3265 | spec->mixers[spec->num_mixers++] = cxt5066_mixer_master; |
3245 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; | 3266 | spec->mixers[spec->num_mixers++] = cxt5066_mixers; |
3246 | spec->init_verbs[0] = cxt5066_init_verbs_thinkpad; | 3267 | spec->init_verbs[0] = cxt5066_init_verbs_thinkpad; |
@@ -3389,7 +3410,7 @@ static void cx_auto_parse_output(struct hda_codec *codec) | |||
3389 | } | 3410 | } |
3390 | } | 3411 | } |
3391 | spec->multiout.dac_nids = spec->private_dac_nids; | 3412 | spec->multiout.dac_nids = spec->private_dac_nids; |
3392 | spec->multiout.max_channels = nums * 2; | 3413 | spec->multiout.max_channels = spec->multiout.num_dacs * 2; |
3393 | 3414 | ||
3394 | if (cfg->hp_outs > 0) | 3415 | if (cfg->hp_outs > 0) |
3395 | spec->auto_mute = 1; | 3416 | spec->auto_mute = 1; |
@@ -3708,9 +3729,9 @@ static int cx_auto_init(struct hda_codec *codec) | |||
3708 | return 0; | 3729 | return 0; |
3709 | } | 3730 | } |
3710 | 3731 | ||
3711 | static int cx_auto_add_volume(struct hda_codec *codec, const char *basename, | 3732 | static int cx_auto_add_volume_idx(struct hda_codec *codec, const char *basename, |
3712 | const char *dir, int cidx, | 3733 | const char *dir, int cidx, |
3713 | hda_nid_t nid, int hda_dir) | 3734 | hda_nid_t nid, int hda_dir, int amp_idx) |
3714 | { | 3735 | { |
3715 | static char name[32]; | 3736 | static char name[32]; |
3716 | static struct snd_kcontrol_new knew[] = { | 3737 | static struct snd_kcontrol_new knew[] = { |
@@ -3722,7 +3743,8 @@ static int cx_auto_add_volume(struct hda_codec *codec, const char *basename, | |||
3722 | 3743 | ||
3723 | for (i = 0; i < 2; i++) { | 3744 | for (i = 0; i < 2; i++) { |
3724 | struct snd_kcontrol *kctl; | 3745 | struct snd_kcontrol *kctl; |
3725 | knew[i].private_value = HDA_COMPOSE_AMP_VAL(nid, 3, 0, hda_dir); | 3746 | knew[i].private_value = HDA_COMPOSE_AMP_VAL(nid, 3, amp_idx, |
3747 | hda_dir); | ||
3726 | knew[i].subdevice = HDA_SUBDEV_AMP_FLAG; | 3748 | knew[i].subdevice = HDA_SUBDEV_AMP_FLAG; |
3727 | knew[i].index = cidx; | 3749 | knew[i].index = cidx; |
3728 | snprintf(name, sizeof(name), "%s%s %s", basename, dir, sfx[i]); | 3750 | snprintf(name, sizeof(name), "%s%s %s", basename, dir, sfx[i]); |
@@ -3738,6 +3760,9 @@ static int cx_auto_add_volume(struct hda_codec *codec, const char *basename, | |||
3738 | return 0; | 3760 | return 0; |
3739 | } | 3761 | } |
3740 | 3762 | ||
3763 | #define cx_auto_add_volume(codec, str, dir, cidx, nid, hda_dir) \ | ||
3764 | cx_auto_add_volume_idx(codec, str, dir, cidx, nid, hda_dir, 0) | ||
3765 | |||
3741 | #define cx_auto_add_pb_volume(codec, nid, str, idx) \ | 3766 | #define cx_auto_add_pb_volume(codec, nid, str, idx) \ |
3742 | cx_auto_add_volume(codec, str, " Playback", idx, nid, HDA_OUTPUT) | 3767 | cx_auto_add_volume(codec, str, " Playback", idx, nid, HDA_OUTPUT) |
3743 | 3768 | ||
@@ -3787,29 +3812,60 @@ static int cx_auto_build_input_controls(struct hda_codec *codec) | |||
3787 | struct conexant_spec *spec = codec->spec; | 3812 | struct conexant_spec *spec = codec->spec; |
3788 | struct auto_pin_cfg *cfg = &spec->autocfg; | 3813 | struct auto_pin_cfg *cfg = &spec->autocfg; |
3789 | static const char *prev_label; | 3814 | static const char *prev_label; |
3790 | int i, err, cidx; | 3815 | int i, err, cidx, conn_len; |
3816 | hda_nid_t conn[HDA_MAX_CONNECTIONS]; | ||
3817 | |||
3818 | int multi_adc_volume = 0; /* If the ADC nid has several input volumes */ | ||
3819 | int adc_nid = spec->adc_nids[0]; | ||
3820 | |||
3821 | conn_len = snd_hda_get_connections(codec, adc_nid, conn, | ||
3822 | HDA_MAX_CONNECTIONS); | ||
3823 | if (conn_len < 0) | ||
3824 | return conn_len; | ||
3825 | |||
3826 | multi_adc_volume = cfg->num_inputs > 1 && conn_len > 1; | ||
3827 | if (!multi_adc_volume) { | ||
3828 | err = cx_auto_add_volume(codec, "Capture", "", 0, adc_nid, | ||
3829 | HDA_INPUT); | ||
3830 | if (err < 0) | ||
3831 | return err; | ||
3832 | } | ||
3791 | 3833 | ||
3792 | err = cx_auto_add_volume(codec, "Capture", "", 0, spec->adc_nids[0], | ||
3793 | HDA_INPUT); | ||
3794 | if (err < 0) | ||
3795 | return err; | ||
3796 | prev_label = NULL; | 3834 | prev_label = NULL; |
3797 | cidx = 0; | 3835 | cidx = 0; |
3798 | for (i = 0; i < cfg->num_inputs; i++) { | 3836 | for (i = 0; i < cfg->num_inputs; i++) { |
3799 | hda_nid_t nid = cfg->inputs[i].pin; | 3837 | hda_nid_t nid = cfg->inputs[i].pin; |
3800 | const char *label; | 3838 | const char *label; |
3801 | if (!(get_wcaps(codec, nid) & AC_WCAP_IN_AMP)) | 3839 | int j; |
3840 | int pin_amp = get_wcaps(codec, nid) & AC_WCAP_IN_AMP; | ||
3841 | if (!pin_amp && !multi_adc_volume) | ||
3802 | continue; | 3842 | continue; |
3843 | |||
3803 | label = hda_get_autocfg_input_label(codec, cfg, i); | 3844 | label = hda_get_autocfg_input_label(codec, cfg, i); |
3804 | if (label == prev_label) | 3845 | if (label == prev_label) |
3805 | cidx++; | 3846 | cidx++; |
3806 | else | 3847 | else |
3807 | cidx = 0; | 3848 | cidx = 0; |
3808 | prev_label = label; | 3849 | prev_label = label; |
3809 | err = cx_auto_add_volume(codec, label, " Capture", cidx, | 3850 | |
3810 | nid, HDA_INPUT); | 3851 | if (pin_amp) { |
3811 | if (err < 0) | 3852 | err = cx_auto_add_volume(codec, label, " Boost", cidx, |
3812 | return err; | 3853 | nid, HDA_INPUT); |
3854 | if (err < 0) | ||
3855 | return err; | ||
3856 | } | ||
3857 | |||
3858 | if (!multi_adc_volume) | ||
3859 | continue; | ||
3860 | for (j = 0; j < conn_len; j++) { | ||
3861 | if (conn[j] == nid) { | ||
3862 | err = cx_auto_add_volume_idx(codec, label, | ||
3863 | " Capture", cidx, adc_nid, HDA_INPUT, j); | ||
3864 | if (err < 0) | ||
3865 | return err; | ||
3866 | break; | ||
3867 | } | ||
3868 | } | ||
3813 | } | 3869 | } |
3814 | return 0; | 3870 | return 0; |
3815 | } | 3871 | } |
diff --git a/sound/pci/hda/patch_hdmi.c b/sound/pci/hda/patch_hdmi.c index 2d5b83fa8d24..a58767736727 100644 --- a/sound/pci/hda/patch_hdmi.c +++ b/sound/pci/hda/patch_hdmi.c | |||
@@ -642,6 +642,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec, hda_nid_t nid, | |||
642 | hdmi_ai->ver = 0x01; | 642 | hdmi_ai->ver = 0x01; |
643 | hdmi_ai->len = 0x0a; | 643 | hdmi_ai->len = 0x0a; |
644 | hdmi_ai->CC02_CT47 = channels - 1; | 644 | hdmi_ai->CC02_CT47 = channels - 1; |
645 | hdmi_ai->CA = ca; | ||
645 | hdmi_checksum_audio_infoframe(hdmi_ai); | 646 | hdmi_checksum_audio_infoframe(hdmi_ai); |
646 | } else if (spec->sink_eld[i].conn_type == 1) { /* DisplayPort */ | 647 | } else if (spec->sink_eld[i].conn_type == 1) { /* DisplayPort */ |
647 | struct dp_audio_infoframe *dp_ai; | 648 | struct dp_audio_infoframe *dp_ai; |
@@ -651,6 +652,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec, hda_nid_t nid, | |||
651 | dp_ai->len = 0x1b; | 652 | dp_ai->len = 0x1b; |
652 | dp_ai->ver = 0x11 << 2; | 653 | dp_ai->ver = 0x11 << 2; |
653 | dp_ai->CC02_CT47 = channels - 1; | 654 | dp_ai->CC02_CT47 = channels - 1; |
655 | dp_ai->CA = ca; | ||
654 | } else { | 656 | } else { |
655 | snd_printd("HDMI: unknown connection type at pin %d\n", | 657 | snd_printd("HDMI: unknown connection type at pin %d\n", |
656 | pin_nid); | 658 | pin_nid); |
diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 7169c9a4d0b0..c5208c90784b 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c | |||
@@ -2290,6 +2290,29 @@ static struct snd_kcontrol_new alc888_base_mixer[] = { | |||
2290 | { } /* end */ | 2290 | { } /* end */ |
2291 | }; | 2291 | }; |
2292 | 2292 | ||
2293 | static struct snd_kcontrol_new alc888_acer_aspire_4930g_mixer[] = { | ||
2294 | HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | ||
2295 | HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), | ||
2296 | HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT), | ||
2297 | HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT), | ||
2298 | HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0f, 2, 0x0, | ||
2299 | HDA_OUTPUT), | ||
2300 | HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0f, 2, 2, HDA_INPUT), | ||
2301 | HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0f, 1, 0x0, HDA_OUTPUT), | ||
2302 | HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0f, 1, 2, HDA_INPUT), | ||
2303 | HDA_CODEC_VOLUME("Side Playback Volume", 0x0e, 0x0, HDA_OUTPUT), | ||
2304 | HDA_BIND_MUTE("Side Playback Switch", 0x0e, 2, HDA_INPUT), | ||
2305 | HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT), | ||
2306 | HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT), | ||
2307 | HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT), | ||
2308 | HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT), | ||
2309 | HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | ||
2310 | HDA_CODEC_VOLUME("Mic Boost Volume", 0x18, 0, HDA_INPUT), | ||
2311 | HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | ||
2312 | { } /* end */ | ||
2313 | }; | ||
2314 | |||
2315 | |||
2293 | static struct snd_kcontrol_new alc889_acer_aspire_8930g_mixer[] = { | 2316 | static struct snd_kcontrol_new alc889_acer_aspire_8930g_mixer[] = { |
2294 | HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | 2317 | HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), |
2295 | HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), | 2318 | HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), |
@@ -10359,7 +10382,7 @@ static struct alc_config_preset alc882_presets[] = { | |||
10359 | .init_hook = alc_automute_amp, | 10382 | .init_hook = alc_automute_amp, |
10360 | }, | 10383 | }, |
10361 | [ALC888_ACER_ASPIRE_4930G] = { | 10384 | [ALC888_ACER_ASPIRE_4930G] = { |
10362 | .mixers = { alc888_base_mixer, | 10385 | .mixers = { alc888_acer_aspire_4930g_mixer, |
10363 | alc883_chmode_mixer }, | 10386 | alc883_chmode_mixer }, |
10364 | .init_verbs = { alc883_init_verbs, alc880_gpio1_init_verbs, | 10387 | .init_verbs = { alc883_init_verbs, alc880_gpio1_init_verbs, |
10365 | alc888_acer_aspire_4930g_verbs }, | 10388 | alc888_acer_aspire_4930g_verbs }, |
@@ -14954,9 +14977,11 @@ static struct snd_pci_quirk alc269_fixup_tbl[] = { | |||
14954 | SND_PCI_QUIRK(0x104d, 0x9084, "Sony VAIO", ALC275_FIXUP_SONY_HWEQ), | 14977 | SND_PCI_QUIRK(0x104d, 0x9084, "Sony VAIO", ALC275_FIXUP_SONY_HWEQ), |
14955 | SND_PCI_QUIRK_VENDOR(0x104d, "Sony VAIO", ALC269_FIXUP_SONY_VAIO), | 14978 | SND_PCI_QUIRK_VENDOR(0x104d, "Sony VAIO", ALC269_FIXUP_SONY_VAIO), |
14956 | SND_PCI_QUIRK(0x1028, 0x0470, "Dell M101z", ALC269_FIXUP_DELL_M101Z), | 14979 | SND_PCI_QUIRK(0x1028, 0x0470, "Dell M101z", ALC269_FIXUP_DELL_M101Z), |
14957 | SND_PCI_QUIRK(0x17aa, 0x21b8, "Thinkpad Edge 14", ALC269_FIXUP_SKU_IGNORE), | ||
14958 | SND_PCI_QUIRK(0x17aa, 0x21e9, "Thinkpad Edge 14", ALC269_FIXUP_SKU_IGNORE), | ||
14959 | SND_PCI_QUIRK(0x17aa, 0x20f2, "Thinkpad SL410/510", ALC269_FIXUP_SKU_IGNORE), | 14980 | SND_PCI_QUIRK(0x17aa, 0x20f2, "Thinkpad SL410/510", ALC269_FIXUP_SKU_IGNORE), |
14981 | SND_PCI_QUIRK(0x17aa, 0x215e, "Thinkpad L512", ALC269_FIXUP_SKU_IGNORE), | ||
14982 | SND_PCI_QUIRK(0x17aa, 0x21b8, "Thinkpad Edge 14", ALC269_FIXUP_SKU_IGNORE), | ||
14983 | SND_PCI_QUIRK(0x17aa, 0x21ca, "Thinkpad L412", ALC269_FIXUP_SKU_IGNORE), | ||
14984 | SND_PCI_QUIRK(0x17aa, 0x21e9, "Thinkpad Edge 15", ALC269_FIXUP_SKU_IGNORE), | ||
14960 | SND_PCI_QUIRK(0x1043, 0x1a13, "Asus G73Jw", ALC269_FIXUP_ASUS_G73JW), | 14985 | SND_PCI_QUIRK(0x1043, 0x1a13, "Asus G73Jw", ALC269_FIXUP_ASUS_G73JW), |
14961 | SND_PCI_QUIRK(0x17aa, 0x9e54, "LENOVO NB", ALC269_FIXUP_LENOVO_EAPD), | 14986 | SND_PCI_QUIRK(0x17aa, 0x9e54, "LENOVO NB", ALC269_FIXUP_LENOVO_EAPD), |
14962 | {} | 14987 | {} |
@@ -18800,6 +18825,7 @@ static struct snd_pci_quirk alc662_cfg_tbl[] = { | |||
18800 | ALC662_3ST_6ch_DIG), | 18825 | ALC662_3ST_6ch_DIG), |
18801 | SND_PCI_QUIRK_MASK(0x1854, 0xf000, 0x2000, "ASUS H13-200x", | 18826 | SND_PCI_QUIRK_MASK(0x1854, 0xf000, 0x2000, "ASUS H13-200x", |
18802 | ALC663_ASUS_H13), | 18827 | ALC663_ASUS_H13), |
18828 | SND_PCI_QUIRK(0x1991, 0x5628, "Ordissimo EVE", ALC662_LENOVO_101E), | ||
18803 | {} | 18829 | {} |
18804 | }; | 18830 | }; |
18805 | 18831 | ||
@@ -19492,6 +19518,7 @@ static const struct alc_fixup alc662_fixups[] = { | |||
19492 | }; | 19518 | }; |
19493 | 19519 | ||
19494 | static struct snd_pci_quirk alc662_fixup_tbl[] = { | 19520 | static struct snd_pci_quirk alc662_fixup_tbl[] = { |
19521 | SND_PCI_QUIRK(0x1025, 0x0308, "Acer Aspire 8942G", ALC662_FIXUP_ASPIRE), | ||
19495 | SND_PCI_QUIRK(0x1025, 0x038b, "Acer Aspire 8943G", ALC662_FIXUP_ASPIRE), | 19522 | SND_PCI_QUIRK(0x1025, 0x038b, "Acer Aspire 8943G", ALC662_FIXUP_ASPIRE), |
19496 | SND_PCI_QUIRK(0x144d, 0xc051, "Samsung R720", ALC662_FIXUP_IDEAPAD), | 19523 | SND_PCI_QUIRK(0x144d, 0xc051, "Samsung R720", ALC662_FIXUP_IDEAPAD), |
19497 | SND_PCI_QUIRK(0x17aa, 0x38af, "Lenovo Ideapad Y550P", ALC662_FIXUP_IDEAPAD), | 19524 | SND_PCI_QUIRK(0x17aa, 0x38af, "Lenovo Ideapad Y550P", ALC662_FIXUP_IDEAPAD), |
diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c index a76c3260d941..63b0054200a8 100644 --- a/sound/pci/hda/patch_via.c +++ b/sound/pci/hda/patch_via.c | |||
@@ -567,7 +567,7 @@ static void via_auto_init_analog_input(struct hda_codec *codec) | |||
567 | hda_nid_t nid = cfg->inputs[i].pin; | 567 | hda_nid_t nid = cfg->inputs[i].pin; |
568 | if (spec->smart51_enabled && is_smart51_pins(spec, nid)) | 568 | if (spec->smart51_enabled && is_smart51_pins(spec, nid)) |
569 | ctl = PIN_OUT; | 569 | ctl = PIN_OUT; |
570 | else if (i == AUTO_PIN_MIC) | 570 | else if (cfg->inputs[i].type == AUTO_PIN_MIC) |
571 | ctl = PIN_VREF50; | 571 | ctl = PIN_VREF50; |
572 | else | 572 | else |
573 | ctl = PIN_IN; | 573 | ctl = PIN_IN; |
diff --git a/sound/pci/oxygen/oxygen.h b/sound/pci/oxygen/oxygen.h index c2ae63d17cd2..f53897a708b4 100644 --- a/sound/pci/oxygen/oxygen.h +++ b/sound/pci/oxygen/oxygen.h | |||
@@ -92,6 +92,8 @@ struct oxygen_model { | |||
92 | void (*update_dac_volume)(struct oxygen *chip); | 92 | void (*update_dac_volume)(struct oxygen *chip); |
93 | void (*update_dac_mute)(struct oxygen *chip); | 93 | void (*update_dac_mute)(struct oxygen *chip); |
94 | void (*update_center_lfe_mix)(struct oxygen *chip, bool mixed); | 94 | void (*update_center_lfe_mix)(struct oxygen *chip, bool mixed); |
95 | unsigned int (*adjust_dac_routing)(struct oxygen *chip, | ||
96 | unsigned int play_routing); | ||
95 | void (*gpio_changed)(struct oxygen *chip); | 97 | void (*gpio_changed)(struct oxygen *chip); |
96 | void (*uart_input)(struct oxygen *chip); | 98 | void (*uart_input)(struct oxygen *chip); |
97 | void (*ac97_switch)(struct oxygen *chip, | 99 | void (*ac97_switch)(struct oxygen *chip, |
diff --git a/sound/pci/oxygen/oxygen_mixer.c b/sound/pci/oxygen/oxygen_mixer.c index 9bff14d5895d..26c7e8bcb229 100644 --- a/sound/pci/oxygen/oxygen_mixer.c +++ b/sound/pci/oxygen/oxygen_mixer.c | |||
@@ -180,6 +180,8 @@ void oxygen_update_dac_routing(struct oxygen *chip) | |||
180 | (1 << OXYGEN_PLAY_DAC1_SOURCE_SHIFT) | | 180 | (1 << OXYGEN_PLAY_DAC1_SOURCE_SHIFT) | |
181 | (2 << OXYGEN_PLAY_DAC2_SOURCE_SHIFT) | | 181 | (2 << OXYGEN_PLAY_DAC2_SOURCE_SHIFT) | |
182 | (3 << OXYGEN_PLAY_DAC3_SOURCE_SHIFT); | 182 | (3 << OXYGEN_PLAY_DAC3_SOURCE_SHIFT); |
183 | if (chip->model.adjust_dac_routing) | ||
184 | reg_value = chip->model.adjust_dac_routing(chip, reg_value); | ||
183 | oxygen_write16_masked(chip, OXYGEN_PLAY_ROUTING, reg_value, | 185 | oxygen_write16_masked(chip, OXYGEN_PLAY_ROUTING, reg_value, |
184 | OXYGEN_PLAY_DAC0_SOURCE_MASK | | 186 | OXYGEN_PLAY_DAC0_SOURCE_MASK | |
185 | OXYGEN_PLAY_DAC1_SOURCE_MASK | | 187 | OXYGEN_PLAY_DAC1_SOURCE_MASK | |
diff --git a/sound/pci/oxygen/xonar_dg.c b/sound/pci/oxygen/xonar_dg.c index e1fa602eba79..bc6eb58be380 100644 --- a/sound/pci/oxygen/xonar_dg.c +++ b/sound/pci/oxygen/xonar_dg.c | |||
@@ -24,6 +24,11 @@ | |||
24 | * | 24 | * |
25 | * SPI 0 -> CS4245 | 25 | * SPI 0 -> CS4245 |
26 | * | 26 | * |
27 | * I²S 1 -> CS4245 | ||
28 | * I²S 2 -> CS4361 (center/LFE) | ||
29 | * I²S 3 -> CS4361 (surround) | ||
30 | * I²S 4 -> CS4361 (front) | ||
31 | * | ||
27 | * GPIO 3 <- ? | 32 | * GPIO 3 <- ? |
28 | * GPIO 4 <- headphone detect | 33 | * GPIO 4 <- headphone detect |
29 | * GPIO 5 -> route input jack to line-in (0) or mic-in (1) | 34 | * GPIO 5 -> route input jack to line-in (0) or mic-in (1) |
@@ -36,6 +41,7 @@ | |||
36 | * input 1 <- aux | 41 | * input 1 <- aux |
37 | * input 2 <- front mic | 42 | * input 2 <- front mic |
38 | * input 4 <- line/mic | 43 | * input 4 <- line/mic |
44 | * DAC out -> headphones | ||
39 | * aux out -> front panel headphones | 45 | * aux out -> front panel headphones |
40 | */ | 46 | */ |
41 | 47 | ||
@@ -207,6 +213,35 @@ static void set_cs4245_adc_params(struct oxygen *chip, | |||
207 | cs4245_write_cached(chip, CS4245_ADC_CTRL, value); | 213 | cs4245_write_cached(chip, CS4245_ADC_CTRL, value); |
208 | } | 214 | } |
209 | 215 | ||
216 | static inline unsigned int shift_bits(unsigned int value, | ||
217 | unsigned int shift_from, | ||
218 | unsigned int shift_to, | ||
219 | unsigned int mask) | ||
220 | { | ||
221 | if (shift_from < shift_to) | ||
222 | return (value << (shift_to - shift_from)) & mask; | ||
223 | else | ||
224 | return (value >> (shift_from - shift_to)) & mask; | ||
225 | } | ||
226 | |||
227 | static unsigned int adjust_dg_dac_routing(struct oxygen *chip, | ||
228 | unsigned int play_routing) | ||
229 | { | ||
230 | return (play_routing & OXYGEN_PLAY_DAC0_SOURCE_MASK) | | ||
231 | shift_bits(play_routing, | ||
232 | OXYGEN_PLAY_DAC2_SOURCE_SHIFT, | ||
233 | OXYGEN_PLAY_DAC1_SOURCE_SHIFT, | ||
234 | OXYGEN_PLAY_DAC1_SOURCE_MASK) | | ||
235 | shift_bits(play_routing, | ||
236 | OXYGEN_PLAY_DAC1_SOURCE_SHIFT, | ||
237 | OXYGEN_PLAY_DAC2_SOURCE_SHIFT, | ||
238 | OXYGEN_PLAY_DAC2_SOURCE_MASK) | | ||
239 | shift_bits(play_routing, | ||
240 | OXYGEN_PLAY_DAC0_SOURCE_SHIFT, | ||
241 | OXYGEN_PLAY_DAC3_SOURCE_SHIFT, | ||
242 | OXYGEN_PLAY_DAC3_SOURCE_MASK); | ||
243 | } | ||
244 | |||
210 | static int output_switch_info(struct snd_kcontrol *ctl, | 245 | static int output_switch_info(struct snd_kcontrol *ctl, |
211 | struct snd_ctl_elem_info *info) | 246 | struct snd_ctl_elem_info *info) |
212 | { | 247 | { |
@@ -557,6 +592,7 @@ struct oxygen_model model_xonar_dg = { | |||
557 | .resume = dg_resume, | 592 | .resume = dg_resume, |
558 | .set_dac_params = set_cs4245_dac_params, | 593 | .set_dac_params = set_cs4245_dac_params, |
559 | .set_adc_params = set_cs4245_adc_params, | 594 | .set_adc_params = set_cs4245_adc_params, |
595 | .adjust_dac_routing = adjust_dg_dac_routing, | ||
560 | .dump_registers = dump_cs4245_registers, | 596 | .dump_registers = dump_cs4245_registers, |
561 | .model_data_size = sizeof(struct dg), | 597 | .model_data_size = sizeof(struct dg), |
562 | .device_config = PLAYBACK_0_TO_I2S | | 598 | .device_config = PLAYBACK_0_TO_I2S | |