diff options
Diffstat (limited to 'sound/pci')
-rw-r--r-- | sound/pci/cs5535audio/cs5535audio_pcm.c | 2 | ||||
-rw-r--r-- | sound/pci/hda/hda_codec.c | 6 | ||||
-rw-r--r-- | sound/pci/hda/hda_eld.c | 41 | ||||
-rw-r--r-- | sound/pci/hda/hda_intel.c | 1 | ||||
-rw-r--r-- | sound/pci/hda/hda_local.h | 3 | ||||
-rw-r--r-- | sound/pci/hda/patch_cirrus.c | 55 | ||||
-rw-r--r-- | sound/pci/hda/patch_hdmi.c | 59 | ||||
-rw-r--r-- | sound/pci/hda/patch_realtek.c | 101 | ||||
-rw-r--r-- | sound/pci/hda/patch_sigmatel.c | 102 | ||||
-rw-r--r-- | sound/pci/hda/patch_via.c | 76 | ||||
-rw-r--r-- | sound/pci/lx6464es/lx_core.c | 23 | ||||
-rw-r--r-- | sound/pci/lx6464es/lx_core.h | 3 | ||||
-rw-r--r-- | sound/pci/rme9652/hdspm.c | 2 | ||||
-rw-r--r-- | sound/pci/sis7019.c | 64 |
14 files changed, 332 insertions, 206 deletions
diff --git a/sound/pci/cs5535audio/cs5535audio_pcm.c b/sound/pci/cs5535audio/cs5535audio_pcm.c index e083122ca55a..dbf94b189e75 100644 --- a/sound/pci/cs5535audio/cs5535audio_pcm.c +++ b/sound/pci/cs5535audio/cs5535audio_pcm.c | |||
@@ -148,7 +148,7 @@ static int cs5535audio_build_dma_packets(struct cs5535audio *cs5535au, | |||
148 | struct cs5535audio_dma_desc *desc = | 148 | struct cs5535audio_dma_desc *desc = |
149 | &((struct cs5535audio_dma_desc *) dma->desc_buf.area)[i]; | 149 | &((struct cs5535audio_dma_desc *) dma->desc_buf.area)[i]; |
150 | desc->addr = cpu_to_le32(addr); | 150 | desc->addr = cpu_to_le32(addr); |
151 | desc->size = cpu_to_le32(period_bytes); | 151 | desc->size = cpu_to_le16(period_bytes); |
152 | desc->ctlreserved = cpu_to_le16(PRD_EOP); | 152 | desc->ctlreserved = cpu_to_le16(PRD_EOP); |
153 | desc_addr += sizeof(struct cs5535audio_dma_desc); | 153 | desc_addr += sizeof(struct cs5535audio_dma_desc); |
154 | addr += period_bytes; | 154 | addr += period_bytes; |
diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index e44b107fdc75..4562e9de6a1a 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c | |||
@@ -4046,9 +4046,9 @@ int snd_hda_check_board_codec_sid_config(struct hda_codec *codec, | |||
4046 | 4046 | ||
4047 | /* Search for codec ID */ | 4047 | /* Search for codec ID */ |
4048 | for (q = tbl; q->subvendor; q++) { | 4048 | for (q = tbl; q->subvendor; q++) { |
4049 | unsigned long vendorid = (q->subdevice) | (q->subvendor << 16); | 4049 | unsigned int mask = 0xffff0000 | q->subdevice_mask; |
4050 | 4050 | unsigned int id = (q->subdevice | (q->subvendor << 16)) & mask; | |
4051 | if (vendorid == codec->subsystem_id) | 4051 | if ((codec->subsystem_id & mask) == id) |
4052 | break; | 4052 | break; |
4053 | } | 4053 | } |
4054 | 4054 | ||
diff --git a/sound/pci/hda/hda_eld.c b/sound/pci/hda/hda_eld.c index 1c8ddf547a2d..c1da422e085a 100644 --- a/sound/pci/hda/hda_eld.c +++ b/sound/pci/hda/hda_eld.c | |||
@@ -297,10 +297,18 @@ static int hdmi_update_eld(struct hdmi_eld *e, | |||
297 | buf + ELD_FIXED_BYTES + mnl + 3 * i); | 297 | buf + ELD_FIXED_BYTES + mnl + 3 * i); |
298 | } | 298 | } |
299 | 299 | ||
300 | /* | ||
301 | * HDMI sink's ELD info cannot always be retrieved for now, e.g. | ||
302 | * in console or for audio devices. Assume the highest speakers | ||
303 | * configuration, to _not_ prohibit multi-channel audio playback. | ||
304 | */ | ||
305 | if (!e->spk_alloc) | ||
306 | e->spk_alloc = 0xffff; | ||
307 | |||
308 | e->eld_valid = true; | ||
300 | return 0; | 309 | return 0; |
301 | 310 | ||
302 | out_fail: | 311 | out_fail: |
303 | e->eld_ver = 0; | ||
304 | return -EINVAL; | 312 | return -EINVAL; |
305 | } | 313 | } |
306 | 314 | ||
@@ -323,9 +331,6 @@ int snd_hdmi_get_eld(struct hdmi_eld *eld, | |||
323 | * ELD is valid, actual eld_size is assigned in hdmi_update_eld() | 331 | * ELD is valid, actual eld_size is assigned in hdmi_update_eld() |
324 | */ | 332 | */ |
325 | 333 | ||
326 | if (!eld->eld_valid) | ||
327 | return -ENOENT; | ||
328 | |||
329 | size = snd_hdmi_get_eld_size(codec, nid); | 334 | size = snd_hdmi_get_eld_size(codec, nid); |
330 | if (size == 0) { | 335 | if (size == 0) { |
331 | /* wfg: workaround for ASUS P5E-VM HDMI board */ | 336 | /* wfg: workaround for ASUS P5E-VM HDMI board */ |
@@ -342,18 +347,28 @@ int snd_hdmi_get_eld(struct hdmi_eld *eld, | |||
342 | 347 | ||
343 | for (i = 0; i < size; i++) { | 348 | for (i = 0; i < size; i++) { |
344 | unsigned int val = hdmi_get_eld_data(codec, nid, i); | 349 | unsigned int val = hdmi_get_eld_data(codec, nid, i); |
350 | /* | ||
351 | * Graphics driver might be writing to ELD buffer right now. | ||
352 | * Just abort. The caller will repoll after a while. | ||
353 | */ | ||
345 | if (!(val & AC_ELDD_ELD_VALID)) { | 354 | if (!(val & AC_ELDD_ELD_VALID)) { |
346 | if (!i) { | ||
347 | snd_printd(KERN_INFO | ||
348 | "HDMI: invalid ELD data\n"); | ||
349 | ret = -EINVAL; | ||
350 | goto error; | ||
351 | } | ||
352 | snd_printd(KERN_INFO | 355 | snd_printd(KERN_INFO |
353 | "HDMI: invalid ELD data byte %d\n", i); | 356 | "HDMI: invalid ELD data byte %d\n", i); |
354 | val = 0; | 357 | ret = -EINVAL; |
355 | } else | 358 | goto error; |
356 | val &= AC_ELDD_ELD_DATA; | 359 | } |
360 | val &= AC_ELDD_ELD_DATA; | ||
361 | /* | ||
362 | * The first byte cannot be zero. This can happen on some DVI | ||
363 | * connections. Some Intel chips may also need some 250ms delay | ||
364 | * to return non-zero ELD data, even when the graphics driver | ||
365 | * correctly writes ELD content before setting ELD_valid bit. | ||
366 | */ | ||
367 | if (!val && !i) { | ||
368 | snd_printdd(KERN_INFO "HDMI: 0 ELD data\n"); | ||
369 | ret = -EINVAL; | ||
370 | goto error; | ||
371 | } | ||
357 | buf[i] = val; | 372 | buf[i] = val; |
358 | } | 373 | } |
359 | 374 | ||
diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index 096507d2ca9a..7d98240def0b 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c | |||
@@ -2508,7 +2508,6 @@ static struct snd_pci_quirk position_fix_list[] __devinitdata = { | |||
2508 | SND_PCI_QUIRK(0x1043, 0x81b3, "ASUS", POS_FIX_LPIB), | 2508 | SND_PCI_QUIRK(0x1043, 0x81b3, "ASUS", POS_FIX_LPIB), |
2509 | SND_PCI_QUIRK(0x1043, 0x81e7, "ASUS M2V", POS_FIX_LPIB), | 2509 | SND_PCI_QUIRK(0x1043, 0x81e7, "ASUS M2V", POS_FIX_LPIB), |
2510 | SND_PCI_QUIRK(0x104d, 0x9069, "Sony VPCS11V9E", POS_FIX_LPIB), | 2510 | SND_PCI_QUIRK(0x104d, 0x9069, "Sony VPCS11V9E", POS_FIX_LPIB), |
2511 | SND_PCI_QUIRK(0x1106, 0x3288, "ASUS M2V-MX SE", POS_FIX_LPIB), | ||
2512 | SND_PCI_QUIRK(0x1297, 0x3166, "Shuttle", POS_FIX_LPIB), | 2511 | SND_PCI_QUIRK(0x1297, 0x3166, "Shuttle", POS_FIX_LPIB), |
2513 | SND_PCI_QUIRK(0x1458, 0xa022, "ga-ma770-ud3", POS_FIX_LPIB), | 2512 | SND_PCI_QUIRK(0x1458, 0xa022, "ga-ma770-ud3", POS_FIX_LPIB), |
2514 | SND_PCI_QUIRK(0x1462, 0x1002, "MSI Wind U115", POS_FIX_LPIB), | 2513 | SND_PCI_QUIRK(0x1462, 0x1002, "MSI Wind U115", POS_FIX_LPIB), |
diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 6579e0f2bb57..618ddad17236 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h | |||
@@ -653,6 +653,9 @@ struct hdmi_eld { | |||
653 | int spk_alloc; | 653 | int spk_alloc; |
654 | int sad_count; | 654 | int sad_count; |
655 | struct cea_sad sad[ELD_MAX_SAD]; | 655 | struct cea_sad sad[ELD_MAX_SAD]; |
656 | /* | ||
657 | * all fields above eld_buffer will be cleared before updating ELD | ||
658 | */ | ||
656 | char eld_buffer[ELD_MAX_SIZE]; | 659 | char eld_buffer[ELD_MAX_SIZE]; |
657 | #ifdef CONFIG_PROC_FS | 660 | #ifdef CONFIG_PROC_FS |
658 | struct snd_info_entry *proc_entry; | 661 | struct snd_info_entry *proc_entry; |
diff --git a/sound/pci/hda/patch_cirrus.c b/sound/pci/hda/patch_cirrus.c index 2a2d8645ba09..70a7abda7e22 100644 --- a/sound/pci/hda/patch_cirrus.c +++ b/sound/pci/hda/patch_cirrus.c | |||
@@ -58,6 +58,8 @@ struct cs_spec { | |||
58 | unsigned int gpio_mask; | 58 | unsigned int gpio_mask; |
59 | unsigned int gpio_dir; | 59 | unsigned int gpio_dir; |
60 | unsigned int gpio_data; | 60 | unsigned int gpio_data; |
61 | unsigned int gpio_eapd_hp; /* EAPD GPIO bit for headphones */ | ||
62 | unsigned int gpio_eapd_speaker; /* EAPD GPIO bit for speakers */ | ||
61 | 63 | ||
62 | struct hda_pcm pcm_rec[2]; /* PCM information */ | 64 | struct hda_pcm pcm_rec[2]; /* PCM information */ |
63 | 65 | ||
@@ -76,6 +78,7 @@ enum { | |||
76 | CS420X_MBP53, | 78 | CS420X_MBP53, |
77 | CS420X_MBP55, | 79 | CS420X_MBP55, |
78 | CS420X_IMAC27, | 80 | CS420X_IMAC27, |
81 | CS420X_APPLE, | ||
79 | CS420X_AUTO, | 82 | CS420X_AUTO, |
80 | CS420X_MODELS | 83 | CS420X_MODELS |
81 | }; | 84 | }; |
@@ -237,6 +240,15 @@ static int cs_dig_playback_pcm_cleanup(struct hda_pcm_stream *hinfo, | |||
237 | return snd_hda_multi_out_dig_cleanup(codec, &spec->multiout); | 240 | return snd_hda_multi_out_dig_cleanup(codec, &spec->multiout); |
238 | } | 241 | } |
239 | 242 | ||
243 | static void cs_update_input_select(struct hda_codec *codec) | ||
244 | { | ||
245 | struct cs_spec *spec = codec->spec; | ||
246 | if (spec->cur_adc) | ||
247 | snd_hda_codec_write(codec, spec->cur_adc, 0, | ||
248 | AC_VERB_SET_CONNECT_SEL, | ||
249 | spec->adc_idx[spec->cur_input]); | ||
250 | } | ||
251 | |||
240 | /* | 252 | /* |
241 | * Analog capture | 253 | * Analog capture |
242 | */ | 254 | */ |
@@ -250,6 +262,7 @@ static int cs_capture_pcm_prepare(struct hda_pcm_stream *hinfo, | |||
250 | spec->cur_adc = spec->adc_nid[spec->cur_input]; | 262 | spec->cur_adc = spec->adc_nid[spec->cur_input]; |
251 | spec->cur_adc_stream_tag = stream_tag; | 263 | spec->cur_adc_stream_tag = stream_tag; |
252 | spec->cur_adc_format = format; | 264 | spec->cur_adc_format = format; |
265 | cs_update_input_select(codec); | ||
253 | snd_hda_codec_setup_stream(codec, spec->cur_adc, stream_tag, 0, format); | 266 | snd_hda_codec_setup_stream(codec, spec->cur_adc, stream_tag, 0, format); |
254 | return 0; | 267 | return 0; |
255 | } | 268 | } |
@@ -689,10 +702,8 @@ static int change_cur_input(struct hda_codec *codec, unsigned int idx, | |||
689 | spec->cur_adc_stream_tag, 0, | 702 | spec->cur_adc_stream_tag, 0, |
690 | spec->cur_adc_format); | 703 | spec->cur_adc_format); |
691 | } | 704 | } |
692 | snd_hda_codec_write(codec, spec->cur_adc, 0, | ||
693 | AC_VERB_SET_CONNECT_SEL, | ||
694 | spec->adc_idx[idx]); | ||
695 | spec->cur_input = idx; | 705 | spec->cur_input = idx; |
706 | cs_update_input_select(codec); | ||
696 | return 1; | 707 | return 1; |
697 | } | 708 | } |
698 | 709 | ||
@@ -920,10 +931,9 @@ static void cs_automute(struct hda_codec *codec) | |||
920 | spdif_present ? 0 : PIN_OUT); | 931 | spdif_present ? 0 : PIN_OUT); |
921 | } | 932 | } |
922 | } | 933 | } |
923 | if (spec->board_config == CS420X_MBP53 || | 934 | if (spec->gpio_eapd_hp) { |
924 | spec->board_config == CS420X_MBP55 || | 935 | unsigned int gpio = hp_present ? |
925 | spec->board_config == CS420X_IMAC27) { | 936 | spec->gpio_eapd_hp : spec->gpio_eapd_speaker; |
926 | unsigned int gpio = hp_present ? 0x02 : 0x08; | ||
927 | snd_hda_codec_write(codec, 0x01, 0, | 937 | snd_hda_codec_write(codec, 0x01, 0, |
928 | AC_VERB_SET_GPIO_DATA, gpio); | 938 | AC_VERB_SET_GPIO_DATA, gpio); |
929 | } | 939 | } |
@@ -973,10 +983,7 @@ static void cs_automic(struct hda_codec *codec) | |||
973 | } else { | 983 | } else { |
974 | spec->cur_input = spec->last_input; | 984 | spec->cur_input = spec->last_input; |
975 | } | 985 | } |
976 | 986 | cs_update_input_select(codec); | |
977 | snd_hda_codec_write_cache(codec, spec->cur_adc, 0, | ||
978 | AC_VERB_SET_CONNECT_SEL, | ||
979 | spec->adc_idx[spec->cur_input]); | ||
980 | } else { | 987 | } else { |
981 | if (present) | 988 | if (present) |
982 | change_cur_input(codec, spec->automic_idx, 0); | 989 | change_cur_input(codec, spec->automic_idx, 0); |
@@ -1073,9 +1080,7 @@ static void init_input(struct hda_codec *codec) | |||
1073 | cs_automic(codec); | 1080 | cs_automic(codec); |
1074 | else { | 1081 | else { |
1075 | spec->cur_adc = spec->adc_nid[spec->cur_input]; | 1082 | spec->cur_adc = spec->adc_nid[spec->cur_input]; |
1076 | snd_hda_codec_write(codec, spec->cur_adc, 0, | 1083 | cs_update_input_select(codec); |
1077 | AC_VERB_SET_CONNECT_SEL, | ||
1078 | spec->adc_idx[spec->cur_input]); | ||
1079 | } | 1084 | } |
1080 | } else { | 1085 | } else { |
1081 | change_cur_input(codec, spec->cur_input, 1); | 1086 | change_cur_input(codec, spec->cur_input, 1); |
@@ -1273,6 +1278,7 @@ static const char * const cs420x_models[CS420X_MODELS] = { | |||
1273 | [CS420X_MBP53] = "mbp53", | 1278 | [CS420X_MBP53] = "mbp53", |
1274 | [CS420X_MBP55] = "mbp55", | 1279 | [CS420X_MBP55] = "mbp55", |
1275 | [CS420X_IMAC27] = "imac27", | 1280 | [CS420X_IMAC27] = "imac27", |
1281 | [CS420X_APPLE] = "apple", | ||
1276 | [CS420X_AUTO] = "auto", | 1282 | [CS420X_AUTO] = "auto", |
1277 | }; | 1283 | }; |
1278 | 1284 | ||
@@ -1282,7 +1288,13 @@ static const struct snd_pci_quirk cs420x_cfg_tbl[] = { | |||
1282 | SND_PCI_QUIRK(0x10de, 0x0d94, "MacBookAir 3,1(2)", CS420X_MBP55), | 1288 | SND_PCI_QUIRK(0x10de, 0x0d94, "MacBookAir 3,1(2)", CS420X_MBP55), |
1283 | SND_PCI_QUIRK(0x10de, 0xcb79, "MacBookPro 5,5", CS420X_MBP55), | 1289 | SND_PCI_QUIRK(0x10de, 0xcb79, "MacBookPro 5,5", CS420X_MBP55), |
1284 | SND_PCI_QUIRK(0x10de, 0xcb89, "MacBookPro 7,1", CS420X_MBP55), | 1290 | SND_PCI_QUIRK(0x10de, 0xcb89, "MacBookPro 7,1", CS420X_MBP55), |
1285 | SND_PCI_QUIRK(0x8086, 0x7270, "IMac 27 Inch", CS420X_IMAC27), | 1291 | /* this conflicts with too many other models */ |
1292 | /*SND_PCI_QUIRK(0x8086, 0x7270, "IMac 27 Inch", CS420X_IMAC27),*/ | ||
1293 | {} /* terminator */ | ||
1294 | }; | ||
1295 | |||
1296 | static const struct snd_pci_quirk cs420x_codec_cfg_tbl[] = { | ||
1297 | SND_PCI_QUIRK_VENDOR(0x106b, "Apple", CS420X_APPLE), | ||
1286 | {} /* terminator */ | 1298 | {} /* terminator */ |
1287 | }; | 1299 | }; |
1288 | 1300 | ||
@@ -1364,6 +1376,10 @@ static int patch_cs420x(struct hda_codec *codec) | |||
1364 | spec->board_config = | 1376 | spec->board_config = |
1365 | snd_hda_check_board_config(codec, CS420X_MODELS, | 1377 | snd_hda_check_board_config(codec, CS420X_MODELS, |
1366 | cs420x_models, cs420x_cfg_tbl); | 1378 | cs420x_models, cs420x_cfg_tbl); |
1379 | if (spec->board_config < 0) | ||
1380 | spec->board_config = | ||
1381 | snd_hda_check_board_codec_sid_config(codec, | ||
1382 | CS420X_MODELS, NULL, cs420x_codec_cfg_tbl); | ||
1367 | if (spec->board_config >= 0) | 1383 | if (spec->board_config >= 0) |
1368 | fix_pincfg(codec, spec->board_config, cs_pincfgs); | 1384 | fix_pincfg(codec, spec->board_config, cs_pincfgs); |
1369 | 1385 | ||
@@ -1371,10 +1387,11 @@ static int patch_cs420x(struct hda_codec *codec) | |||
1371 | case CS420X_IMAC27: | 1387 | case CS420X_IMAC27: |
1372 | case CS420X_MBP53: | 1388 | case CS420X_MBP53: |
1373 | case CS420X_MBP55: | 1389 | case CS420X_MBP55: |
1374 | /* GPIO1 = headphones */ | 1390 | case CS420X_APPLE: |
1375 | /* GPIO3 = speakers */ | 1391 | spec->gpio_eapd_hp = 2; /* GPIO1 = headphones */ |
1376 | spec->gpio_mask = 0x0a; | 1392 | spec->gpio_eapd_speaker = 8; /* GPIO3 = speakers */ |
1377 | spec->gpio_dir = 0x0a; | 1393 | spec->gpio_mask = spec->gpio_dir = |
1394 | spec->gpio_eapd_hp | spec->gpio_eapd_speaker; | ||
1378 | break; | 1395 | break; |
1379 | } | 1396 | } |
1380 | 1397 | ||
diff --git a/sound/pci/hda/patch_hdmi.c b/sound/pci/hda/patch_hdmi.c index 81b7b791b3c3..c505fd5d338c 100644 --- a/sound/pci/hda/patch_hdmi.c +++ b/sound/pci/hda/patch_hdmi.c | |||
@@ -65,7 +65,11 @@ struct hdmi_spec_per_pin { | |||
65 | hda_nid_t pin_nid; | 65 | hda_nid_t pin_nid; |
66 | int num_mux_nids; | 66 | int num_mux_nids; |
67 | hda_nid_t mux_nids[HDA_MAX_CONNECTIONS]; | 67 | hda_nid_t mux_nids[HDA_MAX_CONNECTIONS]; |
68 | |||
69 | struct hda_codec *codec; | ||
68 | struct hdmi_eld sink_eld; | 70 | struct hdmi_eld sink_eld; |
71 | struct delayed_work work; | ||
72 | int repoll_count; | ||
69 | }; | 73 | }; |
70 | 74 | ||
71 | struct hdmi_spec { | 75 | struct hdmi_spec { |
@@ -745,8 +749,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec, int pin_idx, | |||
745 | * Unsolicited events | 749 | * Unsolicited events |
746 | */ | 750 | */ |
747 | 751 | ||
748 | static void hdmi_present_sense(struct hda_codec *codec, hda_nid_t pin_nid, | 752 | static void hdmi_present_sense(struct hdmi_spec_per_pin *per_pin, int repoll); |
749 | struct hdmi_eld *eld); | ||
750 | 753 | ||
751 | static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res) | 754 | static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res) |
752 | { | 755 | { |
@@ -755,7 +758,6 @@ static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res) | |||
755 | int pd = !!(res & AC_UNSOL_RES_PD); | 758 | int pd = !!(res & AC_UNSOL_RES_PD); |
756 | int eldv = !!(res & AC_UNSOL_RES_ELDV); | 759 | int eldv = !!(res & AC_UNSOL_RES_ELDV); |
757 | int pin_idx; | 760 | int pin_idx; |
758 | struct hdmi_eld *eld; | ||
759 | 761 | ||
760 | printk(KERN_INFO | 762 | printk(KERN_INFO |
761 | "HDMI hot plug event: Codec=%d Pin=%d Presence_Detect=%d ELD_Valid=%d\n", | 763 | "HDMI hot plug event: Codec=%d Pin=%d Presence_Detect=%d ELD_Valid=%d\n", |
@@ -764,17 +766,8 @@ static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res) | |||
764 | pin_idx = pin_nid_to_pin_index(spec, pin_nid); | 766 | pin_idx = pin_nid_to_pin_index(spec, pin_nid); |
765 | if (pin_idx < 0) | 767 | if (pin_idx < 0) |
766 | return; | 768 | return; |
767 | eld = &spec->pins[pin_idx].sink_eld; | ||
768 | |||
769 | hdmi_present_sense(codec, pin_nid, eld); | ||
770 | 769 | ||
771 | /* | 770 | hdmi_present_sense(&spec->pins[pin_idx], 1); |
772 | * HDMI sink's ELD info cannot always be retrieved for now, e.g. | ||
773 | * in console or for audio devices. Assume the highest speakers | ||
774 | * configuration, to _not_ prohibit multi-channel audio playback. | ||
775 | */ | ||
776 | if (!eld->spk_alloc) | ||
777 | eld->spk_alloc = 0xffff; | ||
778 | } | 771 | } |
779 | 772 | ||
780 | static void hdmi_non_intrinsic_event(struct hda_codec *codec, unsigned int res) | 773 | static void hdmi_non_intrinsic_event(struct hda_codec *codec, unsigned int res) |
@@ -968,9 +961,11 @@ static int hdmi_read_pin_conn(struct hda_codec *codec, int pin_idx) | |||
968 | return 0; | 961 | return 0; |
969 | } | 962 | } |
970 | 963 | ||
971 | static void hdmi_present_sense(struct hda_codec *codec, hda_nid_t pin_nid, | 964 | static void hdmi_present_sense(struct hdmi_spec_per_pin *per_pin, int repoll) |
972 | struct hdmi_eld *eld) | ||
973 | { | 965 | { |
966 | struct hda_codec *codec = per_pin->codec; | ||
967 | struct hdmi_eld *eld = &per_pin->sink_eld; | ||
968 | hda_nid_t pin_nid = per_pin->pin_nid; | ||
974 | /* | 969 | /* |
975 | * Always execute a GetPinSense verb here, even when called from | 970 | * Always execute a GetPinSense verb here, even when called from |
976 | * hdmi_intrinsic_event; for some NVIDIA HW, the unsolicited | 971 | * hdmi_intrinsic_event; for some NVIDIA HW, the unsolicited |
@@ -980,26 +975,42 @@ static void hdmi_present_sense(struct hda_codec *codec, hda_nid_t pin_nid, | |||
980 | * the unsolicited response to avoid custom WARs. | 975 | * the unsolicited response to avoid custom WARs. |
981 | */ | 976 | */ |
982 | int present = snd_hda_pin_sense(codec, pin_nid); | 977 | int present = snd_hda_pin_sense(codec, pin_nid); |
978 | bool eld_valid = false; | ||
983 | 979 | ||
984 | memset(eld, 0, sizeof(*eld)); | 980 | memset(eld, 0, offsetof(struct hdmi_eld, eld_buffer)); |
985 | 981 | ||
986 | eld->monitor_present = !!(present & AC_PINSENSE_PRESENCE); | 982 | eld->monitor_present = !!(present & AC_PINSENSE_PRESENCE); |
987 | if (eld->monitor_present) | 983 | if (eld->monitor_present) |
988 | eld->eld_valid = !!(present & AC_PINSENSE_ELDV); | 984 | eld_valid = !!(present & AC_PINSENSE_ELDV); |
989 | else | ||
990 | eld->eld_valid = 0; | ||
991 | 985 | ||
992 | printk(KERN_INFO | 986 | printk(KERN_INFO |
993 | "HDMI status: Codec=%d Pin=%d Presence_Detect=%d ELD_Valid=%d\n", | 987 | "HDMI status: Codec=%d Pin=%d Presence_Detect=%d ELD_Valid=%d\n", |
994 | codec->addr, pin_nid, eld->monitor_present, eld->eld_valid); | 988 | codec->addr, pin_nid, eld->monitor_present, eld_valid); |
995 | 989 | ||
996 | if (eld->eld_valid) | 990 | if (eld_valid) { |
997 | if (!snd_hdmi_get_eld(eld, codec, pin_nid)) | 991 | if (!snd_hdmi_get_eld(eld, codec, pin_nid)) |
998 | snd_hdmi_show_eld(eld); | 992 | snd_hdmi_show_eld(eld); |
993 | else if (repoll) { | ||
994 | queue_delayed_work(codec->bus->workq, | ||
995 | &per_pin->work, | ||
996 | msecs_to_jiffies(300)); | ||
997 | } | ||
998 | } | ||
999 | 999 | ||
1000 | snd_hda_input_jack_report(codec, pin_nid); | 1000 | snd_hda_input_jack_report(codec, pin_nid); |
1001 | } | 1001 | } |
1002 | 1002 | ||
1003 | static void hdmi_repoll_eld(struct work_struct *work) | ||
1004 | { | ||
1005 | struct hdmi_spec_per_pin *per_pin = | ||
1006 | container_of(to_delayed_work(work), struct hdmi_spec_per_pin, work); | ||
1007 | |||
1008 | if (per_pin->repoll_count++ > 6) | ||
1009 | per_pin->repoll_count = 0; | ||
1010 | |||
1011 | hdmi_present_sense(per_pin, per_pin->repoll_count); | ||
1012 | } | ||
1013 | |||
1003 | static int hdmi_add_pin(struct hda_codec *codec, hda_nid_t pin_nid) | 1014 | static int hdmi_add_pin(struct hda_codec *codec, hda_nid_t pin_nid) |
1004 | { | 1015 | { |
1005 | struct hdmi_spec *spec = codec->spec; | 1016 | struct hdmi_spec *spec = codec->spec; |
@@ -1228,7 +1239,7 @@ static int generic_hdmi_build_jack(struct hda_codec *codec, int pin_idx) | |||
1228 | if (err < 0) | 1239 | if (err < 0) |
1229 | return err; | 1240 | return err; |
1230 | 1241 | ||
1231 | hdmi_present_sense(codec, per_pin->pin_nid, &per_pin->sink_eld); | 1242 | hdmi_present_sense(per_pin, 0); |
1232 | return 0; | 1243 | return 0; |
1233 | } | 1244 | } |
1234 | 1245 | ||
@@ -1279,6 +1290,8 @@ static int generic_hdmi_init(struct hda_codec *codec) | |||
1279 | AC_VERB_SET_UNSOLICITED_ENABLE, | 1290 | AC_VERB_SET_UNSOLICITED_ENABLE, |
1280 | AC_USRSP_EN | pin_nid); | 1291 | AC_USRSP_EN | pin_nid); |
1281 | 1292 | ||
1293 | per_pin->codec = codec; | ||
1294 | INIT_DELAYED_WORK(&per_pin->work, hdmi_repoll_eld); | ||
1282 | snd_hda_eld_proc_new(codec, eld, pin_idx); | 1295 | snd_hda_eld_proc_new(codec, eld, pin_idx); |
1283 | } | 1296 | } |
1284 | return 0; | 1297 | return 0; |
@@ -1293,10 +1306,12 @@ static void generic_hdmi_free(struct hda_codec *codec) | |||
1293 | struct hdmi_spec_per_pin *per_pin = &spec->pins[pin_idx]; | 1306 | struct hdmi_spec_per_pin *per_pin = &spec->pins[pin_idx]; |
1294 | struct hdmi_eld *eld = &per_pin->sink_eld; | 1307 | struct hdmi_eld *eld = &per_pin->sink_eld; |
1295 | 1308 | ||
1309 | cancel_delayed_work(&per_pin->work); | ||
1296 | snd_hda_eld_proc_free(codec, eld); | 1310 | snd_hda_eld_proc_free(codec, eld); |
1297 | } | 1311 | } |
1298 | snd_hda_input_jack_free(codec); | 1312 | snd_hda_input_jack_free(codec); |
1299 | 1313 | ||
1314 | flush_workqueue(codec->bus->workq); | ||
1300 | kfree(spec); | 1315 | kfree(spec); |
1301 | } | 1316 | } |
1302 | 1317 | ||
diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 308bb575bc06..1d07e8fa2433 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c | |||
@@ -277,6 +277,12 @@ static bool alc_dyn_adc_pcm_resetup(struct hda_codec *codec, int cur) | |||
277 | return false; | 277 | return false; |
278 | } | 278 | } |
279 | 279 | ||
280 | static inline hda_nid_t get_capsrc(struct alc_spec *spec, int idx) | ||
281 | { | ||
282 | return spec->capsrc_nids ? | ||
283 | spec->capsrc_nids[idx] : spec->adc_nids[idx]; | ||
284 | } | ||
285 | |||
280 | /* select the given imux item; either unmute exclusively or select the route */ | 286 | /* select the given imux item; either unmute exclusively or select the route */ |
281 | static int alc_mux_select(struct hda_codec *codec, unsigned int adc_idx, | 287 | static int alc_mux_select(struct hda_codec *codec, unsigned int adc_idx, |
282 | unsigned int idx, bool force) | 288 | unsigned int idx, bool force) |
@@ -291,6 +297,8 @@ static int alc_mux_select(struct hda_codec *codec, unsigned int adc_idx, | |||
291 | imux = &spec->input_mux[mux_idx]; | 297 | imux = &spec->input_mux[mux_idx]; |
292 | if (!imux->num_items && mux_idx > 0) | 298 | if (!imux->num_items && mux_idx > 0) |
293 | imux = &spec->input_mux[0]; | 299 | imux = &spec->input_mux[0]; |
300 | if (!imux->num_items) | ||
301 | return 0; | ||
294 | 302 | ||
295 | if (idx >= imux->num_items) | 303 | if (idx >= imux->num_items) |
296 | idx = imux->num_items - 1; | 304 | idx = imux->num_items - 1; |
@@ -303,8 +311,7 @@ static int alc_mux_select(struct hda_codec *codec, unsigned int adc_idx, | |||
303 | adc_idx = spec->dyn_adc_idx[idx]; | 311 | adc_idx = spec->dyn_adc_idx[idx]; |
304 | } | 312 | } |
305 | 313 | ||
306 | nid = spec->capsrc_nids ? | 314 | nid = get_capsrc(spec, adc_idx); |
307 | spec->capsrc_nids[adc_idx] : spec->adc_nids[adc_idx]; | ||
308 | 315 | ||
309 | /* no selection? */ | 316 | /* no selection? */ |
310 | num_conns = snd_hda_get_conn_list(codec, nid, NULL); | 317 | num_conns = snd_hda_get_conn_list(codec, nid, NULL); |
@@ -1054,8 +1061,19 @@ static bool alc_rebuild_imux_for_auto_mic(struct hda_codec *codec) | |||
1054 | spec->imux_pins[2] = spec->dock_mic_pin; | 1061 | spec->imux_pins[2] = spec->dock_mic_pin; |
1055 | for (i = 0; i < 3; i++) { | 1062 | for (i = 0; i < 3; i++) { |
1056 | strcpy(imux->items[i].label, texts[i]); | 1063 | strcpy(imux->items[i].label, texts[i]); |
1057 | if (spec->imux_pins[i]) | 1064 | if (spec->imux_pins[i]) { |
1065 | hda_nid_t pin = spec->imux_pins[i]; | ||
1066 | int c; | ||
1067 | for (c = 0; c < spec->num_adc_nids; c++) { | ||
1068 | hda_nid_t cap = get_capsrc(spec, c); | ||
1069 | int idx = get_connection_index(codec, cap, pin); | ||
1070 | if (idx >= 0) { | ||
1071 | imux->items[i].index = idx; | ||
1072 | break; | ||
1073 | } | ||
1074 | } | ||
1058 | imux->num_items = i + 1; | 1075 | imux->num_items = i + 1; |
1076 | } | ||
1059 | } | 1077 | } |
1060 | spec->num_mux_defs = 1; | 1078 | spec->num_mux_defs = 1; |
1061 | spec->input_mux = imux; | 1079 | spec->input_mux = imux; |
@@ -1452,7 +1470,7 @@ static void alc_apply_fixup(struct hda_codec *codec, int action) | |||
1452 | switch (fix->type) { | 1470 | switch (fix->type) { |
1453 | case ALC_FIXUP_SKU: | 1471 | case ALC_FIXUP_SKU: |
1454 | if (action != ALC_FIXUP_ACT_PRE_PROBE || !fix->v.sku) | 1472 | if (action != ALC_FIXUP_ACT_PRE_PROBE || !fix->v.sku) |
1455 | break;; | 1473 | break; |
1456 | snd_printdd(KERN_INFO "hda_codec: %s: " | 1474 | snd_printdd(KERN_INFO "hda_codec: %s: " |
1457 | "Apply sku override for %s\n", | 1475 | "Apply sku override for %s\n", |
1458 | codec->chip_name, modelname); | 1476 | codec->chip_name, modelname); |
@@ -1957,10 +1975,8 @@ static int alc_build_controls(struct hda_codec *codec) | |||
1957 | if (!kctl) | 1975 | if (!kctl) |
1958 | kctl = snd_hda_find_mixer_ctl(codec, "Input Source"); | 1976 | kctl = snd_hda_find_mixer_ctl(codec, "Input Source"); |
1959 | for (i = 0; kctl && i < kctl->count; i++) { | 1977 | for (i = 0; kctl && i < kctl->count; i++) { |
1960 | const hda_nid_t *nids = spec->capsrc_nids; | 1978 | err = snd_hda_add_nid(codec, kctl, i, |
1961 | if (!nids) | 1979 | get_capsrc(spec, i)); |
1962 | nids = spec->adc_nids; | ||
1963 | err = snd_hda_add_nid(codec, kctl, i, nids[i]); | ||
1964 | if (err < 0) | 1980 | if (err < 0) |
1965 | return err; | 1981 | return err; |
1966 | } | 1982 | } |
@@ -2615,6 +2631,8 @@ static const char *alc_get_line_out_pfx(struct alc_spec *spec, int ch, | |||
2615 | case AUTO_PIN_SPEAKER_OUT: | 2631 | case AUTO_PIN_SPEAKER_OUT: |
2616 | if (cfg->line_outs == 1) | 2632 | if (cfg->line_outs == 1) |
2617 | return "Speaker"; | 2633 | return "Speaker"; |
2634 | if (cfg->line_outs == 2) | ||
2635 | return ch ? "Bass Speaker" : "Speaker"; | ||
2618 | break; | 2636 | break; |
2619 | case AUTO_PIN_HP_OUT: | 2637 | case AUTO_PIN_HP_OUT: |
2620 | /* for multi-io case, only the primary out */ | 2638 | /* for multi-io case, only the primary out */ |
@@ -2747,8 +2765,7 @@ static int alc_auto_create_input_ctls(struct hda_codec *codec) | |||
2747 | } | 2765 | } |
2748 | 2766 | ||
2749 | for (c = 0; c < num_adcs; c++) { | 2767 | for (c = 0; c < num_adcs; c++) { |
2750 | hda_nid_t cap = spec->capsrc_nids ? | 2768 | hda_nid_t cap = get_capsrc(spec, c); |
2751 | spec->capsrc_nids[c] : spec->adc_nids[c]; | ||
2752 | idx = get_connection_index(codec, cap, pin); | 2769 | idx = get_connection_index(codec, cap, pin); |
2753 | if (idx >= 0) { | 2770 | if (idx >= 0) { |
2754 | spec->imux_pins[imux->num_items] = pin; | 2771 | spec->imux_pins[imux->num_items] = pin; |
@@ -2889,7 +2906,7 @@ static hda_nid_t alc_auto_look_for_dac(struct hda_codec *codec, hda_nid_t pin) | |||
2889 | if (!nid) | 2906 | if (!nid) |
2890 | continue; | 2907 | continue; |
2891 | if (found_in_nid_list(nid, spec->multiout.dac_nids, | 2908 | if (found_in_nid_list(nid, spec->multiout.dac_nids, |
2892 | spec->multiout.num_dacs)) | 2909 | ARRAY_SIZE(spec->private_dac_nids))) |
2893 | continue; | 2910 | continue; |
2894 | if (found_in_nid_list(nid, spec->multiout.hp_out_nid, | 2911 | if (found_in_nid_list(nid, spec->multiout.hp_out_nid, |
2895 | ARRAY_SIZE(spec->multiout.hp_out_nid))) | 2912 | ARRAY_SIZE(spec->multiout.hp_out_nid))) |
@@ -2910,6 +2927,7 @@ static hda_nid_t get_dac_if_single(struct hda_codec *codec, hda_nid_t pin) | |||
2910 | return 0; | 2927 | return 0; |
2911 | } | 2928 | } |
2912 | 2929 | ||
2930 | /* return 0 if no possible DAC is found, 1 if one or more found */ | ||
2913 | static int alc_auto_fill_extra_dacs(struct hda_codec *codec, int num_outs, | 2931 | static int alc_auto_fill_extra_dacs(struct hda_codec *codec, int num_outs, |
2914 | const hda_nid_t *pins, hda_nid_t *dacs) | 2932 | const hda_nid_t *pins, hda_nid_t *dacs) |
2915 | { | 2933 | { |
@@ -2927,7 +2945,7 @@ static int alc_auto_fill_extra_dacs(struct hda_codec *codec, int num_outs, | |||
2927 | if (!dacs[i]) | 2945 | if (!dacs[i]) |
2928 | dacs[i] = alc_auto_look_for_dac(codec, pins[i]); | 2946 | dacs[i] = alc_auto_look_for_dac(codec, pins[i]); |
2929 | } | 2947 | } |
2930 | return 0; | 2948 | return 1; |
2931 | } | 2949 | } |
2932 | 2950 | ||
2933 | static int alc_auto_fill_multi_ios(struct hda_codec *codec, | 2951 | static int alc_auto_fill_multi_ios(struct hda_codec *codec, |
@@ -2937,7 +2955,7 @@ static int alc_auto_fill_multi_ios(struct hda_codec *codec, | |||
2937 | static int alc_auto_fill_dac_nids(struct hda_codec *codec) | 2955 | static int alc_auto_fill_dac_nids(struct hda_codec *codec) |
2938 | { | 2956 | { |
2939 | struct alc_spec *spec = codec->spec; | 2957 | struct alc_spec *spec = codec->spec; |
2940 | const struct auto_pin_cfg *cfg = &spec->autocfg; | 2958 | struct auto_pin_cfg *cfg = &spec->autocfg; |
2941 | bool redone = false; | 2959 | bool redone = false; |
2942 | int i; | 2960 | int i; |
2943 | 2961 | ||
@@ -2948,6 +2966,7 @@ static int alc_auto_fill_dac_nids(struct hda_codec *codec) | |||
2948 | spec->multiout.extra_out_nid[0] = 0; | 2966 | spec->multiout.extra_out_nid[0] = 0; |
2949 | memset(spec->private_dac_nids, 0, sizeof(spec->private_dac_nids)); | 2967 | memset(spec->private_dac_nids, 0, sizeof(spec->private_dac_nids)); |
2950 | spec->multiout.dac_nids = spec->private_dac_nids; | 2968 | spec->multiout.dac_nids = spec->private_dac_nids; |
2969 | spec->multi_ios = 0; | ||
2951 | 2970 | ||
2952 | /* fill hard-wired DACs first */ | 2971 | /* fill hard-wired DACs first */ |
2953 | if (!redone) { | 2972 | if (!redone) { |
@@ -2981,10 +3000,12 @@ static int alc_auto_fill_dac_nids(struct hda_codec *codec) | |||
2981 | for (i = 0; i < cfg->line_outs; i++) { | 3000 | for (i = 0; i < cfg->line_outs; i++) { |
2982 | if (spec->private_dac_nids[i]) | 3001 | if (spec->private_dac_nids[i]) |
2983 | spec->multiout.num_dacs++; | 3002 | spec->multiout.num_dacs++; |
2984 | else | 3003 | else { |
2985 | memmove(spec->private_dac_nids + i, | 3004 | memmove(spec->private_dac_nids + i, |
2986 | spec->private_dac_nids + i + 1, | 3005 | spec->private_dac_nids + i + 1, |
2987 | sizeof(hda_nid_t) * (cfg->line_outs - i - 1)); | 3006 | sizeof(hda_nid_t) * (cfg->line_outs - i - 1)); |
3007 | spec->private_dac_nids[cfg->line_outs - 1] = 0; | ||
3008 | } | ||
2988 | } | 3009 | } |
2989 | 3010 | ||
2990 | if (cfg->line_outs == 1 && cfg->line_out_type != AUTO_PIN_SPEAKER_OUT) { | 3011 | if (cfg->line_outs == 1 && cfg->line_out_type != AUTO_PIN_SPEAKER_OUT) { |
@@ -3006,9 +3027,28 @@ static int alc_auto_fill_dac_nids(struct hda_codec *codec) | |||
3006 | if (cfg->line_out_type != AUTO_PIN_HP_OUT) | 3027 | if (cfg->line_out_type != AUTO_PIN_HP_OUT) |
3007 | alc_auto_fill_extra_dacs(codec, cfg->hp_outs, cfg->hp_pins, | 3028 | alc_auto_fill_extra_dacs(codec, cfg->hp_outs, cfg->hp_pins, |
3008 | spec->multiout.hp_out_nid); | 3029 | spec->multiout.hp_out_nid); |
3009 | if (cfg->line_out_type != AUTO_PIN_SPEAKER_OUT) | 3030 | if (cfg->line_out_type != AUTO_PIN_SPEAKER_OUT) { |
3010 | alc_auto_fill_extra_dacs(codec, cfg->speaker_outs, cfg->speaker_pins, | 3031 | int err = alc_auto_fill_extra_dacs(codec, cfg->speaker_outs, |
3011 | spec->multiout.extra_out_nid); | 3032 | cfg->speaker_pins, |
3033 | spec->multiout.extra_out_nid); | ||
3034 | /* if no speaker volume is assigned, try again as the primary | ||
3035 | * output | ||
3036 | */ | ||
3037 | if (!err && cfg->speaker_outs > 0 && | ||
3038 | cfg->line_out_type == AUTO_PIN_HP_OUT) { | ||
3039 | cfg->hp_outs = cfg->line_outs; | ||
3040 | memcpy(cfg->hp_pins, cfg->line_out_pins, | ||
3041 | sizeof(cfg->hp_pins)); | ||
3042 | cfg->line_outs = cfg->speaker_outs; | ||
3043 | memcpy(cfg->line_out_pins, cfg->speaker_pins, | ||
3044 | sizeof(cfg->speaker_pins)); | ||
3045 | cfg->speaker_outs = 0; | ||
3046 | memset(cfg->speaker_pins, 0, sizeof(cfg->speaker_pins)); | ||
3047 | cfg->line_out_type = AUTO_PIN_SPEAKER_OUT; | ||
3048 | redone = false; | ||
3049 | goto again; | ||
3050 | } | ||
3051 | } | ||
3012 | 3052 | ||
3013 | return 0; | 3053 | return 0; |
3014 | } | 3054 | } |
@@ -3158,7 +3198,8 @@ static int alc_auto_create_multi_out_ctls(struct hda_codec *codec, | |||
3158 | } | 3198 | } |
3159 | 3199 | ||
3160 | static int alc_auto_create_extra_out(struct hda_codec *codec, hda_nid_t pin, | 3200 | static int alc_auto_create_extra_out(struct hda_codec *codec, hda_nid_t pin, |
3161 | hda_nid_t dac, const char *pfx) | 3201 | hda_nid_t dac, const char *pfx, |
3202 | int cidx) | ||
3162 | { | 3203 | { |
3163 | struct alc_spec *spec = codec->spec; | 3204 | struct alc_spec *spec = codec->spec; |
3164 | hda_nid_t sw, vol; | 3205 | hda_nid_t sw, vol; |
@@ -3174,15 +3215,15 @@ static int alc_auto_create_extra_out(struct hda_codec *codec, hda_nid_t pin, | |||
3174 | if (is_ctl_used(spec->sw_ctls, val)) | 3215 | if (is_ctl_used(spec->sw_ctls, val)) |
3175 | return 0; /* already created */ | 3216 | return 0; /* already created */ |
3176 | mark_ctl_usage(spec->sw_ctls, val); | 3217 | mark_ctl_usage(spec->sw_ctls, val); |
3177 | return add_pb_sw_ctrl(spec, ALC_CTL_WIDGET_MUTE, pfx, val); | 3218 | return __add_pb_sw_ctrl(spec, ALC_CTL_WIDGET_MUTE, pfx, cidx, val); |
3178 | } | 3219 | } |
3179 | 3220 | ||
3180 | sw = alc_look_for_out_mute_nid(codec, pin, dac); | 3221 | sw = alc_look_for_out_mute_nid(codec, pin, dac); |
3181 | vol = alc_look_for_out_vol_nid(codec, pin, dac); | 3222 | vol = alc_look_for_out_vol_nid(codec, pin, dac); |
3182 | err = alc_auto_add_stereo_vol(codec, pfx, 0, vol); | 3223 | err = alc_auto_add_stereo_vol(codec, pfx, cidx, vol); |
3183 | if (err < 0) | 3224 | if (err < 0) |
3184 | return err; | 3225 | return err; |
3185 | err = alc_auto_add_stereo_sw(codec, pfx, 0, sw); | 3226 | err = alc_auto_add_stereo_sw(codec, pfx, cidx, sw); |
3186 | if (err < 0) | 3227 | if (err < 0) |
3187 | return err; | 3228 | return err; |
3188 | return 0; | 3229 | return 0; |
@@ -3223,16 +3264,21 @@ static int alc_auto_create_extra_outs(struct hda_codec *codec, int num_pins, | |||
3223 | hda_nid_t dac = *dacs; | 3264 | hda_nid_t dac = *dacs; |
3224 | if (!dac) | 3265 | if (!dac) |
3225 | dac = spec->multiout.dac_nids[0]; | 3266 | dac = spec->multiout.dac_nids[0]; |
3226 | return alc_auto_create_extra_out(codec, *pins, dac, pfx); | 3267 | return alc_auto_create_extra_out(codec, *pins, dac, pfx, 0); |
3227 | } | 3268 | } |
3228 | 3269 | ||
3229 | if (dacs[num_pins - 1]) { | 3270 | if (dacs[num_pins - 1]) { |
3230 | /* OK, we have a multi-output system with individual volumes */ | 3271 | /* OK, we have a multi-output system with individual volumes */ |
3231 | for (i = 0; i < num_pins; i++) { | 3272 | for (i = 0; i < num_pins; i++) { |
3232 | snprintf(name, sizeof(name), "%s %s", | 3273 | if (num_pins >= 3) { |
3233 | pfx, channel_name[i]); | 3274 | snprintf(name, sizeof(name), "%s %s", |
3234 | err = alc_auto_create_extra_out(codec, pins[i], dacs[i], | 3275 | pfx, channel_name[i]); |
3235 | name); | 3276 | err = alc_auto_create_extra_out(codec, pins[i], dacs[i], |
3277 | name, 0); | ||
3278 | } else { | ||
3279 | err = alc_auto_create_extra_out(codec, pins[i], dacs[i], | ||
3280 | pfx, i); | ||
3281 | } | ||
3236 | if (err < 0) | 3282 | if (err < 0) |
3237 | return err; | 3283 | return err; |
3238 | } | 3284 | } |
@@ -3694,8 +3740,7 @@ static int init_capsrc_for_pin(struct hda_codec *codec, hda_nid_t pin) | |||
3694 | if (!pin) | 3740 | if (!pin) |
3695 | return 0; | 3741 | return 0; |
3696 | for (i = 0; i < spec->num_adc_nids; i++) { | 3742 | for (i = 0; i < spec->num_adc_nids; i++) { |
3697 | hda_nid_t cap = spec->capsrc_nids ? | 3743 | hda_nid_t cap = get_capsrc(spec, i); |
3698 | spec->capsrc_nids[i] : spec->adc_nids[i]; | ||
3699 | int idx; | 3744 | int idx; |
3700 | 3745 | ||
3701 | idx = get_connection_index(codec, cap, pin); | 3746 | idx = get_connection_index(codec, cap, pin); |
diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index edc2b7bc177c..eeb25d529e30 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c | |||
@@ -215,6 +215,7 @@ struct sigmatel_spec { | |||
215 | unsigned int gpio_mute; | 215 | unsigned int gpio_mute; |
216 | unsigned int gpio_led; | 216 | unsigned int gpio_led; |
217 | unsigned int gpio_led_polarity; | 217 | unsigned int gpio_led_polarity; |
218 | unsigned int vref_mute_led_nid; /* pin NID for mute-LED vref control */ | ||
218 | unsigned int vref_led; | 219 | unsigned int vref_led; |
219 | 220 | ||
220 | /* stream */ | 221 | /* stream */ |
@@ -227,7 +228,6 @@ struct sigmatel_spec { | |||
227 | 228 | ||
228 | /* power management */ | 229 | /* power management */ |
229 | unsigned int num_pwrs; | 230 | unsigned int num_pwrs; |
230 | const unsigned int *pwr_mapping; | ||
231 | const hda_nid_t *pwr_nids; | 231 | const hda_nid_t *pwr_nids; |
232 | const hda_nid_t *dac_list; | 232 | const hda_nid_t *dac_list; |
233 | 233 | ||
@@ -374,18 +374,15 @@ static const unsigned long stac92hd73xx_capvols[] = { | |||
374 | 374 | ||
375 | #define STAC92HD83_DAC_COUNT 3 | 375 | #define STAC92HD83_DAC_COUNT 3 |
376 | 376 | ||
377 | static const hda_nid_t stac92hd83xxx_pwr_nids[4] = { | 377 | static const hda_nid_t stac92hd83xxx_pwr_nids[7] = { |
378 | 0xa, 0xb, 0xd, 0xe, | 378 | 0x0a, 0x0b, 0x0c, 0xd, 0x0e, |
379 | 0x0f, 0x10 | ||
379 | }; | 380 | }; |
380 | 381 | ||
381 | static const hda_nid_t stac92hd83xxx_slave_dig_outs[2] = { | 382 | static const hda_nid_t stac92hd83xxx_slave_dig_outs[2] = { |
382 | 0x1e, 0, | 383 | 0x1e, 0, |
383 | }; | 384 | }; |
384 | 385 | ||
385 | static const unsigned int stac92hd83xxx_pwr_mapping[4] = { | ||
386 | 0x03, 0x0c, 0x20, 0x40, | ||
387 | }; | ||
388 | |||
389 | static const hda_nid_t stac92hd83xxx_dmic_nids[] = { | 386 | static const hda_nid_t stac92hd83xxx_dmic_nids[] = { |
390 | 0x11, 0x20, | 387 | 0x11, 0x20, |
391 | }; | 388 | }; |
@@ -1645,6 +1642,8 @@ static const struct snd_pci_quirk stac92hd73xx_codec_id_cfg_tbl[] = { | |||
1645 | "Alienware M17x", STAC_ALIENWARE_M17X), | 1642 | "Alienware M17x", STAC_ALIENWARE_M17X), |
1646 | SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x043a, | 1643 | SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x043a, |
1647 | "Alienware M17x", STAC_ALIENWARE_M17X), | 1644 | "Alienware M17x", STAC_ALIENWARE_M17X), |
1645 | SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0490, | ||
1646 | "Alienware M17x", STAC_ALIENWARE_M17X), | ||
1648 | {} /* terminator */ | 1647 | {} /* terminator */ |
1649 | }; | 1648 | }; |
1650 | 1649 | ||
@@ -4320,12 +4319,10 @@ static void stac_store_hints(struct hda_codec *codec) | |||
4320 | spec->eapd_switch = val; | 4319 | spec->eapd_switch = val; |
4321 | get_int_hint(codec, "gpio_led_polarity", &spec->gpio_led_polarity); | 4320 | get_int_hint(codec, "gpio_led_polarity", &spec->gpio_led_polarity); |
4322 | if (get_int_hint(codec, "gpio_led", &spec->gpio_led)) { | 4321 | if (get_int_hint(codec, "gpio_led", &spec->gpio_led)) { |
4323 | if (spec->gpio_led <= 8) { | 4322 | spec->gpio_mask |= spec->gpio_led; |
4324 | spec->gpio_mask |= spec->gpio_led; | 4323 | spec->gpio_dir |= spec->gpio_led; |
4325 | spec->gpio_dir |= spec->gpio_led; | 4324 | if (spec->gpio_led_polarity) |
4326 | if (spec->gpio_led_polarity) | 4325 | spec->gpio_data |= spec->gpio_led; |
4327 | spec->gpio_data |= spec->gpio_led; | ||
4328 | } | ||
4329 | } | 4326 | } |
4330 | } | 4327 | } |
4331 | 4328 | ||
@@ -4443,7 +4440,9 @@ static int stac92xx_init(struct hda_codec *codec) | |||
4443 | int pinctl, def_conf; | 4440 | int pinctl, def_conf; |
4444 | 4441 | ||
4445 | /* power on when no jack detection is available */ | 4442 | /* power on when no jack detection is available */ |
4446 | if (!spec->hp_detect) { | 4443 | /* or when the VREF is used for controlling LED */ |
4444 | if (!spec->hp_detect || | ||
4445 | spec->vref_mute_led_nid == nid) { | ||
4447 | stac_toggle_power_map(codec, nid, 1); | 4446 | stac_toggle_power_map(codec, nid, 1); |
4448 | continue; | 4447 | continue; |
4449 | } | 4448 | } |
@@ -4470,8 +4469,12 @@ static int stac92xx_init(struct hda_codec *codec) | |||
4470 | stac_toggle_power_map(codec, nid, 1); | 4469 | stac_toggle_power_map(codec, nid, 1); |
4471 | continue; | 4470 | continue; |
4472 | } | 4471 | } |
4473 | if (enable_pin_detect(codec, nid, STAC_PWR_EVENT)) | 4472 | if (enable_pin_detect(codec, nid, STAC_PWR_EVENT)) { |
4474 | stac_issue_unsol_event(codec, nid); | 4473 | stac_issue_unsol_event(codec, nid); |
4474 | continue; | ||
4475 | } | ||
4476 | /* none of the above, turn the port OFF */ | ||
4477 | stac_toggle_power_map(codec, nid, 0); | ||
4475 | } | 4478 | } |
4476 | 4479 | ||
4477 | /* sync mute LED */ | 4480 | /* sync mute LED */ |
@@ -4727,11 +4730,7 @@ static void stac_toggle_power_map(struct hda_codec *codec, hda_nid_t nid, | |||
4727 | if (idx >= spec->num_pwrs) | 4730 | if (idx >= spec->num_pwrs) |
4728 | return; | 4731 | return; |
4729 | 4732 | ||
4730 | /* several codecs have two power down bits */ | 4733 | idx = 1 << idx; |
4731 | if (spec->pwr_mapping) | ||
4732 | idx = spec->pwr_mapping[idx]; | ||
4733 | else | ||
4734 | idx = 1 << idx; | ||
4735 | 4734 | ||
4736 | val = snd_hda_codec_read(codec, codec->afg, 0, 0x0fec, 0x0) & 0xff; | 4735 | val = snd_hda_codec_read(codec, codec->afg, 0, 0x0fec, 0x0) & 0xff; |
4737 | if (enable) | 4736 | if (enable) |
@@ -4915,8 +4914,14 @@ static int find_mute_led_gpio(struct hda_codec *codec, int default_polarity) | |||
4915 | if (sscanf(dev->name, "HP_Mute_LED_%d_%x", | 4914 | if (sscanf(dev->name, "HP_Mute_LED_%d_%x", |
4916 | &spec->gpio_led_polarity, | 4915 | &spec->gpio_led_polarity, |
4917 | &spec->gpio_led) == 2) { | 4916 | &spec->gpio_led) == 2) { |
4918 | if (spec->gpio_led < 4) | 4917 | unsigned int max_gpio; |
4918 | max_gpio = snd_hda_param_read(codec, codec->afg, | ||
4919 | AC_PAR_GPIO_CAP); | ||
4920 | max_gpio &= AC_GPIO_IO_COUNT; | ||
4921 | if (spec->gpio_led < max_gpio) | ||
4919 | spec->gpio_led = 1 << spec->gpio_led; | 4922 | spec->gpio_led = 1 << spec->gpio_led; |
4923 | else | ||
4924 | spec->vref_mute_led_nid = spec->gpio_led; | ||
4920 | return 1; | 4925 | return 1; |
4921 | } | 4926 | } |
4922 | if (sscanf(dev->name, "HP_Mute_LED_%d", | 4927 | if (sscanf(dev->name, "HP_Mute_LED_%d", |
@@ -5045,29 +5050,12 @@ static int stac92xx_pre_resume(struct hda_codec *codec) | |||
5045 | struct sigmatel_spec *spec = codec->spec; | 5050 | struct sigmatel_spec *spec = codec->spec; |
5046 | 5051 | ||
5047 | /* sync mute LED */ | 5052 | /* sync mute LED */ |
5048 | if (spec->gpio_led) { | 5053 | if (spec->vref_mute_led_nid) |
5049 | if (spec->gpio_led <= 8) { | 5054 | stac_vrefout_set(codec, spec->vref_mute_led_nid, |
5050 | stac_gpio_set(codec, spec->gpio_mask, | 5055 | spec->vref_led); |
5051 | spec->gpio_dir, spec->gpio_data); | 5056 | else if (spec->gpio_led) |
5052 | } else { | 5057 | stac_gpio_set(codec, spec->gpio_mask, |
5053 | stac_vrefout_set(codec, | 5058 | spec->gpio_dir, spec->gpio_data); |
5054 | spec->gpio_led, spec->vref_led); | ||
5055 | } | ||
5056 | } | ||
5057 | return 0; | ||
5058 | } | ||
5059 | |||
5060 | static int stac92xx_post_suspend(struct hda_codec *codec) | ||
5061 | { | ||
5062 | struct sigmatel_spec *spec = codec->spec; | ||
5063 | if (spec->gpio_led > 8) { | ||
5064 | /* with vref-out pin used for mute led control | ||
5065 | * codec AFG is prevented from D3 state, but on | ||
5066 | * system suspend it can (and should) be used | ||
5067 | */ | ||
5068 | snd_hda_codec_read(codec, codec->afg, 0, | ||
5069 | AC_VERB_SET_POWER_STATE, AC_PWRST_D3); | ||
5070 | } | ||
5071 | return 0; | 5059 | return 0; |
5072 | } | 5060 | } |
5073 | 5061 | ||
@@ -5078,7 +5066,7 @@ static void stac92xx_set_power_state(struct hda_codec *codec, hda_nid_t fg, | |||
5078 | struct sigmatel_spec *spec = codec->spec; | 5066 | struct sigmatel_spec *spec = codec->spec; |
5079 | 5067 | ||
5080 | if (power_state == AC_PWRST_D3) { | 5068 | if (power_state == AC_PWRST_D3) { |
5081 | if (spec->gpio_led > 8) { | 5069 | if (spec->vref_mute_led_nid) { |
5082 | /* with vref-out pin used for mute led control | 5070 | /* with vref-out pin used for mute led control |
5083 | * codec AFG is prevented from D3 state | 5071 | * codec AFG is prevented from D3 state |
5084 | */ | 5072 | */ |
@@ -5131,7 +5119,7 @@ static int stac92xx_update_led_status(struct hda_codec *codec) | |||
5131 | } | 5119 | } |
5132 | } | 5120 | } |
5133 | /*polarity defines *not* muted state level*/ | 5121 | /*polarity defines *not* muted state level*/ |
5134 | if (spec->gpio_led <= 8) { | 5122 | if (!spec->vref_mute_led_nid) { |
5135 | if (muted) | 5123 | if (muted) |
5136 | spec->gpio_data &= ~spec->gpio_led; /* orange */ | 5124 | spec->gpio_data &= ~spec->gpio_led; /* orange */ |
5137 | else | 5125 | else |
@@ -5149,7 +5137,8 @@ static int stac92xx_update_led_status(struct hda_codec *codec) | |||
5149 | muted_lvl = spec->gpio_led_polarity ? | 5137 | muted_lvl = spec->gpio_led_polarity ? |
5150 | AC_PINCTL_VREF_GRD : AC_PINCTL_VREF_HIZ; | 5138 | AC_PINCTL_VREF_GRD : AC_PINCTL_VREF_HIZ; |
5151 | spec->vref_led = muted ? muted_lvl : notmtd_lvl; | 5139 | spec->vref_led = muted ? muted_lvl : notmtd_lvl; |
5152 | stac_vrefout_set(codec, spec->gpio_led, spec->vref_led); | 5140 | stac_vrefout_set(codec, spec->vref_mute_led_nid, |
5141 | spec->vref_led); | ||
5153 | } | 5142 | } |
5154 | return 0; | 5143 | return 0; |
5155 | } | 5144 | } |
@@ -5629,9 +5618,6 @@ static int patch_stac92hd83xxx(struct hda_codec *codec) | |||
5629 | snd_hda_codec_set_pincfg(codec, 0xf, 0x2181205e); | 5618 | snd_hda_codec_set_pincfg(codec, 0xf, 0x2181205e); |
5630 | } | 5619 | } |
5631 | 5620 | ||
5632 | /* reset pin power-down; Windows may leave these bits after reboot */ | ||
5633 | snd_hda_codec_write_cache(codec, codec->afg, 0, 0x7EC, 0); | ||
5634 | snd_hda_codec_write_cache(codec, codec->afg, 0, 0x7ED, 0); | ||
5635 | codec->no_trigger_sense = 1; | 5621 | codec->no_trigger_sense = 1; |
5636 | codec->spec = spec; | 5622 | codec->spec = spec; |
5637 | 5623 | ||
@@ -5641,7 +5627,6 @@ static int patch_stac92hd83xxx(struct hda_codec *codec) | |||
5641 | codec->slave_dig_outs = stac92hd83xxx_slave_dig_outs; | 5627 | codec->slave_dig_outs = stac92hd83xxx_slave_dig_outs; |
5642 | spec->digbeep_nid = 0x21; | 5628 | spec->digbeep_nid = 0x21; |
5643 | spec->pwr_nids = stac92hd83xxx_pwr_nids; | 5629 | spec->pwr_nids = stac92hd83xxx_pwr_nids; |
5644 | spec->pwr_mapping = stac92hd83xxx_pwr_mapping; | ||
5645 | spec->num_pwrs = ARRAY_SIZE(stac92hd83xxx_pwr_nids); | 5630 | spec->num_pwrs = ARRAY_SIZE(stac92hd83xxx_pwr_nids); |
5646 | spec->multiout.dac_nids = spec->dac_nids; | 5631 | spec->multiout.dac_nids = spec->dac_nids; |
5647 | spec->init = stac92hd83xxx_core_init; | 5632 | spec->init = stac92hd83xxx_core_init; |
@@ -5658,9 +5643,6 @@ again: | |||
5658 | stac92xx_set_config_regs(codec, | 5643 | stac92xx_set_config_regs(codec, |
5659 | stac92hd83xxx_brd_tbl[spec->board_config]); | 5644 | stac92hd83xxx_brd_tbl[spec->board_config]); |
5660 | 5645 | ||
5661 | if (spec->board_config != STAC_92HD83XXX_PWR_REF) | ||
5662 | spec->num_pwrs = 0; | ||
5663 | |||
5664 | codec->patch_ops = stac92xx_patch_ops; | 5646 | codec->patch_ops = stac92xx_patch_ops; |
5665 | 5647 | ||
5666 | if (find_mute_led_gpio(codec, 0)) | 5648 | if (find_mute_led_gpio(codec, 0)) |
@@ -5670,15 +5652,13 @@ again: | |||
5670 | 5652 | ||
5671 | #ifdef CONFIG_SND_HDA_POWER_SAVE | 5653 | #ifdef CONFIG_SND_HDA_POWER_SAVE |
5672 | if (spec->gpio_led) { | 5654 | if (spec->gpio_led) { |
5673 | if (spec->gpio_led <= 8) { | 5655 | if (!spec->vref_mute_led_nid) { |
5674 | spec->gpio_mask |= spec->gpio_led; | 5656 | spec->gpio_mask |= spec->gpio_led; |
5675 | spec->gpio_dir |= spec->gpio_led; | 5657 | spec->gpio_dir |= spec->gpio_led; |
5676 | spec->gpio_data |= spec->gpio_led; | 5658 | spec->gpio_data |= spec->gpio_led; |
5677 | } else { | 5659 | } else { |
5678 | codec->patch_ops.set_power_state = | 5660 | codec->patch_ops.set_power_state = |
5679 | stac92xx_set_power_state; | 5661 | stac92xx_set_power_state; |
5680 | codec->patch_ops.post_suspend = | ||
5681 | stac92xx_post_suspend; | ||
5682 | } | 5662 | } |
5683 | codec->patch_ops.pre_resume = stac92xx_pre_resume; | 5663 | codec->patch_ops.pre_resume = stac92xx_pre_resume; |
5684 | codec->patch_ops.check_power_status = | 5664 | codec->patch_ops.check_power_status = |
@@ -5869,8 +5849,6 @@ again: | |||
5869 | (codec->revision_id & 0xf) == 1) | 5849 | (codec->revision_id & 0xf) == 1) |
5870 | spec->stream_delay = 40; /* 40 milliseconds */ | 5850 | spec->stream_delay = 40; /* 40 milliseconds */ |
5871 | 5851 | ||
5872 | /* no output amps */ | ||
5873 | spec->num_pwrs = 0; | ||
5874 | /* disable VSW */ | 5852 | /* disable VSW */ |
5875 | spec->init = stac92hd71bxx_core_init; | 5853 | spec->init = stac92hd71bxx_core_init; |
5876 | unmute_init++; | 5854 | unmute_init++; |
@@ -5885,8 +5863,6 @@ again: | |||
5885 | if ((codec->revision_id & 0xf) == 1) | 5863 | if ((codec->revision_id & 0xf) == 1) |
5886 | spec->stream_delay = 40; /* 40 milliseconds */ | 5864 | spec->stream_delay = 40; /* 40 milliseconds */ |
5887 | 5865 | ||
5888 | /* no output amps */ | ||
5889 | spec->num_pwrs = 0; | ||
5890 | /* fallthru */ | 5866 | /* fallthru */ |
5891 | default: | 5867 | default: |
5892 | spec->init = stac92hd71bxx_core_init; | 5868 | spec->init = stac92hd71bxx_core_init; |
@@ -5989,15 +5965,13 @@ again: | |||
5989 | 5965 | ||
5990 | #ifdef CONFIG_SND_HDA_POWER_SAVE | 5966 | #ifdef CONFIG_SND_HDA_POWER_SAVE |
5991 | if (spec->gpio_led) { | 5967 | if (spec->gpio_led) { |
5992 | if (spec->gpio_led <= 8) { | 5968 | if (!spec->vref_mute_led_nid) { |
5993 | spec->gpio_mask |= spec->gpio_led; | 5969 | spec->gpio_mask |= spec->gpio_led; |
5994 | spec->gpio_dir |= spec->gpio_led; | 5970 | spec->gpio_dir |= spec->gpio_led; |
5995 | spec->gpio_data |= spec->gpio_led; | 5971 | spec->gpio_data |= spec->gpio_led; |
5996 | } else { | 5972 | } else { |
5997 | codec->patch_ops.set_power_state = | 5973 | codec->patch_ops.set_power_state = |
5998 | stac92xx_set_power_state; | 5974 | stac92xx_set_power_state; |
5999 | codec->patch_ops.post_suspend = | ||
6000 | stac92xx_post_suspend; | ||
6001 | } | 5975 | } |
6002 | codec->patch_ops.pre_resume = stac92xx_pre_resume; | 5976 | codec->patch_ops.pre_resume = stac92xx_pre_resume; |
6003 | codec->patch_ops.check_power_status = | 5977 | codec->patch_ops.check_power_status = |
diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c index 431c0d417eeb..b5137629f8e9 100644 --- a/sound/pci/hda/patch_via.c +++ b/sound/pci/hda/patch_via.c | |||
@@ -208,6 +208,7 @@ struct via_spec { | |||
208 | /* work to check hp jack state */ | 208 | /* work to check hp jack state */ |
209 | struct hda_codec *codec; | 209 | struct hda_codec *codec; |
210 | struct delayed_work vt1708_hp_work; | 210 | struct delayed_work vt1708_hp_work; |
211 | int hp_work_active; | ||
211 | int vt1708_jack_detect; | 212 | int vt1708_jack_detect; |
212 | int vt1708_hp_present; | 213 | int vt1708_hp_present; |
213 | 214 | ||
@@ -305,27 +306,35 @@ enum { | |||
305 | static void analog_low_current_mode(struct hda_codec *codec); | 306 | static void analog_low_current_mode(struct hda_codec *codec); |
306 | static bool is_aa_path_mute(struct hda_codec *codec); | 307 | static bool is_aa_path_mute(struct hda_codec *codec); |
307 | 308 | ||
308 | static void vt1708_start_hp_work(struct via_spec *spec) | 309 | #define hp_detect_with_aa(codec) \ |
310 | (snd_hda_get_bool_hint(codec, "analog_loopback_hp_detect") == 1 && \ | ||
311 | !is_aa_path_mute(codec)) | ||
312 | |||
313 | static void vt1708_stop_hp_work(struct via_spec *spec) | ||
309 | { | 314 | { |
310 | if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0) | 315 | if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0) |
311 | return; | 316 | return; |
312 | snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, | 317 | if (spec->hp_work_active) { |
313 | !spec->vt1708_jack_detect); | 318 | snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, 1); |
314 | if (!delayed_work_pending(&spec->vt1708_hp_work)) | 319 | cancel_delayed_work_sync(&spec->vt1708_hp_work); |
315 | schedule_delayed_work(&spec->vt1708_hp_work, | 320 | spec->hp_work_active = 0; |
316 | msecs_to_jiffies(100)); | 321 | } |
317 | } | 322 | } |
318 | 323 | ||
319 | static void vt1708_stop_hp_work(struct via_spec *spec) | 324 | static void vt1708_update_hp_work(struct via_spec *spec) |
320 | { | 325 | { |
321 | if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0) | 326 | if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0) |
322 | return; | 327 | return; |
323 | if (snd_hda_get_bool_hint(spec->codec, "analog_loopback_hp_detect") == 1 | 328 | if (spec->vt1708_jack_detect && |
324 | && !is_aa_path_mute(spec->codec)) | 329 | (spec->active_streams || hp_detect_with_aa(spec->codec))) { |
325 | return; | 330 | if (!spec->hp_work_active) { |
326 | snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, | 331 | snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, 0); |
327 | !spec->vt1708_jack_detect); | 332 | schedule_delayed_work(&spec->vt1708_hp_work, |
328 | cancel_delayed_work_sync(&spec->vt1708_hp_work); | 333 | msecs_to_jiffies(100)); |
334 | spec->hp_work_active = 1; | ||
335 | } | ||
336 | } else if (!hp_detect_with_aa(spec->codec)) | ||
337 | vt1708_stop_hp_work(spec); | ||
329 | } | 338 | } |
330 | 339 | ||
331 | static void set_widgets_power_state(struct hda_codec *codec) | 340 | static void set_widgets_power_state(struct hda_codec *codec) |
@@ -343,12 +352,7 @@ static int analog_input_switch_put(struct snd_kcontrol *kcontrol, | |||
343 | 352 | ||
344 | set_widgets_power_state(codec); | 353 | set_widgets_power_state(codec); |
345 | analog_low_current_mode(snd_kcontrol_chip(kcontrol)); | 354 | analog_low_current_mode(snd_kcontrol_chip(kcontrol)); |
346 | if (snd_hda_get_bool_hint(codec, "analog_loopback_hp_detect") == 1) { | 355 | vt1708_update_hp_work(codec->spec); |
347 | if (is_aa_path_mute(codec)) | ||
348 | vt1708_start_hp_work(codec->spec); | ||
349 | else | ||
350 | vt1708_stop_hp_work(codec->spec); | ||
351 | } | ||
352 | return change; | 356 | return change; |
353 | } | 357 | } |
354 | 358 | ||
@@ -1154,7 +1158,7 @@ static int via_playback_multi_pcm_prepare(struct hda_pcm_stream *hinfo, | |||
1154 | spec->cur_dac_stream_tag = stream_tag; | 1158 | spec->cur_dac_stream_tag = stream_tag; |
1155 | spec->cur_dac_format = format; | 1159 | spec->cur_dac_format = format; |
1156 | mutex_unlock(&spec->config_mutex); | 1160 | mutex_unlock(&spec->config_mutex); |
1157 | vt1708_start_hp_work(spec); | 1161 | vt1708_update_hp_work(spec); |
1158 | return 0; | 1162 | return 0; |
1159 | } | 1163 | } |
1160 | 1164 | ||
@@ -1174,7 +1178,7 @@ static int via_playback_hp_pcm_prepare(struct hda_pcm_stream *hinfo, | |||
1174 | spec->cur_hp_stream_tag = stream_tag; | 1178 | spec->cur_hp_stream_tag = stream_tag; |
1175 | spec->cur_hp_format = format; | 1179 | spec->cur_hp_format = format; |
1176 | mutex_unlock(&spec->config_mutex); | 1180 | mutex_unlock(&spec->config_mutex); |
1177 | vt1708_start_hp_work(spec); | 1181 | vt1708_update_hp_work(spec); |
1178 | return 0; | 1182 | return 0; |
1179 | } | 1183 | } |
1180 | 1184 | ||
@@ -1188,7 +1192,7 @@ static int via_playback_multi_pcm_cleanup(struct hda_pcm_stream *hinfo, | |||
1188 | snd_hda_multi_out_analog_cleanup(codec, &spec->multiout); | 1192 | snd_hda_multi_out_analog_cleanup(codec, &spec->multiout); |
1189 | spec->active_streams &= ~STREAM_MULTI_OUT; | 1193 | spec->active_streams &= ~STREAM_MULTI_OUT; |
1190 | mutex_unlock(&spec->config_mutex); | 1194 | mutex_unlock(&spec->config_mutex); |
1191 | vt1708_stop_hp_work(spec); | 1195 | vt1708_update_hp_work(spec); |
1192 | return 0; | 1196 | return 0; |
1193 | } | 1197 | } |
1194 | 1198 | ||
@@ -1203,7 +1207,7 @@ static int via_playback_hp_pcm_cleanup(struct hda_pcm_stream *hinfo, | |||
1203 | snd_hda_codec_setup_stream(codec, spec->hp_dac_nid, 0, 0, 0); | 1207 | snd_hda_codec_setup_stream(codec, spec->hp_dac_nid, 0, 0, 0); |
1204 | spec->active_streams &= ~STREAM_INDEP_HP; | 1208 | spec->active_streams &= ~STREAM_INDEP_HP; |
1205 | mutex_unlock(&spec->config_mutex); | 1209 | mutex_unlock(&spec->config_mutex); |
1206 | vt1708_stop_hp_work(spec); | 1210 | vt1708_update_hp_work(spec); |
1207 | return 0; | 1211 | return 0; |
1208 | } | 1212 | } |
1209 | 1213 | ||
@@ -1645,7 +1649,8 @@ static void via_hp_automute(struct hda_codec *codec) | |||
1645 | int nums; | 1649 | int nums; |
1646 | struct via_spec *spec = codec->spec; | 1650 | struct via_spec *spec = codec->spec; |
1647 | 1651 | ||
1648 | if (!spec->hp_independent_mode && spec->autocfg.hp_pins[0]) | 1652 | if (!spec->hp_independent_mode && spec->autocfg.hp_pins[0] && |
1653 | (spec->codec_type != VT1708 || spec->vt1708_jack_detect)) | ||
1649 | present = snd_hda_jack_detect(codec, spec->autocfg.hp_pins[0]); | 1654 | present = snd_hda_jack_detect(codec, spec->autocfg.hp_pins[0]); |
1650 | 1655 | ||
1651 | if (spec->smart51_enabled) | 1656 | if (spec->smart51_enabled) |
@@ -2612,8 +2617,6 @@ static int vt1708_jack_detect_get(struct snd_kcontrol *kcontrol, | |||
2612 | 2617 | ||
2613 | if (spec->codec_type != VT1708) | 2618 | if (spec->codec_type != VT1708) |
2614 | return 0; | 2619 | return 0; |
2615 | spec->vt1708_jack_detect = | ||
2616 | !((snd_hda_codec_read(codec, 0x1, 0, 0xf84, 0) >> 8) & 0x1); | ||
2617 | ucontrol->value.integer.value[0] = spec->vt1708_jack_detect; | 2620 | ucontrol->value.integer.value[0] = spec->vt1708_jack_detect; |
2618 | return 0; | 2621 | return 0; |
2619 | } | 2622 | } |
@@ -2623,18 +2626,22 @@ static int vt1708_jack_detect_put(struct snd_kcontrol *kcontrol, | |||
2623 | { | 2626 | { |
2624 | struct hda_codec *codec = snd_kcontrol_chip(kcontrol); | 2627 | struct hda_codec *codec = snd_kcontrol_chip(kcontrol); |
2625 | struct via_spec *spec = codec->spec; | 2628 | struct via_spec *spec = codec->spec; |
2626 | int change; | 2629 | int val; |
2627 | 2630 | ||
2628 | if (spec->codec_type != VT1708) | 2631 | if (spec->codec_type != VT1708) |
2629 | return 0; | 2632 | return 0; |
2630 | spec->vt1708_jack_detect = ucontrol->value.integer.value[0]; | 2633 | val = !!ucontrol->value.integer.value[0]; |
2631 | change = (0x1 & (snd_hda_codec_read(codec, 0x1, 0, 0xf84, 0) >> 8)) | 2634 | if (spec->vt1708_jack_detect == val) |
2632 | == !spec->vt1708_jack_detect; | 2635 | return 0; |
2633 | if (spec->vt1708_jack_detect) { | 2636 | spec->vt1708_jack_detect = val; |
2637 | if (spec->vt1708_jack_detect && | ||
2638 | snd_hda_get_bool_hint(codec, "analog_loopback_hp_detect") != 1) { | ||
2634 | mute_aa_path(codec, 1); | 2639 | mute_aa_path(codec, 1); |
2635 | notify_aa_path_ctls(codec); | 2640 | notify_aa_path_ctls(codec); |
2636 | } | 2641 | } |
2637 | return change; | 2642 | via_hp_automute(codec); |
2643 | vt1708_update_hp_work(spec); | ||
2644 | return 1; | ||
2638 | } | 2645 | } |
2639 | 2646 | ||
2640 | static const struct snd_kcontrol_new vt1708_jack_detect_ctl = { | 2647 | static const struct snd_kcontrol_new vt1708_jack_detect_ctl = { |
@@ -2771,6 +2778,7 @@ static int via_init(struct hda_codec *codec) | |||
2771 | via_auto_init_unsol_event(codec); | 2778 | via_auto_init_unsol_event(codec); |
2772 | 2779 | ||
2773 | via_hp_automute(codec); | 2780 | via_hp_automute(codec); |
2781 | vt1708_update_hp_work(spec); | ||
2774 | 2782 | ||
2775 | return 0; | 2783 | return 0; |
2776 | } | 2784 | } |
@@ -2787,7 +2795,9 @@ static void vt1708_update_hp_jack_state(struct work_struct *work) | |||
2787 | spec->vt1708_hp_present ^= 1; | 2795 | spec->vt1708_hp_present ^= 1; |
2788 | via_hp_automute(spec->codec); | 2796 | via_hp_automute(spec->codec); |
2789 | } | 2797 | } |
2790 | vt1708_start_hp_work(spec); | 2798 | if (spec->vt1708_jack_detect) |
2799 | schedule_delayed_work(&spec->vt1708_hp_work, | ||
2800 | msecs_to_jiffies(100)); | ||
2791 | } | 2801 | } |
2792 | 2802 | ||
2793 | static int get_mux_nids(struct hda_codec *codec) | 2803 | static int get_mux_nids(struct hda_codec *codec) |
diff --git a/sound/pci/lx6464es/lx_core.c b/sound/pci/lx6464es/lx_core.c index 5c8717e29eeb..8c3e7fcefd99 100644 --- a/sound/pci/lx6464es/lx_core.c +++ b/sound/pci/lx6464es/lx_core.c | |||
@@ -78,10 +78,15 @@ unsigned long lx_dsp_reg_read(struct lx6464es *chip, int port) | |||
78 | return ioread32(address); | 78 | return ioread32(address); |
79 | } | 79 | } |
80 | 80 | ||
81 | void lx_dsp_reg_readbuf(struct lx6464es *chip, int port, u32 *data, u32 len) | 81 | static void lx_dsp_reg_readbuf(struct lx6464es *chip, int port, u32 *data, |
82 | u32 len) | ||
82 | { | 83 | { |
83 | void __iomem *address = lx_dsp_register(chip, port); | 84 | u32 __iomem *address = lx_dsp_register(chip, port); |
84 | memcpy_fromio(data, address, len*sizeof(u32)); | 85 | int i; |
86 | |||
87 | /* we cannot use memcpy_fromio */ | ||
88 | for (i = 0; i != len; ++i) | ||
89 | data[i] = ioread32(address + i); | ||
85 | } | 90 | } |
86 | 91 | ||
87 | 92 | ||
@@ -91,11 +96,15 @@ void lx_dsp_reg_write(struct lx6464es *chip, int port, unsigned data) | |||
91 | iowrite32(data, address); | 96 | iowrite32(data, address); |
92 | } | 97 | } |
93 | 98 | ||
94 | void lx_dsp_reg_writebuf(struct lx6464es *chip, int port, const u32 *data, | 99 | static void lx_dsp_reg_writebuf(struct lx6464es *chip, int port, |
95 | u32 len) | 100 | const u32 *data, u32 len) |
96 | { | 101 | { |
97 | void __iomem *address = lx_dsp_register(chip, port); | 102 | u32 __iomem *address = lx_dsp_register(chip, port); |
98 | memcpy_toio(address, data, len*sizeof(u32)); | 103 | int i; |
104 | |||
105 | /* we cannot use memcpy_to */ | ||
106 | for (i = 0; i != len; ++i) | ||
107 | iowrite32(data[i], address + i); | ||
99 | } | 108 | } |
100 | 109 | ||
101 | 110 | ||
diff --git a/sound/pci/lx6464es/lx_core.h b/sound/pci/lx6464es/lx_core.h index 1dd562980b6c..4d7ff797a646 100644 --- a/sound/pci/lx6464es/lx_core.h +++ b/sound/pci/lx6464es/lx_core.h | |||
@@ -72,10 +72,7 @@ enum { | |||
72 | }; | 72 | }; |
73 | 73 | ||
74 | unsigned long lx_dsp_reg_read(struct lx6464es *chip, int port); | 74 | unsigned long lx_dsp_reg_read(struct lx6464es *chip, int port); |
75 | void lx_dsp_reg_readbuf(struct lx6464es *chip, int port, u32 *data, u32 len); | ||
76 | void lx_dsp_reg_write(struct lx6464es *chip, int port, unsigned data); | 75 | void lx_dsp_reg_write(struct lx6464es *chip, int port, unsigned data); |
77 | void lx_dsp_reg_writebuf(struct lx6464es *chip, int port, const u32 *data, | ||
78 | u32 len); | ||
79 | 76 | ||
80 | /* plx register access */ | 77 | /* plx register access */ |
81 | enum { | 78 | enum { |
diff --git a/sound/pci/rme9652/hdspm.c b/sound/pci/rme9652/hdspm.c index e760adad9523..19ee2203cbb5 100644 --- a/sound/pci/rme9652/hdspm.c +++ b/sound/pci/rme9652/hdspm.c | |||
@@ -6518,7 +6518,7 @@ static int __devinit snd_hdspm_create(struct snd_card *card, | |||
6518 | hdspm->io_type = AES32; | 6518 | hdspm->io_type = AES32; |
6519 | hdspm->card_name = "RME AES32"; | 6519 | hdspm->card_name = "RME AES32"; |
6520 | hdspm->midiPorts = 2; | 6520 | hdspm->midiPorts = 2; |
6521 | } else if ((hdspm->firmware_rev == 0xd5) || | 6521 | } else if ((hdspm->firmware_rev == 0xd2) || |
6522 | ((hdspm->firmware_rev >= 0xc8) && | 6522 | ((hdspm->firmware_rev >= 0xc8) && |
6523 | (hdspm->firmware_rev <= 0xcf))) { | 6523 | (hdspm->firmware_rev <= 0xcf))) { |
6524 | hdspm->io_type = MADI; | 6524 | hdspm->io_type = MADI; |
diff --git a/sound/pci/sis7019.c b/sound/pci/sis7019.c index a391e622a192..28dfafb56dd1 100644 --- a/sound/pci/sis7019.c +++ b/sound/pci/sis7019.c | |||
@@ -41,6 +41,7 @@ MODULE_SUPPORTED_DEVICE("{{SiS,SiS7019 Audio Accelerator}}"); | |||
41 | static int index = SNDRV_DEFAULT_IDX1; /* Index 0-MAX */ | 41 | static int index = SNDRV_DEFAULT_IDX1; /* Index 0-MAX */ |
42 | static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */ | 42 | static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */ |
43 | static int enable = 1; | 43 | static int enable = 1; |
44 | static int codecs = 1; | ||
44 | 45 | ||
45 | module_param(index, int, 0444); | 46 | module_param(index, int, 0444); |
46 | MODULE_PARM_DESC(index, "Index value for SiS7019 Audio Accelerator."); | 47 | MODULE_PARM_DESC(index, "Index value for SiS7019 Audio Accelerator."); |
@@ -48,6 +49,8 @@ module_param(id, charp, 0444); | |||
48 | MODULE_PARM_DESC(id, "ID string for SiS7019 Audio Accelerator."); | 49 | MODULE_PARM_DESC(id, "ID string for SiS7019 Audio Accelerator."); |
49 | module_param(enable, bool, 0444); | 50 | module_param(enable, bool, 0444); |
50 | MODULE_PARM_DESC(enable, "Enable SiS7019 Audio Accelerator."); | 51 | MODULE_PARM_DESC(enable, "Enable SiS7019 Audio Accelerator."); |
52 | module_param(codecs, int, 0444); | ||
53 | MODULE_PARM_DESC(codecs, "Set bit to indicate that codec number is expected to be present (default 1)"); | ||
51 | 54 | ||
52 | static DEFINE_PCI_DEVICE_TABLE(snd_sis7019_ids) = { | 55 | static DEFINE_PCI_DEVICE_TABLE(snd_sis7019_ids) = { |
53 | { PCI_DEVICE(PCI_VENDOR_ID_SI, 0x7019) }, | 56 | { PCI_DEVICE(PCI_VENDOR_ID_SI, 0x7019) }, |
@@ -140,6 +143,9 @@ struct sis7019 { | |||
140 | dma_addr_t silence_dma_addr; | 143 | dma_addr_t silence_dma_addr; |
141 | }; | 144 | }; |
142 | 145 | ||
146 | /* These values are also used by the module param 'codecs' to indicate | ||
147 | * which codecs should be present. | ||
148 | */ | ||
143 | #define SIS_PRIMARY_CODEC_PRESENT 0x0001 | 149 | #define SIS_PRIMARY_CODEC_PRESENT 0x0001 |
144 | #define SIS_SECONDARY_CODEC_PRESENT 0x0002 | 150 | #define SIS_SECONDARY_CODEC_PRESENT 0x0002 |
145 | #define SIS_TERTIARY_CODEC_PRESENT 0x0004 | 151 | #define SIS_TERTIARY_CODEC_PRESENT 0x0004 |
@@ -1078,6 +1084,7 @@ static int sis_chip_init(struct sis7019 *sis) | |||
1078 | { | 1084 | { |
1079 | unsigned long io = sis->ioport; | 1085 | unsigned long io = sis->ioport; |
1080 | void __iomem *ioaddr = sis->ioaddr; | 1086 | void __iomem *ioaddr = sis->ioaddr; |
1087 | unsigned long timeout; | ||
1081 | u16 status; | 1088 | u16 status; |
1082 | int count; | 1089 | int count; |
1083 | int i; | 1090 | int i; |
@@ -1104,21 +1111,45 @@ static int sis_chip_init(struct sis7019 *sis) | |||
1104 | while ((inw(io + SIS_AC97_STATUS) & SIS_AC97_STATUS_BUSY) && --count) | 1111 | while ((inw(io + SIS_AC97_STATUS) & SIS_AC97_STATUS_BUSY) && --count) |
1105 | udelay(1); | 1112 | udelay(1); |
1106 | 1113 | ||
1114 | /* Command complete, we can let go of the semaphore now. | ||
1115 | */ | ||
1116 | outl(SIS_AC97_SEMA_RELEASE, io + SIS_AC97_SEMA); | ||
1117 | if (!count) | ||
1118 | return -EIO; | ||
1119 | |||
1107 | /* Now that we've finished the reset, find out what's attached. | 1120 | /* Now that we've finished the reset, find out what's attached. |
1121 | * There are some codec/board combinations that take an extremely | ||
1122 | * long time to come up. 350+ ms has been observed in the field, | ||
1123 | * so we'll give them up to 500ms. | ||
1108 | */ | 1124 | */ |
1109 | status = inl(io + SIS_AC97_STATUS); | 1125 | sis->codecs_present = 0; |
1110 | if (status & SIS_AC97_STATUS_CODEC_READY) | 1126 | timeout = msecs_to_jiffies(500) + jiffies; |
1111 | sis->codecs_present |= SIS_PRIMARY_CODEC_PRESENT; | 1127 | while (time_before_eq(jiffies, timeout)) { |
1112 | if (status & SIS_AC97_STATUS_CODEC2_READY) | 1128 | status = inl(io + SIS_AC97_STATUS); |
1113 | sis->codecs_present |= SIS_SECONDARY_CODEC_PRESENT; | 1129 | if (status & SIS_AC97_STATUS_CODEC_READY) |
1114 | if (status & SIS_AC97_STATUS_CODEC3_READY) | 1130 | sis->codecs_present |= SIS_PRIMARY_CODEC_PRESENT; |
1115 | sis->codecs_present |= SIS_TERTIARY_CODEC_PRESENT; | 1131 | if (status & SIS_AC97_STATUS_CODEC2_READY) |
1116 | 1132 | sis->codecs_present |= SIS_SECONDARY_CODEC_PRESENT; | |
1117 | /* All done, let go of the semaphore, and check for errors | 1133 | if (status & SIS_AC97_STATUS_CODEC3_READY) |
1134 | sis->codecs_present |= SIS_TERTIARY_CODEC_PRESENT; | ||
1135 | |||
1136 | if (sis->codecs_present == codecs) | ||
1137 | break; | ||
1138 | |||
1139 | msleep(1); | ||
1140 | } | ||
1141 | |||
1142 | /* All done, check for errors. | ||
1118 | */ | 1143 | */ |
1119 | outl(SIS_AC97_SEMA_RELEASE, io + SIS_AC97_SEMA); | 1144 | if (!sis->codecs_present) { |
1120 | if (!sis->codecs_present || !count) | 1145 | printk(KERN_ERR "sis7019: could not find any codecs\n"); |
1121 | return -EIO; | 1146 | return -EIO; |
1147 | } | ||
1148 | |||
1149 | if (sis->codecs_present != codecs) { | ||
1150 | printk(KERN_WARNING "sis7019: missing codecs, found %0x, expected %0x\n", | ||
1151 | sis->codecs_present, codecs); | ||
1152 | } | ||
1122 | 1153 | ||
1123 | /* Let the hardware know that the audio driver is alive, | 1154 | /* Let the hardware know that the audio driver is alive, |
1124 | * and enable PCM slots on the AC-link for L/R playback (3 & 4) and | 1155 | * and enable PCM slots on the AC-link for L/R playback (3 & 4) and |
@@ -1390,6 +1421,17 @@ static int __devinit snd_sis7019_probe(struct pci_dev *pci, | |||
1390 | if (!enable) | 1421 | if (!enable) |
1391 | goto error_out; | 1422 | goto error_out; |
1392 | 1423 | ||
1424 | /* The user can specify which codecs should be present so that we | ||
1425 | * can wait for them to show up if they are slow to recover from | ||
1426 | * the AC97 cold reset. We default to a single codec, the primary. | ||
1427 | * | ||
1428 | * We assume that SIS_PRIMARY_*_PRESENT matches bits 0-2. | ||
1429 | */ | ||
1430 | codecs &= SIS_PRIMARY_CODEC_PRESENT | SIS_SECONDARY_CODEC_PRESENT | | ||
1431 | SIS_TERTIARY_CODEC_PRESENT; | ||
1432 | if (!codecs) | ||
1433 | codecs = SIS_PRIMARY_CODEC_PRESENT; | ||
1434 | |||
1393 | rc = snd_card_create(index, id, THIS_MODULE, sizeof(*sis), &card); | 1435 | rc = snd_card_create(index, id, THIS_MODULE, sizeof(*sis), &card); |
1394 | if (rc < 0) | 1436 | if (rc < 0) |
1395 | goto error_out; | 1437 | goto error_out; |