aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2009-06-30 09:28:30 -0400
committerTakashi Iwai <tiwai@suse.de>2009-06-30 10:10:34 -0400
commit4953550a6ca399b644ef057626617465d8be9a7b (patch)
treec578a24960ec21aca31c73374d3c8f890e85400a
parentb9791ca013cfe344052455e9c8336e39d133c654 (diff)
ALSA: hda - Merge patch_alc882() and patch_alc883()
Merge patch_alc882() and patch_alc883() to the former one since both codecs have fairly similar connections but just a slight difference. Signed-off-by: Takashi Iwai <tiwai@suse.de>
-rw-r--r--Documentation/sound/alsa/HD-Audio-Models.txt12
-rw-r--r--sound/pci/hda/patch_realtek.c1829
2 files changed, 691 insertions, 1150 deletions
diff --git a/Documentation/sound/alsa/HD-Audio-Models.txt b/Documentation/sound/alsa/HD-Audio-Models.txt
index 939a3dd58148..a1895d7f3cf7 100644
--- a/Documentation/sound/alsa/HD-Audio-Models.txt
+++ b/Documentation/sound/alsa/HD-Audio-Models.txt
@@ -114,8 +114,8 @@ ALC662/663/272
114 samsung-nc10 Samsung NC10 mini notebook 114 samsung-nc10 Samsung NC10 mini notebook
115 auto auto-config reading BIOS (default) 115 auto auto-config reading BIOS (default)
116 116
117ALC882/885 117ALC882/883/885/888/889
118========== 118======================
119 3stack-dig 3-jack with SPDIF I/O 119 3stack-dig 3-jack with SPDIF I/O
120 6stack-dig 6-jack digital with SPDIF I/O 120 6stack-dig 6-jack digital with SPDIF I/O
121 arima Arima W820Di1 121 arima Arima W820Di1
@@ -127,12 +127,8 @@ ALC882/885
127 mbp3 Macbook Pro rev3 127 mbp3 Macbook Pro rev3
128 imac24 iMac 24'' with jack detection 128 imac24 iMac 24'' with jack detection
129 w2jc ASUS W2JC 129 w2jc ASUS W2JC
130 auto auto-config reading BIOS (default) 130 3stack-2ch-dig 3-jack with SPDIF I/O (ALC883)
131 131 alc883-6stack-dig 6-jack digital with SPDIF I/O (ALC883)
132ALC883/888
133==========
134 3stack-dig 3-jack with SPDIF I/O
135 6stack-dig 6-jack digital with SPDIF I/O
136 3stack-6ch 3-jack 6-channel 132 3stack-6ch 3-jack 6-channel
137 3stack-6ch-dig 3-jack 6-channel with SPDIF I/O 133 3stack-6ch-dig 3-jack 6-channel with SPDIF I/O
138 6stack-dig-demo 6-jack digital for Intel demo board 134 6stack-dig-demo 6-jack digital for Intel demo board
diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c
index 3a8e58c483df..6a899e8fdd0c 100644
--- a/sound/pci/hda/patch_realtek.c
+++ b/sound/pci/hda/patch_realtek.c
@@ -208,12 +208,6 @@ enum {
208 ALC885_MBP3, 208 ALC885_MBP3,
209 ALC885_MB5, 209 ALC885_MB5,
210 ALC885_IMAC24, 210 ALC885_IMAC24,
211 ALC882_AUTO,
212 ALC882_MODEL_LAST,
213};
214
215/* ALC883 models */
216enum {
217 ALC883_3ST_2ch_DIG, 211 ALC883_3ST_2ch_DIG,
218 ALC883_3ST_6ch_DIG, 212 ALC883_3ST_6ch_DIG,
219 ALC883_3ST_6ch, 213 ALC883_3ST_6ch,
@@ -246,8 +240,8 @@ enum {
246 ALC889A_MB31, 240 ALC889A_MB31,
247 ALC1200_ASUS_P5Q, 241 ALC1200_ASUS_P5Q,
248 ALC883_SONY_VAIO_TT, 242 ALC883_SONY_VAIO_TT,
249 ALC883_AUTO, 243 ALC882_AUTO,
250 ALC883_MODEL_LAST, 244 ALC882_MODEL_LAST,
251}; 245};
252 246
253/* for GPIO Poll */ 247/* for GPIO Poll */
@@ -320,6 +314,8 @@ struct alc_spec {
320 struct snd_array kctls; 314 struct snd_array kctls;
321 struct hda_input_mux private_imux[3]; 315 struct hda_input_mux private_imux[3];
322 hda_nid_t private_dac_nids[AUTO_CFG_MAX_OUTS]; 316 hda_nid_t private_dac_nids[AUTO_CFG_MAX_OUTS];
317 hda_nid_t private_adc_nids[AUTO_CFG_MAX_OUTS];
318 hda_nid_t private_capsrc_nids[AUTO_CFG_MAX_OUTS];
323 319
324 /* hooks */ 320 /* hooks */
325 void (*init_hook)(struct hda_codec *codec); 321 void (*init_hook)(struct hda_codec *codec);
@@ -6295,7 +6291,7 @@ static int patch_alc260(struct hda_codec *codec)
6295 6291
6296 6292
6297/* 6293/*
6298 * ALC882 support 6294 * ALC882/883/885/888/889 support
6299 * 6295 *
6300 * ALC882 is almost identical with ALC880 but has cleaner and more flexible 6296 * ALC882 is almost identical with ALC880 but has cleaner and more flexible
6301 * configuration. Each pin widget can choose any input DACs and a mixer. 6297 * configuration. Each pin widget can choose any input DACs and a mixer.
@@ -6307,22 +6303,35 @@ static int patch_alc260(struct hda_codec *codec)
6307 */ 6303 */
6308#define ALC882_DIGOUT_NID 0x06 6304#define ALC882_DIGOUT_NID 0x06
6309#define ALC882_DIGIN_NID 0x0a 6305#define ALC882_DIGIN_NID 0x0a
6306#define ALC883_DIGOUT_NID ALC882_DIGOUT_NID
6307#define ALC883_DIGIN_NID ALC882_DIGIN_NID
6308#define ALC1200_DIGOUT_NID 0x10
6309
6310 6310
6311static struct hda_channel_mode alc882_ch_modes[1] = { 6311static struct hda_channel_mode alc882_ch_modes[1] = {
6312 { 8, NULL } 6312 { 8, NULL }
6313}; 6313};
6314 6314
6315/* DACs */
6315static hda_nid_t alc882_dac_nids[4] = { 6316static hda_nid_t alc882_dac_nids[4] = {
6316 /* front, rear, clfe, rear_surr */ 6317 /* front, rear, clfe, rear_surr */
6317 0x02, 0x03, 0x04, 0x05 6318 0x02, 0x03, 0x04, 0x05
6318}; 6319};
6320#define alc883_dac_nids alc882_dac_nids
6319 6321
6320/* identical with ALC880 */ 6322/* ADCs */
6321#define alc882_adc_nids alc880_adc_nids 6323#define alc882_adc_nids alc880_adc_nids
6322#define alc882_adc_nids_alt alc880_adc_nids_alt 6324#define alc882_adc_nids_alt alc880_adc_nids_alt
6325#define alc883_adc_nids alc882_adc_nids_alt
6326static hda_nid_t alc883_adc_nids_alt[1] = { 0x08 };
6327static hda_nid_t alc883_adc_nids_rev[2] = { 0x09, 0x08 };
6328#define alc889_adc_nids alc880_adc_nids
6323 6329
6324static hda_nid_t alc882_capsrc_nids[3] = { 0x24, 0x23, 0x22 }; 6330static hda_nid_t alc882_capsrc_nids[3] = { 0x24, 0x23, 0x22 };
6325static hda_nid_t alc882_capsrc_nids_alt[2] = { 0x23, 0x22 }; 6331static hda_nid_t alc882_capsrc_nids_alt[2] = { 0x23, 0x22 };
6332#define alc883_capsrc_nids alc882_capsrc_nids_alt
6333static hda_nid_t alc883_capsrc_nids_rev[2] = { 0x22, 0x23 };
6334#define alc889_capsrc_nids alc882_capsrc_nids
6326 6335
6327/* input MUX */ 6336/* input MUX */
6328/* FIXME: should be a matrix-type input source selection */ 6337/* FIXME: should be a matrix-type input source selection */
@@ -6337,6 +6346,8 @@ static struct hda_input_mux alc882_capture_source = {
6337 }, 6346 },
6338}; 6347};
6339 6348
6349#define alc883_capture_source alc882_capture_source
6350
6340static struct hda_input_mux mb5_capture_source = { 6351static struct hda_input_mux mb5_capture_source = {
6341 .num_items = 3, 6352 .num_items = 3,
6342 .items = { 6353 .items = {
@@ -6346,6 +6357,77 @@ static struct hda_input_mux mb5_capture_source = {
6346 }, 6357 },
6347}; 6358};
6348 6359
6360static struct hda_input_mux alc883_3stack_6ch_intel = {
6361 .num_items = 4,
6362 .items = {
6363 { "Mic", 0x1 },
6364 { "Front Mic", 0x0 },
6365 { "Line", 0x2 },
6366 { "CD", 0x4 },
6367 },
6368};
6369
6370static struct hda_input_mux alc883_lenovo_101e_capture_source = {
6371 .num_items = 2,
6372 .items = {
6373 { "Mic", 0x1 },
6374 { "Line", 0x2 },
6375 },
6376};
6377
6378static struct hda_input_mux alc883_lenovo_nb0763_capture_source = {
6379 .num_items = 4,
6380 .items = {
6381 { "Mic", 0x0 },
6382 { "iMic", 0x1 },
6383 { "Line", 0x2 },
6384 { "CD", 0x4 },
6385 },
6386};
6387
6388static struct hda_input_mux alc883_fujitsu_pi2515_capture_source = {
6389 .num_items = 2,
6390 .items = {
6391 { "Mic", 0x0 },
6392 { "Int Mic", 0x1 },
6393 },
6394};
6395
6396static struct hda_input_mux alc883_lenovo_sky_capture_source = {
6397 .num_items = 3,
6398 .items = {
6399 { "Mic", 0x0 },
6400 { "Front Mic", 0x1 },
6401 { "Line", 0x4 },
6402 },
6403};
6404
6405static struct hda_input_mux alc883_asus_eee1601_capture_source = {
6406 .num_items = 2,
6407 .items = {
6408 { "Mic", 0x0 },
6409 { "Line", 0x2 },
6410 },
6411};
6412
6413static struct hda_input_mux alc889A_mb31_capture_source = {
6414 .num_items = 2,
6415 .items = {
6416 { "Mic", 0x0 },
6417 /* Front Mic (0x01) unused */
6418 { "Line", 0x2 },
6419 /* Line 2 (0x03) unused */
6420 /* CD (0x04) unsused? */
6421 },
6422};
6423
6424/*
6425 * 2ch mode
6426 */
6427static struct hda_channel_mode alc883_3ST_2ch_modes[1] = {
6428 { 2, NULL }
6429};
6430
6349/* 6431/*
6350 * 2ch mode 6432 * 2ch mode
6351 */ 6433 */
@@ -6358,6 +6440,18 @@ static struct hda_verb alc882_3ST_ch2_init[] = {
6358}; 6440};
6359 6441
6360/* 6442/*
6443 * 4ch mode
6444 */
6445static struct hda_verb alc882_3ST_ch4_init[] = {
6446 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
6447 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6448 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6449 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6450 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6451 { } /* end */
6452};
6453
6454/*
6361 * 6ch mode 6455 * 6ch mode
6362 */ 6456 */
6363static struct hda_verb alc882_3ST_ch6_init[] = { 6457static struct hda_verb alc882_3ST_ch6_init[] = {
@@ -6370,11 +6464,14 @@ static struct hda_verb alc882_3ST_ch6_init[] = {
6370 { } /* end */ 6464 { } /* end */
6371}; 6465};
6372 6466
6373static struct hda_channel_mode alc882_3ST_6ch_modes[2] = { 6467static struct hda_channel_mode alc882_3ST_6ch_modes[3] = {
6374 { 2, alc882_3ST_ch2_init }, 6468 { 2, alc882_3ST_ch2_init },
6469 { 4, alc882_3ST_ch4_init },
6375 { 6, alc882_3ST_ch6_init }, 6470 { 6, alc882_3ST_ch6_init },
6376}; 6471};
6377 6472
6473#define alc883_3ST_6ch_modes alc882_3ST_6ch_modes
6474
6378/* 6475/*
6379 * 6ch mode 6476 * 6ch mode
6380 */ 6477 */
@@ -6462,6 +6559,143 @@ static struct hda_channel_mode alc885_mb5_6ch_modes[2] = {
6462 { 6, alc885_mb5_ch6_init }, 6559 { 6, alc885_mb5_ch6_init },
6463}; 6560};
6464 6561
6562
6563/*
6564 * 2ch mode
6565 */
6566static struct hda_verb alc883_4ST_ch2_init[] = {
6567 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6568 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6569 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
6570 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6571 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
6572 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6573 { } /* end */
6574};
6575
6576/*
6577 * 4ch mode
6578 */
6579static struct hda_verb alc883_4ST_ch4_init[] = {
6580 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6581 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6582 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
6583 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6584 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6585 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6586 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6587 { } /* end */
6588};
6589
6590/*
6591 * 6ch mode
6592 */
6593static struct hda_verb alc883_4ST_ch6_init[] = {
6594 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6595 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6596 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6597 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6598 { 0x18, AC_VERB_SET_CONNECT_SEL, 0x02 },
6599 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6600 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6601 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6602 { } /* end */
6603};
6604
6605/*
6606 * 8ch mode
6607 */
6608static struct hda_verb alc883_4ST_ch8_init[] = {
6609 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6610 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6611 { 0x17, AC_VERB_SET_CONNECT_SEL, 0x03 },
6612 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6613 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6614 { 0x18, AC_VERB_SET_CONNECT_SEL, 0x02 },
6615 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6616 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6617 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6618 { } /* end */
6619};
6620
6621static struct hda_channel_mode alc883_4ST_8ch_modes[4] = {
6622 { 2, alc883_4ST_ch2_init },
6623 { 4, alc883_4ST_ch4_init },
6624 { 6, alc883_4ST_ch6_init },
6625 { 8, alc883_4ST_ch8_init },
6626};
6627
6628
6629/*
6630 * 2ch mode
6631 */
6632static struct hda_verb alc883_3ST_ch2_intel_init[] = {
6633 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
6634 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6635 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
6636 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6637 { } /* end */
6638};
6639
6640/*
6641 * 4ch mode
6642 */
6643static struct hda_verb alc883_3ST_ch4_intel_init[] = {
6644 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
6645 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
6646 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6647 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6648 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6649 { } /* end */
6650};
6651
6652/*
6653 * 6ch mode
6654 */
6655static struct hda_verb alc883_3ST_ch6_intel_init[] = {
6656 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6657 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6658 { 0x19, AC_VERB_SET_CONNECT_SEL, 0x02 },
6659 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6660 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
6661 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
6662 { } /* end */
6663};
6664
6665static struct hda_channel_mode alc883_3ST_6ch_intel_modes[3] = {
6666 { 2, alc883_3ST_ch2_intel_init },
6667 { 4, alc883_3ST_ch4_intel_init },
6668 { 6, alc883_3ST_ch6_intel_init },
6669};
6670
6671/*
6672 * 6ch mode
6673 */
6674static struct hda_verb alc883_sixstack_ch6_init[] = {
6675 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
6676 { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6677 { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6678 { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6679 { } /* end */
6680};
6681
6682/*
6683 * 8ch mode
6684 */
6685static struct hda_verb alc883_sixstack_ch8_init[] = {
6686 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6687 { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6688 { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6689 { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
6690 { } /* end */
6691};
6692
6693static struct hda_channel_mode alc883_sixstack_modes[2] = {
6694 { 6, alc883_sixstack_ch6_init },
6695 { 8, alc883_sixstack_ch8_init },
6696};
6697
6698
6465/* Pin assignment: Front=0x14, Rear=0x15, CLFE=0x16, Side=0x17 6699/* Pin assignment: Front=0x14, Rear=0x15, CLFE=0x16, Side=0x17
6466 * Mic=0x18, Front Mic=0x19, Line-In=0x1a, HP=0x1b 6700 * Mic=0x18, Front Mic=0x19, Line-In=0x1a, HP=0x1b
6467 */ 6701 */
@@ -6597,7 +6831,7 @@ static struct snd_kcontrol_new alc882_chmode_mixer[] = {
6597 { } /* end */ 6831 { } /* end */
6598}; 6832};
6599 6833
6600static struct hda_verb alc882_init_verbs[] = { 6834static struct hda_verb alc882_base_init_verbs[] = {
6601 /* Front mixer: unmute input/output amp left and right (volume = 0) */ 6835 /* Front mixer: unmute input/output amp left and right (volume = 0) */
6602 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, 6836 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
6603 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, 6837 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
@@ -6649,11 +6883,6 @@ static struct hda_verb alc882_init_verbs[] = {
6649 6883
6650 /* FIXME: use matrix-type input source selection */ 6884 /* FIXME: use matrix-type input source selection */
6651 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */ 6885 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
6652 /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
6653 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
6654 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
6655 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
6656 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
6657 /* Input mixer2 */ 6886 /* Input mixer2 */
6658 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, 6887 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
6659 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, 6888 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
@@ -6664,9 +6893,6 @@ static struct hda_verb alc882_init_verbs[] = {
6664 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, 6893 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
6665 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, 6894 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
6666 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, 6895 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
6667 /* ADC1: mute amp left and right */
6668 {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
6669 {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
6670 /* ADC2: mute amp left and right */ 6896 /* ADC2: mute amp left and right */
6671 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, 6897 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
6672 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00}, 6898 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
@@ -6677,6 +6903,21 @@ static struct hda_verb alc882_init_verbs[] = {
6677 { } 6903 { }
6678}; 6904};
6679 6905
6906static struct hda_verb alc882_adc1_init_verbs[] = {
6907 /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
6908 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
6909 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
6910 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
6911 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
6912 /* ADC1: mute amp left and right */
6913 {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
6914 {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
6915 { }
6916};
6917
6918/* HACK - expand to two elements */
6919#define alc882_init_verbs alc882_base_init_verbs, alc882_adc1_init_verbs
6920
6680static struct hda_verb alc882_eapd_verbs[] = { 6921static struct hda_verb alc882_eapd_verbs[] = {
6681 /* change to EAPD mode */ 6922 /* change to EAPD mode */
6682 {0x20, AC_VERB_SET_COEF_INDEX, 0x07}, 6923 {0x20, AC_VERB_SET_COEF_INDEX, 0x07},
@@ -6684,6 +6925,8 @@ static struct hda_verb alc882_eapd_verbs[] = {
6684 { } 6925 { }
6685}; 6926};
6686 6927
6928#define alc883_init_verbs alc882_base_init_verbs
6929
6687/* Mac Pro test */ 6930/* Mac Pro test */
6688static struct snd_kcontrol_new alc882_macpro_mixer[] = { 6931static struct snd_kcontrol_new alc882_macpro_mixer[] = {
6689 HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), 6932 HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
@@ -7034,12 +7277,10 @@ static void alc885_imac24_init_hook(struct hda_codec *codec)
7034/* 7277/*
7035 * generic initialization of ADC, input mixers and output mixers 7278 * generic initialization of ADC, input mixers and output mixers
7036 */ 7279 */
7037static struct hda_verb alc882_auto_init_verbs[] = { 7280static struct hda_verb alc883_auto_init_verbs[] = {
7038 /* 7281 /*
7039 * Unmute ADC0-2 and set the default input to mic-in 7282 * Unmute ADC0-2 and set the default input to mic-in
7040 */ 7283 */
7041 {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
7042 {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
7043 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00}, 7284 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
7044 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, 7285 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
7045 {0x09, AC_VERB_SET_CONNECT_SEL, 0x00}, 7286 {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
@@ -7080,11 +7321,6 @@ static struct hda_verb alc882_auto_init_verbs[] = {
7080 7321
7081 /* FIXME: use matrix-type input source selection */ 7322 /* FIXME: use matrix-type input source selection */
7082 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */ 7323 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
7083 /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
7084 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
7085 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
7086 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
7087 {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
7088 /* Input mixer2 */ 7324 /* Input mixer2 */
7089 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))}, 7325 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
7090 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))}, 7326 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
@@ -7099,819 +7335,6 @@ static struct hda_verb alc882_auto_init_verbs[] = {
7099 { } 7335 { }
7100}; 7336};
7101 7337
7102#ifdef CONFIG_SND_HDA_POWER_SAVE
7103#define alc882_loopbacks alc880_loopbacks
7104#endif
7105
7106/* pcm configuration: identical with ALC880 */
7107#define alc882_pcm_analog_playback alc880_pcm_analog_playback
7108#define alc882_pcm_analog_capture alc880_pcm_analog_capture
7109#define alc882_pcm_digital_playback alc880_pcm_digital_playback
7110#define alc882_pcm_digital_capture alc880_pcm_digital_capture
7111
7112/*
7113 * configuration and preset
7114 */
7115static const char *alc882_models[ALC882_MODEL_LAST] = {
7116 [ALC882_3ST_DIG] = "3stack-dig",
7117 [ALC882_6ST_DIG] = "6stack-dig",
7118 [ALC882_ARIMA] = "arima",
7119 [ALC882_W2JC] = "w2jc",
7120 [ALC882_TARGA] = "targa",
7121 [ALC882_ASUS_A7J] = "asus-a7j",
7122 [ALC882_ASUS_A7M] = "asus-a7m",
7123 [ALC885_MACPRO] = "macpro",
7124 [ALC885_MB5] = "mb5",
7125 [ALC885_MBP3] = "mbp3",
7126 [ALC885_IMAC24] = "imac24",
7127 [ALC882_AUTO] = "auto",
7128};
7129
7130static struct snd_pci_quirk alc882_cfg_tbl[] = {
7131 SND_PCI_QUIRK(0x1019, 0x6668, "ECS", ALC882_6ST_DIG),
7132 SND_PCI_QUIRK(0x1043, 0x060d, "Asus A7J", ALC882_ASUS_A7J),
7133 SND_PCI_QUIRK(0x1043, 0x1243, "Asus A7J", ALC882_ASUS_A7J),
7134 SND_PCI_QUIRK(0x1043, 0x13c2, "Asus A7M", ALC882_ASUS_A7M),
7135 SND_PCI_QUIRK(0x1043, 0x1971, "Asus W2JC", ALC882_W2JC),
7136 SND_PCI_QUIRK(0x1043, 0x817f, "Asus P5LD2", ALC882_6ST_DIG),
7137 SND_PCI_QUIRK(0x1043, 0x81d8, "Asus P5WD", ALC882_6ST_DIG),
7138 SND_PCI_QUIRK(0x105b, 0x6668, "Foxconn", ALC882_6ST_DIG),
7139 SND_PCI_QUIRK(0x1458, 0xa002, "Gigabyte P35 DS3R", ALC882_6ST_DIG),
7140 SND_PCI_QUIRK(0x1462, 0x28fb, "Targa T8", ALC882_TARGA), /* MSI-1049 T8 */
7141 SND_PCI_QUIRK(0x1462, 0x6668, "MSI", ALC882_6ST_DIG),
7142 SND_PCI_QUIRK(0x161f, 0x2054, "Arima W820", ALC882_ARIMA),
7143 {}
7144};
7145
7146static struct alc_config_preset alc882_presets[] = {
7147 [ALC882_3ST_DIG] = {
7148 .mixers = { alc882_base_mixer },
7149 .init_verbs = { alc882_init_verbs },
7150 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7151 .dac_nids = alc882_dac_nids,
7152 .dig_out_nid = ALC882_DIGOUT_NID,
7153 .dig_in_nid = ALC882_DIGIN_NID,
7154 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
7155 .channel_mode = alc882_ch_modes,
7156 .need_dac_fix = 1,
7157 .input_mux = &alc882_capture_source,
7158 },
7159 [ALC882_6ST_DIG] = {
7160 .mixers = { alc882_base_mixer, alc882_chmode_mixer },
7161 .init_verbs = { alc882_init_verbs },
7162 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7163 .dac_nids = alc882_dac_nids,
7164 .dig_out_nid = ALC882_DIGOUT_NID,
7165 .dig_in_nid = ALC882_DIGIN_NID,
7166 .num_channel_mode = ARRAY_SIZE(alc882_sixstack_modes),
7167 .channel_mode = alc882_sixstack_modes,
7168 .input_mux = &alc882_capture_source,
7169 },
7170 [ALC882_ARIMA] = {
7171 .mixers = { alc882_base_mixer, alc882_chmode_mixer },
7172 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs },
7173 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7174 .dac_nids = alc882_dac_nids,
7175 .num_channel_mode = ARRAY_SIZE(alc882_sixstack_modes),
7176 .channel_mode = alc882_sixstack_modes,
7177 .input_mux = &alc882_capture_source,
7178 },
7179 [ALC882_W2JC] = {
7180 .mixers = { alc882_w2jc_mixer, alc882_chmode_mixer },
7181 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs,
7182 alc880_gpio1_init_verbs },
7183 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7184 .dac_nids = alc882_dac_nids,
7185 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
7186 .channel_mode = alc880_threestack_modes,
7187 .need_dac_fix = 1,
7188 .input_mux = &alc882_capture_source,
7189 .dig_out_nid = ALC882_DIGOUT_NID,
7190 },
7191 [ALC885_MBP3] = {
7192 .mixers = { alc885_mbp3_mixer, alc882_chmode_mixer },
7193 .init_verbs = { alc885_mbp3_init_verbs,
7194 alc880_gpio1_init_verbs },
7195 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7196 .dac_nids = alc882_dac_nids,
7197 .channel_mode = alc885_mbp_6ch_modes,
7198 .num_channel_mode = ARRAY_SIZE(alc885_mbp_6ch_modes),
7199 .input_mux = &alc882_capture_source,
7200 .dig_out_nid = ALC882_DIGOUT_NID,
7201 .dig_in_nid = ALC882_DIGIN_NID,
7202 .unsol_event = alc_automute_amp_unsol_event,
7203 .init_hook = alc885_mbp3_init_hook,
7204 },
7205 [ALC885_MB5] = {
7206 .mixers = { alc885_mb5_mixer, alc882_chmode_mixer },
7207 .init_verbs = { alc885_mb5_init_verbs,
7208 alc880_gpio1_init_verbs },
7209 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7210 .dac_nids = alc882_dac_nids,
7211 .channel_mode = alc885_mb5_6ch_modes,
7212 .num_channel_mode = ARRAY_SIZE(alc885_mb5_6ch_modes),
7213 .input_mux = &mb5_capture_source,
7214 .dig_out_nid = ALC882_DIGOUT_NID,
7215 .dig_in_nid = ALC882_DIGIN_NID,
7216 },
7217 [ALC885_MACPRO] = {
7218 .mixers = { alc882_macpro_mixer },
7219 .init_verbs = { alc882_macpro_init_verbs },
7220 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7221 .dac_nids = alc882_dac_nids,
7222 .dig_out_nid = ALC882_DIGOUT_NID,
7223 .dig_in_nid = ALC882_DIGIN_NID,
7224 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
7225 .channel_mode = alc882_ch_modes,
7226 .input_mux = &alc882_capture_source,
7227 .init_hook = alc885_macpro_init_hook,
7228 },
7229 [ALC885_IMAC24] = {
7230 .mixers = { alc885_imac24_mixer },
7231 .init_verbs = { alc885_imac24_init_verbs },
7232 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7233 .dac_nids = alc882_dac_nids,
7234 .dig_out_nid = ALC882_DIGOUT_NID,
7235 .dig_in_nid = ALC882_DIGIN_NID,
7236 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
7237 .channel_mode = alc882_ch_modes,
7238 .input_mux = &alc882_capture_source,
7239 .unsol_event = alc_automute_amp_unsol_event,
7240 .init_hook = alc885_imac24_init_hook,
7241 },
7242 [ALC882_TARGA] = {
7243 .mixers = { alc882_targa_mixer, alc882_chmode_mixer },
7244 .init_verbs = { alc882_init_verbs, alc882_targa_verbs},
7245 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7246 .dac_nids = alc882_dac_nids,
7247 .dig_out_nid = ALC882_DIGOUT_NID,
7248 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
7249 .adc_nids = alc882_adc_nids,
7250 .capsrc_nids = alc882_capsrc_nids,
7251 .num_channel_mode = ARRAY_SIZE(alc882_3ST_6ch_modes),
7252 .channel_mode = alc882_3ST_6ch_modes,
7253 .need_dac_fix = 1,
7254 .input_mux = &alc882_capture_source,
7255 .unsol_event = alc882_targa_unsol_event,
7256 .init_hook = alc882_targa_init_hook,
7257 },
7258 [ALC882_ASUS_A7J] = {
7259 .mixers = { alc882_asus_a7j_mixer, alc882_chmode_mixer },
7260 .init_verbs = { alc882_init_verbs, alc882_asus_a7j_verbs},
7261 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7262 .dac_nids = alc882_dac_nids,
7263 .dig_out_nid = ALC882_DIGOUT_NID,
7264 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
7265 .adc_nids = alc882_adc_nids,
7266 .capsrc_nids = alc882_capsrc_nids,
7267 .num_channel_mode = ARRAY_SIZE(alc882_3ST_6ch_modes),
7268 .channel_mode = alc882_3ST_6ch_modes,
7269 .need_dac_fix = 1,
7270 .input_mux = &alc882_capture_source,
7271 },
7272 [ALC882_ASUS_A7M] = {
7273 .mixers = { alc882_asus_a7m_mixer, alc882_chmode_mixer },
7274 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs,
7275 alc880_gpio1_init_verbs,
7276 alc882_asus_a7m_verbs },
7277 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
7278 .dac_nids = alc882_dac_nids,
7279 .dig_out_nid = ALC882_DIGOUT_NID,
7280 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
7281 .channel_mode = alc880_threestack_modes,
7282 .need_dac_fix = 1,
7283 .input_mux = &alc882_capture_source,
7284 },
7285};
7286
7287
7288/*
7289 * Pin config fixes
7290 */
7291enum {
7292 PINFIX_ABIT_AW9D_MAX
7293};
7294
7295static struct alc_pincfg alc882_abit_aw9d_pinfix[] = {
7296 { 0x15, 0x01080104 }, /* side */
7297 { 0x16, 0x01011012 }, /* rear */
7298 { 0x17, 0x01016011 }, /* clfe */
7299 { }
7300};
7301
7302static const struct alc_pincfg *alc882_pin_fixes[] = {
7303 [PINFIX_ABIT_AW9D_MAX] = alc882_abit_aw9d_pinfix,
7304};
7305
7306static struct snd_pci_quirk alc882_pinfix_tbl[] = {
7307 SND_PCI_QUIRK(0x147b, 0x107a, "Abit AW9D-MAX", PINFIX_ABIT_AW9D_MAX),
7308 {}
7309};
7310
7311/*
7312 * BIOS auto configuration
7313 */
7314static void alc882_auto_set_output_and_unmute(struct hda_codec *codec,
7315 hda_nid_t nid, int pin_type,
7316 int dac_idx)
7317{
7318 /* set as output */
7319 struct alc_spec *spec = codec->spec;
7320 int idx;
7321
7322 alc_set_pin_output(codec, nid, pin_type);
7323 if (spec->multiout.dac_nids[dac_idx] == 0x25)
7324 idx = 4;
7325 else
7326 idx = spec->multiout.dac_nids[dac_idx] - 2;
7327 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_CONNECT_SEL, idx);
7328
7329}
7330
7331static void alc882_auto_init_multi_out(struct hda_codec *codec)
7332{
7333 struct alc_spec *spec = codec->spec;
7334 int i;
7335
7336 for (i = 0; i <= HDA_SIDE; i++) {
7337 hda_nid_t nid = spec->autocfg.line_out_pins[i];
7338 int pin_type = get_pin_type(spec->autocfg.line_out_type);
7339 if (nid)
7340 alc882_auto_set_output_and_unmute(codec, nid, pin_type,
7341 i);
7342 }
7343}
7344
7345static void alc882_auto_init_hp_out(struct hda_codec *codec)
7346{
7347 struct alc_spec *spec = codec->spec;
7348 hda_nid_t pin;
7349
7350 pin = spec->autocfg.hp_pins[0];
7351 if (pin) /* connect to front */
7352 /* use dac 0 */
7353 alc882_auto_set_output_and_unmute(codec, pin, PIN_HP, 0);
7354 pin = spec->autocfg.speaker_pins[0];
7355 if (pin)
7356 alc882_auto_set_output_and_unmute(codec, pin, PIN_OUT, 0);
7357}
7358
7359#define alc882_is_input_pin(nid) alc880_is_input_pin(nid)
7360#define ALC882_PIN_CD_NID ALC880_PIN_CD_NID
7361
7362static void alc882_auto_init_analog_input(struct hda_codec *codec)
7363{
7364 struct alc_spec *spec = codec->spec;
7365 int i;
7366
7367 for (i = 0; i < AUTO_PIN_LAST; i++) {
7368 hda_nid_t nid = spec->autocfg.input_pins[i];
7369 if (!nid)
7370 continue;
7371 alc_set_input_pin(codec, nid, AUTO_PIN_FRONT_MIC /*i*/);
7372 if (get_wcaps(codec, nid) & AC_WCAP_OUT_AMP)
7373 snd_hda_codec_write(codec, nid, 0,
7374 AC_VERB_SET_AMP_GAIN_MUTE,
7375 AMP_OUT_MUTE);
7376 }
7377}
7378
7379static void alc882_auto_init_input_src(struct hda_codec *codec)
7380{
7381 struct alc_spec *spec = codec->spec;
7382 int c;
7383
7384 for (c = 0; c < spec->num_adc_nids; c++) {
7385 hda_nid_t conn_list[HDA_MAX_NUM_INPUTS];
7386 hda_nid_t nid = spec->capsrc_nids[c];
7387 unsigned int mux_idx;
7388 const struct hda_input_mux *imux;
7389 int conns, mute, idx, item;
7390
7391 conns = snd_hda_get_connections(codec, nid, conn_list,
7392 ARRAY_SIZE(conn_list));
7393 if (conns < 0)
7394 continue;
7395 mux_idx = c >= spec->num_mux_defs ? 0 : c;
7396 imux = &spec->input_mux[mux_idx];
7397 for (idx = 0; idx < conns; idx++) {
7398 /* if the current connection is the selected one,
7399 * unmute it as default - otherwise mute it
7400 */
7401 mute = AMP_IN_MUTE(idx);
7402 for (item = 0; item < imux->num_items; item++) {
7403 if (imux->items[item].index == idx) {
7404 if (spec->cur_mux[c] == item)
7405 mute = AMP_IN_UNMUTE(idx);
7406 break;
7407 }
7408 }
7409 /* check if we have a selector or mixer
7410 * we could check for the widget type instead, but
7411 * just check for Amp-In presence (in case of mixer
7412 * without amp-in there is something wrong, this
7413 * function shouldn't be used or capsrc nid is wrong)
7414 */
7415 if (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)
7416 snd_hda_codec_write(codec, nid, 0,
7417 AC_VERB_SET_AMP_GAIN_MUTE,
7418 mute);
7419 else if (mute != AMP_IN_MUTE(idx))
7420 snd_hda_codec_write(codec, nid, 0,
7421 AC_VERB_SET_CONNECT_SEL,
7422 idx);
7423 }
7424 }
7425}
7426
7427/* add mic boosts if needed */
7428static int alc_auto_add_mic_boost(struct hda_codec *codec)
7429{
7430 struct alc_spec *spec = codec->spec;
7431 int err;
7432 hda_nid_t nid;
7433
7434 nid = spec->autocfg.input_pins[AUTO_PIN_MIC];
7435 if (nid && (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)) {
7436 err = add_control(spec, ALC_CTL_WIDGET_VOL,
7437 "Mic Boost",
7438 HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_INPUT));
7439 if (err < 0)
7440 return err;
7441 }
7442 nid = spec->autocfg.input_pins[AUTO_PIN_FRONT_MIC];
7443 if (nid && (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)) {
7444 err = add_control(spec, ALC_CTL_WIDGET_VOL,
7445 "Front Mic Boost",
7446 HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_INPUT));
7447 if (err < 0)
7448 return err;
7449 }
7450 return 0;
7451}
7452
7453/* almost identical with ALC880 parser... */
7454static int alc882_parse_auto_config(struct hda_codec *codec)
7455{
7456 struct alc_spec *spec = codec->spec;
7457 int err = alc880_parse_auto_config(codec);
7458
7459 if (err < 0)
7460 return err;
7461 else if (!err)
7462 return 0; /* no config found */
7463
7464 err = alc_auto_add_mic_boost(codec);
7465 if (err < 0)
7466 return err;
7467
7468 /* hack - override the init verbs */
7469 spec->init_verbs[0] = alc882_auto_init_verbs;
7470
7471 return 1; /* config found */
7472}
7473
7474/* additional initialization for auto-configuration model */
7475static void alc882_auto_init(struct hda_codec *codec)
7476{
7477 struct alc_spec *spec = codec->spec;
7478 alc882_auto_init_multi_out(codec);
7479 alc882_auto_init_hp_out(codec);
7480 alc882_auto_init_analog_input(codec);
7481 alc882_auto_init_input_src(codec);
7482 if (spec->unsol_event)
7483 alc_inithook(codec);
7484}
7485
7486static int patch_alc883(struct hda_codec *codec); /* called in patch_alc882() */
7487
7488static int patch_alc882(struct hda_codec *codec)
7489{
7490 struct alc_spec *spec;
7491 int err, board_config;
7492
7493 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
7494 if (spec == NULL)
7495 return -ENOMEM;
7496
7497 codec->spec = spec;
7498
7499 board_config = snd_hda_check_board_config(codec, ALC882_MODEL_LAST,
7500 alc882_models,
7501 alc882_cfg_tbl);
7502
7503 if (board_config < 0 || board_config >= ALC882_MODEL_LAST) {
7504 /* Pick up systems that don't supply PCI SSID */
7505 switch (codec->subsystem_id) {
7506 case 0x106b0c00: /* Mac Pro */
7507 board_config = ALC885_MACPRO;
7508 break;
7509 case 0x106b1000: /* iMac 24 */
7510 case 0x106b2800: /* AppleTV */
7511 case 0x106b3e00: /* iMac 24 Aluminium */
7512 board_config = ALC885_IMAC24;
7513 break;
7514 case 0x106b00a0: /* MacBookPro3,1 - Another revision */
7515 case 0x106b00a1: /* Macbook (might be wrong - PCI SSID?) */
7516 case 0x106b00a4: /* MacbookPro4,1 */
7517 case 0x106b2c00: /* Macbook Pro rev3 */
7518 /* Macbook 3.1 (0x106b3600) is handled by patch_alc883() */
7519 case 0x106b3800: /* MacbookPro4,1 - latter revision */
7520 board_config = ALC885_MBP3;
7521 break;
7522 case 0x106b3f00: /* Macbook 5,1 */
7523 case 0x106b4000: /* Macbook Pro 5,1 - FIXME: HP jack sense
7524 * seems not working, so apparently
7525 * no perfect solution yet
7526 */
7527 board_config = ALC885_MB5;
7528 break;
7529 default:
7530 /* ALC889A is handled better as ALC888-compatible */
7531 if (codec->revision_id == 0x100101 ||
7532 codec->revision_id == 0x100103) {
7533 alc_free(codec);
7534 return patch_alc883(codec);
7535 }
7536 printk(KERN_INFO "hda_codec: Unknown model for %s, "
7537 "trying auto-probe from BIOS...\n",
7538 codec->chip_name);
7539 board_config = ALC882_AUTO;
7540 }
7541 }
7542
7543 alc_fix_pincfg(codec, alc882_pinfix_tbl, alc882_pin_fixes);
7544
7545 if (board_config == ALC882_AUTO) {
7546 /* automatic parse from the BIOS config */
7547 err = alc882_parse_auto_config(codec);
7548 if (err < 0) {
7549 alc_free(codec);
7550 return err;
7551 } else if (!err) {
7552 printk(KERN_INFO
7553 "hda_codec: Cannot set up configuration "
7554 "from BIOS. Using base mode...\n");
7555 board_config = ALC882_3ST_DIG;
7556 }
7557 }
7558
7559 err = snd_hda_attach_beep_device(codec, 0x1);
7560 if (err < 0) {
7561 alc_free(codec);
7562 return err;
7563 }
7564
7565 if (board_config != ALC882_AUTO)
7566 setup_preset(spec, &alc882_presets[board_config]);
7567
7568 spec->stream_analog_playback = &alc882_pcm_analog_playback;
7569 spec->stream_analog_capture = &alc882_pcm_analog_capture;
7570 /* FIXME: setup DAC5 */
7571 /*spec->stream_analog_alt_playback = &alc880_pcm_analog_alt_playback;*/
7572 spec->stream_analog_alt_capture = &alc880_pcm_analog_alt_capture;
7573
7574 spec->stream_digital_playback = &alc882_pcm_digital_playback;
7575 spec->stream_digital_capture = &alc882_pcm_digital_capture;
7576
7577 if (!spec->adc_nids && spec->input_mux) {
7578 /* check whether NID 0x07 is valid */
7579 unsigned int wcap = get_wcaps(codec, 0x07);
7580 /* get type */
7581 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT;
7582 if (wcap != AC_WID_AUD_IN) {
7583 spec->adc_nids = alc882_adc_nids_alt;
7584 spec->num_adc_nids = ARRAY_SIZE(alc882_adc_nids_alt);
7585 spec->capsrc_nids = alc882_capsrc_nids_alt;
7586 } else {
7587 spec->adc_nids = alc882_adc_nids;
7588 spec->num_adc_nids = ARRAY_SIZE(alc882_adc_nids);
7589 spec->capsrc_nids = alc882_capsrc_nids;
7590 }
7591 }
7592 set_capture_mixer(spec);
7593 set_beep_amp(spec, 0x0b, 0x05, HDA_INPUT);
7594
7595 spec->vmaster_nid = 0x0c;
7596
7597 codec->patch_ops = alc_patch_ops;
7598 if (board_config == ALC882_AUTO)
7599 spec->init_hook = alc882_auto_init;
7600#ifdef CONFIG_SND_HDA_POWER_SAVE
7601 if (!spec->loopback.amplist)
7602 spec->loopback.amplist = alc882_loopbacks;
7603#endif
7604 codec->proc_widget_hook = print_realtek_coef;
7605
7606 return 0;
7607}
7608
7609/*
7610 * ALC883 support
7611 *
7612 * ALC883 is almost identical with ALC880 but has cleaner and more flexible
7613 * configuration. Each pin widget can choose any input DACs and a mixer.
7614 * Each ADC is connected from a mixer of all inputs. This makes possible
7615 * 6-channel independent captures.
7616 *
7617 * In addition, an independent DAC for the multi-playback (not used in this
7618 * driver yet).
7619 */
7620#define ALC883_DIGOUT_NID 0x06
7621#define ALC883_DIGIN_NID 0x0a
7622
7623#define ALC1200_DIGOUT_NID 0x10
7624
7625static hda_nid_t alc883_dac_nids[4] = {
7626 /* front, rear, clfe, rear_surr */
7627 0x02, 0x03, 0x04, 0x05
7628};
7629
7630static hda_nid_t alc883_adc_nids[2] = {
7631 /* ADC1-2 */
7632 0x08, 0x09,
7633};
7634
7635static hda_nid_t alc883_adc_nids_alt[1] = {
7636 /* ADC1 */
7637 0x08,
7638};
7639
7640static hda_nid_t alc883_adc_nids_rev[2] = {
7641 /* ADC2-1 */
7642 0x09, 0x08
7643};
7644
7645#define alc889_adc_nids alc880_adc_nids
7646
7647static hda_nid_t alc883_capsrc_nids[2] = { 0x23, 0x22 };
7648
7649static hda_nid_t alc883_capsrc_nids_rev[2] = { 0x22, 0x23 };
7650
7651#define alc889_capsrc_nids alc882_capsrc_nids
7652
7653/* input MUX */
7654/* FIXME: should be a matrix-type input source selection */
7655
7656static struct hda_input_mux alc883_capture_source = {
7657 .num_items = 4,
7658 .items = {
7659 { "Mic", 0x0 },
7660 { "Front Mic", 0x1 },
7661 { "Line", 0x2 },
7662 { "CD", 0x4 },
7663 },
7664};
7665
7666static struct hda_input_mux alc883_3stack_6ch_intel = {
7667 .num_items = 4,
7668 .items = {
7669 { "Mic", 0x1 },
7670 { "Front Mic", 0x0 },
7671 { "Line", 0x2 },
7672 { "CD", 0x4 },
7673 },
7674};
7675
7676static struct hda_input_mux alc883_lenovo_101e_capture_source = {
7677 .num_items = 2,
7678 .items = {
7679 { "Mic", 0x1 },
7680 { "Line", 0x2 },
7681 },
7682};
7683
7684static struct hda_input_mux alc883_lenovo_nb0763_capture_source = {
7685 .num_items = 4,
7686 .items = {
7687 { "Mic", 0x0 },
7688 { "iMic", 0x1 },
7689 { "Line", 0x2 },
7690 { "CD", 0x4 },
7691 },
7692};
7693
7694static struct hda_input_mux alc883_fujitsu_pi2515_capture_source = {
7695 .num_items = 2,
7696 .items = {
7697 { "Mic", 0x0 },
7698 { "Int Mic", 0x1 },
7699 },
7700};
7701
7702static struct hda_input_mux alc883_lenovo_sky_capture_source = {
7703 .num_items = 3,
7704 .items = {
7705 { "Mic", 0x0 },
7706 { "Front Mic", 0x1 },
7707 { "Line", 0x4 },
7708 },
7709};
7710
7711static struct hda_input_mux alc883_asus_eee1601_capture_source = {
7712 .num_items = 2,
7713 .items = {
7714 { "Mic", 0x0 },
7715 { "Line", 0x2 },
7716 },
7717};
7718
7719static struct hda_input_mux alc889A_mb31_capture_source = {
7720 .num_items = 2,
7721 .items = {
7722 { "Mic", 0x0 },
7723 /* Front Mic (0x01) unused */
7724 { "Line", 0x2 },
7725 /* Line 2 (0x03) unused */
7726 /* CD (0x04) unsused? */
7727 },
7728};
7729
7730/*
7731 * 2ch mode
7732 */
7733static struct hda_channel_mode alc883_3ST_2ch_modes[1] = {
7734 { 2, NULL }
7735};
7736
7737/*
7738 * 2ch mode
7739 */
7740static struct hda_verb alc883_3ST_ch2_init[] = {
7741 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7742 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7743 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
7744 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7745 { } /* end */
7746};
7747
7748/*
7749 * 4ch mode
7750 */
7751static struct hda_verb alc883_3ST_ch4_init[] = {
7752 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7753 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7754 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7755 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7756 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7757 { } /* end */
7758};
7759
7760/*
7761 * 6ch mode
7762 */
7763static struct hda_verb alc883_3ST_ch6_init[] = {
7764 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7765 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7766 { 0x18, AC_VERB_SET_CONNECT_SEL, 0x02 },
7767 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7768 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7769 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7770 { } /* end */
7771};
7772
7773static struct hda_channel_mode alc883_3ST_6ch_modes[3] = {
7774 { 2, alc883_3ST_ch2_init },
7775 { 4, alc883_3ST_ch4_init },
7776 { 6, alc883_3ST_ch6_init },
7777};
7778
7779
7780/*
7781 * 2ch mode
7782 */
7783static struct hda_verb alc883_4ST_ch2_init[] = {
7784 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7785 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7786 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7787 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7788 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
7789 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7790 { } /* end */
7791};
7792
7793/*
7794 * 4ch mode
7795 */
7796static struct hda_verb alc883_4ST_ch4_init[] = {
7797 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7798 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7799 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7800 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7801 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7802 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7803 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7804 { } /* end */
7805};
7806
7807/*
7808 * 6ch mode
7809 */
7810static struct hda_verb alc883_4ST_ch6_init[] = {
7811 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7812 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7813 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7814 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7815 { 0x18, AC_VERB_SET_CONNECT_SEL, 0x02 },
7816 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7817 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7818 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7819 { } /* end */
7820};
7821
7822/*
7823 * 8ch mode
7824 */
7825static struct hda_verb alc883_4ST_ch8_init[] = {
7826 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7827 { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7828 { 0x17, AC_VERB_SET_CONNECT_SEL, 0x03 },
7829 { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7830 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7831 { 0x18, AC_VERB_SET_CONNECT_SEL, 0x02 },
7832 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7833 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7834 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7835 { } /* end */
7836};
7837
7838static struct hda_channel_mode alc883_4ST_8ch_modes[4] = {
7839 { 2, alc883_4ST_ch2_init },
7840 { 4, alc883_4ST_ch4_init },
7841 { 6, alc883_4ST_ch6_init },
7842 { 8, alc883_4ST_ch8_init },
7843};
7844
7845
7846/*
7847 * 2ch mode
7848 */
7849static struct hda_verb alc883_3ST_ch2_intel_init[] = {
7850 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7851 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7852 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
7853 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7854 { } /* end */
7855};
7856
7857/*
7858 * 4ch mode
7859 */
7860static struct hda_verb alc883_3ST_ch4_intel_init[] = {
7861 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
7862 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
7863 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7864 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7865 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7866 { } /* end */
7867};
7868
7869/*
7870 * 6ch mode
7871 */
7872static struct hda_verb alc883_3ST_ch6_intel_init[] = {
7873 { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7874 { 0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7875 { 0x19, AC_VERB_SET_CONNECT_SEL, 0x02 },
7876 { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7877 { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
7878 { 0x1a, AC_VERB_SET_CONNECT_SEL, 0x01 },
7879 { } /* end */
7880};
7881
7882static struct hda_channel_mode alc883_3ST_6ch_intel_modes[3] = {
7883 { 2, alc883_3ST_ch2_intel_init },
7884 { 4, alc883_3ST_ch4_intel_init },
7885 { 6, alc883_3ST_ch6_intel_init },
7886};
7887
7888/*
7889 * 6ch mode
7890 */
7891static struct hda_verb alc883_sixstack_ch6_init[] = {
7892 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
7893 { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7894 { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7895 { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7896 { } /* end */
7897};
7898
7899/*
7900 * 8ch mode
7901 */
7902static struct hda_verb alc883_sixstack_ch8_init[] = {
7903 { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7904 { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7905 { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7906 { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
7907 { } /* end */
7908};
7909
7910static struct hda_channel_mode alc883_sixstack_modes[2] = {
7911 { 6, alc883_sixstack_ch6_init },
7912 { 8, alc883_sixstack_ch8_init },
7913};
7914
7915/* 2ch mode (Speaker:front, Subwoofer:CLFE, Line:input, Headphones:front) */ 7338/* 2ch mode (Speaker:front, Subwoofer:CLFE, Line:input, Headphones:front) */
7916static struct hda_verb alc889A_mb31_ch2_init[] = { 7339static struct hda_verb alc889A_mb31_ch2_init[] = {
7917 {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP as front */ 7340 {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP as front */
@@ -7962,34 +7385,7 @@ static struct hda_verb alc883_medion_eapd_verbs[] = {
7962 { } 7385 { }
7963}; 7386};
7964 7387
7965/* Pin assignment: Front=0x14, Rear=0x15, CLFE=0x16, Side=0x17 7388#define alc883_base_mixer alc882_base_mixer
7966 * Mic=0x18, Front Mic=0x19, Line-In=0x1a, HP=0x1b
7967 */
7968
7969static struct snd_kcontrol_new alc883_base_mixer[] = {
7970 HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
7971 HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
7972 HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
7973 HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
7974 HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
7975 HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
7976 HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
7977 HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
7978 HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
7979 HDA_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT),
7980 HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
7981 HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
7982 HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
7983 HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
7984 HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
7985 HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
7986 HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT),
7987 HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
7988 HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x1, HDA_INPUT),
7989 HDA_CODEC_VOLUME("Front Mic Boost", 0x19, 0, HDA_INPUT),
7990 HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x1, HDA_INPUT),
7991 { } /* end */
7992};
7993 7389
7994static struct snd_kcontrol_new alc883_mitac_mixer[] = { 7390static struct snd_kcontrol_new alc883_mitac_mixer[] = {
7995 HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), 7391 HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
@@ -8340,84 +7736,6 @@ static struct snd_kcontrol_new alc883_chmode_mixer[] = {
8340 { } /* end */ 7736 { } /* end */
8341}; 7737};
8342 7738
8343static struct hda_verb alc883_init_verbs[] = {
8344 /* ADC1: mute amp left and right */
8345 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8346 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
8347 /* ADC2: mute amp left and right */
8348 {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8349 {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
8350 /* Front mixer: unmute input/output amp left and right (volume = 0) */
8351 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8352 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8353 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8354 /* Rear mixer */
8355 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8356 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8357 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8358 /* CLFE mixer */
8359 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8360 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8361 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8362 /* Side mixer */
8363 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8364 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8365 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8366
8367 /* mute analog input loopbacks */
8368 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8369 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8370 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
8371 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
8372 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
8373
8374 /* Front Pin: output 0 (0x0c) */
8375 {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
8376 {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
8377 {0x14, AC_VERB_SET_CONNECT_SEL, 0x00},
8378 /* Rear Pin: output 1 (0x0d) */
8379 {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
8380 {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
8381 {0x15, AC_VERB_SET_CONNECT_SEL, 0x01},
8382 /* CLFE Pin: output 2 (0x0e) */
8383 {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
8384 {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
8385 {0x16, AC_VERB_SET_CONNECT_SEL, 0x02},
8386 /* Side Pin: output 3 (0x0f) */
8387 {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
8388 {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
8389 {0x17, AC_VERB_SET_CONNECT_SEL, 0x03},
8390 /* Mic (rear) pin: input vref at 80% */
8391 {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
8392 {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
8393 /* Front Mic pin: input vref at 80% */
8394 {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
8395 {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
8396 /* Line In pin: input */
8397 {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
8398 {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
8399 /* Line-2 In: Headphone output (output 0 - 0x0c) */
8400 {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
8401 {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
8402 {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00},
8403 /* CD pin widget for input */
8404 {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
8405
8406 /* FIXME: use matrix-type input source selection */
8407 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
8408 /* Input mixer2 */
8409 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8410 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8411 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
8412 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
8413 /* Input mixer3 */
8414 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8415 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8416 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
8417 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
8418 { }
8419};
8420
8421/* toggle speaker-output according to the hp-jack state */ 7739/* toggle speaker-output according to the hp-jack state */
8422static void alc883_mitac_init_hook(struct hda_codec *codec) 7740static void alc883_mitac_init_hook(struct hda_codec *codec)
8423{ 7741{
@@ -8850,69 +8168,6 @@ static void alc883_vaiott_init_hook(struct hda_codec *codec)
8850 alc_automute_amp(codec); 8168 alc_automute_amp(codec);
8851} 8169}
8852 8170
8853/*
8854 * generic initialization of ADC, input mixers and output mixers
8855 */
8856static struct hda_verb alc883_auto_init_verbs[] = {
8857 /*
8858 * Unmute ADC0-2 and set the default input to mic-in
8859 */
8860 {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
8861 {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8862 {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
8863 {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8864
8865 /* Mute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
8866 * mixer widget
8867 * Note: PASD motherboards uses the Line In 2 as the input for
8868 * front panel mic (mic 2)
8869 */
8870 /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
8871 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8872 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
8873 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
8874 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
8875 {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
8876
8877 /*
8878 * Set up output mixers (0x0c - 0x0f)
8879 */
8880 /* set vol=0 to output mixers */
8881 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8882 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8883 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8884 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
8885 /* set up input amps for analog loopback */
8886 /* Amp Indices: DAC = 0, mixer = 1 */
8887 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8888 {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8889 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8890 {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8891 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8892 {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8893 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8894 {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8895 {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8896 {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8897
8898 /* FIXME: use matrix-type input source selection */
8899 /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
8900 /* Input mixer1 */
8901 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8902 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8903 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
8904 /* {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)}, */
8905 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
8906 /* Input mixer2 */
8907 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
8908 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
8909 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
8910 /* {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)}, */
8911 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
8912
8913 { }
8914};
8915
8916static struct hda_verb alc888_asus_m90v_verbs[] = { 8171static struct hda_verb alc888_asus_m90v_verbs[] = {
8917 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, 8172 {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
8918 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, 8173 {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
@@ -9023,25 +8278,44 @@ static void alc889A_mb31_unsol_event(struct hda_codec *codec, unsigned int res)
9023 alc889A_mb31_automute(codec); 8278 alc889A_mb31_automute(codec);
9024} 8279}
9025 8280
8281
9026#ifdef CONFIG_SND_HDA_POWER_SAVE 8282#ifdef CONFIG_SND_HDA_POWER_SAVE
9027#define alc883_loopbacks alc880_loopbacks 8283#define alc882_loopbacks alc880_loopbacks
9028#endif 8284#endif
9029 8285
9030/* pcm configuration: identical with ALC880 */ 8286/* pcm configuration: identical with ALC880 */
9031#define alc883_pcm_analog_playback alc880_pcm_analog_playback 8287#define alc882_pcm_analog_playback alc880_pcm_analog_playback
9032#define alc883_pcm_analog_capture alc880_pcm_analog_capture 8288#define alc882_pcm_analog_capture alc880_pcm_analog_capture
9033#define alc883_pcm_analog_alt_capture alc880_pcm_analog_alt_capture 8289#define alc882_pcm_digital_playback alc880_pcm_digital_playback
9034#define alc883_pcm_digital_playback alc880_pcm_digital_playback 8290#define alc882_pcm_digital_capture alc880_pcm_digital_capture
9035#define alc883_pcm_digital_capture alc880_pcm_digital_capture 8291
8292static hda_nid_t alc883_slave_dig_outs[] = {
8293 ALC1200_DIGOUT_NID, 0,
8294};
8295
8296static hda_nid_t alc1200_slave_dig_outs[] = {
8297 ALC883_DIGOUT_NID, 0,
8298};
9036 8299
9037/* 8300/*
9038 * configuration and preset 8301 * configuration and preset
9039 */ 8302 */
9040static const char *alc883_models[ALC883_MODEL_LAST] = { 8303static const char *alc882_models[ALC882_MODEL_LAST] = {
9041 [ALC883_3ST_2ch_DIG] = "3stack-dig", 8304 [ALC882_3ST_DIG] = "3stack-dig",
8305 [ALC882_6ST_DIG] = "6stack-dig",
8306 [ALC882_ARIMA] = "arima",
8307 [ALC882_W2JC] = "w2jc",
8308 [ALC882_TARGA] = "targa",
8309 [ALC882_ASUS_A7J] = "asus-a7j",
8310 [ALC882_ASUS_A7M] = "asus-a7m",
8311 [ALC885_MACPRO] = "macpro",
8312 [ALC885_MB5] = "mb5",
8313 [ALC885_MBP3] = "mbp3",
8314 [ALC885_IMAC24] = "imac24",
8315 [ALC883_3ST_2ch_DIG] = "3stack-2ch-dig",
9042 [ALC883_3ST_6ch_DIG] = "3stack-6ch-dig", 8316 [ALC883_3ST_6ch_DIG] = "3stack-6ch-dig",
9043 [ALC883_3ST_6ch] = "3stack-6ch", 8317 [ALC883_3ST_6ch] = "3stack-6ch",
9044 [ALC883_6ST_DIG] = "6stack-dig", 8318 [ALC883_6ST_DIG] = "alc883-6stack-dig",
9045 [ALC883_TARGA_DIG] = "targa-dig", 8319 [ALC883_TARGA_DIG] = "targa-dig",
9046 [ALC883_TARGA_2ch_DIG] = "targa-2ch-dig", 8320 [ALC883_TARGA_2ch_DIG] = "targa-2ch-dig",
9047 [ALC883_TARGA_8ch_DIG] = "targa-8ch-dig", 8321 [ALC883_TARGA_8ch_DIG] = "targa-8ch-dig",
@@ -9068,11 +8342,12 @@ static const char *alc883_models[ALC883_MODEL_LAST] = {
9068 [ALC1200_ASUS_P5Q] = "asus-p5q", 8342 [ALC1200_ASUS_P5Q] = "asus-p5q",
9069 [ALC889A_MB31] = "mb31", 8343 [ALC889A_MB31] = "mb31",
9070 [ALC883_SONY_VAIO_TT] = "sony-vaio-tt", 8344 [ALC883_SONY_VAIO_TT] = "sony-vaio-tt",
9071 [ALC883_AUTO] = "auto", 8345 [ALC882_AUTO] = "auto",
9072}; 8346};
9073 8347
9074static struct snd_pci_quirk alc883_cfg_tbl[] = { 8348static struct snd_pci_quirk alc882_cfg_tbl[] = {
9075 SND_PCI_QUIRK(0x1019, 0x6668, "ECS", ALC883_3ST_6ch_DIG), 8349 SND_PCI_QUIRK(0x1019, 0x6668, "ECS", ALC882_6ST_DIG),
8350
9076 SND_PCI_QUIRK(0x1025, 0x006c, "Acer Aspire 9810", ALC883_ACER_ASPIRE), 8351 SND_PCI_QUIRK(0x1025, 0x006c, "Acer Aspire 9810", ALC883_ACER_ASPIRE),
9077 SND_PCI_QUIRK(0x1025, 0x0090, "Acer Aspire", ALC883_ACER_ASPIRE), 8352 SND_PCI_QUIRK(0x1025, 0x0090, "Acer Aspire", ALC883_ACER_ASPIRE),
9078 SND_PCI_QUIRK(0x1025, 0x010a, "Acer Ferrari 5000", ALC883_ACER_ASPIRE), 8353 SND_PCI_QUIRK(0x1025, 0x010a, "Acer Ferrari 5000", ALC883_ACER_ASPIRE),
@@ -9087,8 +8362,8 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
9087 ALC888_ACER_ASPIRE_8930G), 8362 ALC888_ACER_ASPIRE_8930G),
9088 SND_PCI_QUIRK(0x1025, 0x0146, "Acer Aspire 6935G", 8363 SND_PCI_QUIRK(0x1025, 0x0146, "Acer Aspire 6935G",
9089 ALC888_ACER_ASPIRE_8930G), 8364 ALC888_ACER_ASPIRE_8930G),
9090 SND_PCI_QUIRK(0x1025, 0x0157, "Acer X3200", ALC883_AUTO), 8365 SND_PCI_QUIRK(0x1025, 0x0157, "Acer X3200", ALC882_AUTO),
9091 SND_PCI_QUIRK(0x1025, 0x0158, "Acer AX1700-U3700A", ALC883_AUTO), 8366 SND_PCI_QUIRK(0x1025, 0x0158, "Acer AX1700-U3700A", ALC882_AUTO),
9092 SND_PCI_QUIRK(0x1025, 0x015e, "Acer Aspire 6930G", 8367 SND_PCI_QUIRK(0x1025, 0x015e, "Acer Aspire 6930G",
9093 ALC888_ACER_ASPIRE_6530G), 8368 ALC888_ACER_ASPIRE_6530G),
9094 SND_PCI_QUIRK(0x1025, 0x0166, "Acer Aspire 6530G", 8369 SND_PCI_QUIRK(0x1025, 0x0166, "Acer Aspire 6530G",
@@ -9097,30 +8372,44 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
9097 * model=auto should work fine now 8372 * model=auto should work fine now
9098 */ 8373 */
9099 /* SND_PCI_QUIRK_VENDOR(0x1025, "Acer laptop", ALC883_ACER), */ 8374 /* SND_PCI_QUIRK_VENDOR(0x1025, "Acer laptop", ALC883_ACER), */
8375
9100 SND_PCI_QUIRK(0x1028, 0x020d, "Dell Inspiron 530", ALC888_6ST_DELL), 8376 SND_PCI_QUIRK(0x1028, 0x020d, "Dell Inspiron 530", ALC888_6ST_DELL),
8377
9101 SND_PCI_QUIRK(0x103c, 0x2a3d, "HP Pavillion", ALC883_6ST_DIG), 8378 SND_PCI_QUIRK(0x103c, 0x2a3d, "HP Pavillion", ALC883_6ST_DIG),
9102 SND_PCI_QUIRK(0x103c, 0x2a4f, "HP Samba", ALC888_3ST_HP), 8379 SND_PCI_QUIRK(0x103c, 0x2a4f, "HP Samba", ALC888_3ST_HP),
9103 SND_PCI_QUIRK(0x103c, 0x2a60, "HP Lucknow", ALC888_3ST_HP), 8380 SND_PCI_QUIRK(0x103c, 0x2a60, "HP Lucknow", ALC888_3ST_HP),
9104 SND_PCI_QUIRK(0x103c, 0x2a61, "HP Nettle", ALC883_6ST_DIG), 8381 SND_PCI_QUIRK(0x103c, 0x2a61, "HP Nettle", ALC883_6ST_DIG),
9105 SND_PCI_QUIRK(0x103c, 0x2a66, "HP Acacia", ALC888_3ST_HP), 8382 SND_PCI_QUIRK(0x103c, 0x2a66, "HP Acacia", ALC888_3ST_HP),
9106 SND_PCI_QUIRK(0x103c, 0x2a72, "HP Educ.ar", ALC888_3ST_HP), 8383 SND_PCI_QUIRK(0x103c, 0x2a72, "HP Educ.ar", ALC888_3ST_HP),
8384
8385 SND_PCI_QUIRK(0x1043, 0x060d, "Asus A7J", ALC882_ASUS_A7J),
8386 SND_PCI_QUIRK(0x1043, 0x1243, "Asus A7J", ALC882_ASUS_A7J),
8387 SND_PCI_QUIRK(0x1043, 0x13c2, "Asus A7M", ALC882_ASUS_A7M),
9107 SND_PCI_QUIRK(0x1043, 0x1873, "Asus M90V", ALC888_ASUS_M90V), 8388 SND_PCI_QUIRK(0x1043, 0x1873, "Asus M90V", ALC888_ASUS_M90V),
8389 SND_PCI_QUIRK(0x1043, 0x1971, "Asus W2JC", ALC882_W2JC),
8390 SND_PCI_QUIRK(0x1043, 0x817f, "Asus P5LD2", ALC882_6ST_DIG),
8391 SND_PCI_QUIRK(0x1043, 0x81d8, "Asus P5WD", ALC882_6ST_DIG),
9108 SND_PCI_QUIRK(0x1043, 0x8249, "Asus M2A-VM HDMI", ALC883_3ST_6ch_DIG), 8392 SND_PCI_QUIRK(0x1043, 0x8249, "Asus M2A-VM HDMI", ALC883_3ST_6ch_DIG),
9109 SND_PCI_QUIRK(0x1043, 0x8284, "Asus Z37E", ALC883_6ST_DIG), 8393 SND_PCI_QUIRK(0x1043, 0x8284, "Asus Z37E", ALC883_6ST_DIG),
9110 SND_PCI_QUIRK(0x1043, 0x82fe, "Asus P5Q-EM HDMI", ALC1200_ASUS_P5Q), 8394 SND_PCI_QUIRK(0x1043, 0x82fe, "Asus P5Q-EM HDMI", ALC1200_ASUS_P5Q),
9111 SND_PCI_QUIRK(0x1043, 0x835f, "Asus Eee 1601", ALC888_ASUS_EEE1601), 8395 SND_PCI_QUIRK(0x1043, 0x835f, "Asus Eee 1601", ALC888_ASUS_EEE1601),
8396
8397 SND_PCI_QUIRK(0x104d, 0x9047, "Sony Vaio TT", ALC883_SONY_VAIO_TT),
9112 SND_PCI_QUIRK(0x105b, 0x0ce8, "Foxconn P35AX-S", ALC883_6ST_DIG), 8398 SND_PCI_QUIRK(0x105b, 0x0ce8, "Foxconn P35AX-S", ALC883_6ST_DIG),
9113 SND_PCI_QUIRK(0x105b, 0x6668, "Foxconn", ALC883_6ST_DIG), 8399 SND_PCI_QUIRK(0x105b, 0x6668, "Foxconn", ALC882_6ST_DIG),
9114 SND_PCI_QUIRK(0x1071, 0x8227, "Mitac 82801H", ALC883_MITAC), 8400 SND_PCI_QUIRK(0x1071, 0x8227, "Mitac 82801H", ALC883_MITAC),
9115 SND_PCI_QUIRK(0x1071, 0x8253, "Mitac 8252d", ALC883_MITAC), 8401 SND_PCI_QUIRK(0x1071, 0x8253, "Mitac 8252d", ALC883_MITAC),
9116 SND_PCI_QUIRK(0x1071, 0x8258, "Evesham Voyaeger", ALC883_LAPTOP_EAPD), 8402 SND_PCI_QUIRK(0x1071, 0x8258, "Evesham Voyaeger", ALC883_LAPTOP_EAPD),
9117 SND_PCI_QUIRK(0x10f1, 0x2350, "TYAN-S2350", ALC888_6ST_DELL), 8403 SND_PCI_QUIRK(0x10f1, 0x2350, "TYAN-S2350", ALC888_6ST_DELL),
9118 SND_PCI_QUIRK(0x108e, 0x534d, NULL, ALC883_3ST_6ch), 8404 SND_PCI_QUIRK(0x108e, 0x534d, NULL, ALC883_3ST_6ch),
9119 SND_PCI_QUIRK(0x1458, 0xa002, "MSI", ALC883_6ST_DIG), 8405 SND_PCI_QUIRK(0x1458, 0xa002, "Gigabyte P35 DS3R", ALC882_6ST_DIG),
8406
9120 SND_PCI_QUIRK(0x1462, 0x0349, "MSI", ALC883_TARGA_2ch_DIG), 8407 SND_PCI_QUIRK(0x1462, 0x0349, "MSI", ALC883_TARGA_2ch_DIG),
9121 SND_PCI_QUIRK(0x1462, 0x040d, "MSI", ALC883_TARGA_2ch_DIG), 8408 SND_PCI_QUIRK(0x1462, 0x040d, "MSI", ALC883_TARGA_2ch_DIG),
9122 SND_PCI_QUIRK(0x1462, 0x0579, "MSI", ALC883_TARGA_2ch_DIG), 8409 SND_PCI_QUIRK(0x1462, 0x0579, "MSI", ALC883_TARGA_2ch_DIG),
8410 SND_PCI_QUIRK(0x1462, 0x28fb, "Targa T8", ALC882_TARGA), /* MSI-1049 T8 */
9123 SND_PCI_QUIRK(0x1462, 0x2fb3, "MSI", ALC883_TARGA_2ch_DIG), 8411 SND_PCI_QUIRK(0x1462, 0x2fb3, "MSI", ALC883_TARGA_2ch_DIG),
8412 SND_PCI_QUIRK(0x1462, 0x6668, "MSI", ALC882_6ST_DIG),
9124 SND_PCI_QUIRK(0x1462, 0x3729, "MSI S420", ALC883_TARGA_DIG), 8413 SND_PCI_QUIRK(0x1462, 0x3729, "MSI S420", ALC883_TARGA_DIG),
9125 SND_PCI_QUIRK(0x1462, 0x3783, "NEC S970", ALC883_TARGA_DIG), 8414 SND_PCI_QUIRK(0x1462, 0x3783, "NEC S970", ALC883_TARGA_DIG),
9126 SND_PCI_QUIRK(0x1462, 0x3b7f, "MSI", ALC883_TARGA_2ch_DIG), 8415 SND_PCI_QUIRK(0x1462, 0x3b7f, "MSI", ALC883_TARGA_2ch_DIG),
@@ -9142,11 +8431,13 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
9142 SND_PCI_QUIRK(0x1462, 0x7327, "MSI", ALC883_6ST_DIG), 8431 SND_PCI_QUIRK(0x1462, 0x7327, "MSI", ALC883_6ST_DIG),
9143 SND_PCI_QUIRK(0x1462, 0x7350, "MSI", ALC883_6ST_DIG), 8432 SND_PCI_QUIRK(0x1462, 0x7350, "MSI", ALC883_6ST_DIG),
9144 SND_PCI_QUIRK(0x1462, 0xa422, "MSI", ALC883_TARGA_2ch_DIG), 8433 SND_PCI_QUIRK(0x1462, 0xa422, "MSI", ALC883_TARGA_2ch_DIG),
8434
9145 SND_PCI_QUIRK(0x147b, 0x1083, "Abit IP35-PRO", ALC883_6ST_DIG), 8435 SND_PCI_QUIRK(0x147b, 0x1083, "Abit IP35-PRO", ALC883_6ST_DIG),
9146 SND_PCI_QUIRK(0x1558, 0x0721, "Clevo laptop M720R", ALC883_CLEVO_M720), 8436 SND_PCI_QUIRK(0x1558, 0x0721, "Clevo laptop M720R", ALC883_CLEVO_M720),
9147 SND_PCI_QUIRK(0x1558, 0x0722, "Clevo laptop M720SR", ALC883_CLEVO_M720), 8437 SND_PCI_QUIRK(0x1558, 0x0722, "Clevo laptop M720SR", ALC883_CLEVO_M720),
9148 SND_PCI_QUIRK_VENDOR(0x1558, "Clevo laptop", ALC883_LAPTOP_EAPD), 8438 SND_PCI_QUIRK_VENDOR(0x1558, "Clevo laptop", ALC883_LAPTOP_EAPD),
9149 SND_PCI_QUIRK(0x15d9, 0x8780, "Supermicro PDSBA", ALC883_3ST_6ch), 8439 SND_PCI_QUIRK(0x15d9, 0x8780, "Supermicro PDSBA", ALC883_3ST_6ch),
8440 /* SND_PCI_QUIRK(0x161f, 0x2054, "Arima W820", ALC882_ARIMA), */
9150 SND_PCI_QUIRK(0x161f, 0x2054, "Medion laptop", ALC883_MEDION), 8441 SND_PCI_QUIRK(0x161f, 0x2054, "Medion laptop", ALC883_MEDION),
9151 SND_PCI_QUIRK_MASK(0x1734, 0xfff0, 0x1100, "FSC AMILO Xi/Pi25xx", 8442 SND_PCI_QUIRK_MASK(0x1734, 0xfff0, 0x1100, "FSC AMILO Xi/Pi25xx",
9152 ALC883_FUJITSU_PI2515), 8443 ALC883_FUJITSU_PI2515),
@@ -9161,24 +8452,175 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
9161 SND_PCI_QUIRK(0x17c0, 0x4085, "MEDION MD96630", ALC888_LENOVO_MS7195_DIG), 8452 SND_PCI_QUIRK(0x17c0, 0x4085, "MEDION MD96630", ALC888_LENOVO_MS7195_DIG),
9162 SND_PCI_QUIRK(0x17f2, 0x5000, "Albatron KI690-AM2", ALC883_6ST_DIG), 8453 SND_PCI_QUIRK(0x17f2, 0x5000, "Albatron KI690-AM2", ALC883_6ST_DIG),
9163 SND_PCI_QUIRK(0x1991, 0x5625, "Haier W66", ALC883_HAIER_W66), 8454 SND_PCI_QUIRK(0x1991, 0x5625, "Haier W66", ALC883_HAIER_W66),
8455
9164 SND_PCI_QUIRK(0x8086, 0x0001, "DG33BUC", ALC883_3ST_6ch_INTEL), 8456 SND_PCI_QUIRK(0x8086, 0x0001, "DG33BUC", ALC883_3ST_6ch_INTEL),
9165 SND_PCI_QUIRK(0x8086, 0x0002, "DG33FBC", ALC883_3ST_6ch_INTEL), 8457 SND_PCI_QUIRK(0x8086, 0x0002, "DG33FBC", ALC883_3ST_6ch_INTEL),
9166 SND_PCI_QUIRK(0x8086, 0x2503, "82801H", ALC883_MITAC), 8458 SND_PCI_QUIRK(0x8086, 0x2503, "82801H", ALC883_MITAC),
9167 SND_PCI_QUIRK(0x8086, 0x0022, "DX58SO", ALC883_3ST_6ch_INTEL), 8459 SND_PCI_QUIRK(0x8086, 0x0022, "DX58SO", ALC883_3ST_6ch_INTEL),
9168 SND_PCI_QUIRK(0x8086, 0xd601, "D102GGC", ALC883_3ST_6ch), 8460 SND_PCI_QUIRK(0x8086, 0xd601, "D102GGC", ALC883_3ST_6ch),
9169 SND_PCI_QUIRK(0x104d, 0x9047, "Sony Vaio TT", ALC883_SONY_VAIO_TT),
9170 {}
9171};
9172 8461
9173static hda_nid_t alc883_slave_dig_outs[] = { 8462 {}
9174 ALC1200_DIGOUT_NID, 0,
9175}; 8463};
9176 8464
9177static hda_nid_t alc1200_slave_dig_outs[] = { 8465/* codec SSID table for Intel Mac */
9178 ALC883_DIGOUT_NID, 0, 8466static struct snd_pci_quirk alc882_ssid_cfg_tbl[] = {
8467 SND_PCI_QUIRK(0x106b, 0x00a0, "MacBookPro 3,1", ALC885_MBP3),
8468 SND_PCI_QUIRK(0x106b, 0x00a1, "Macbook", ALC885_MBP3),
8469 SND_PCI_QUIRK(0x106b, 0x00a4, "MacbookPro 4,1", ALC885_MBP3),
8470 SND_PCI_QUIRK(0x106b, 0x0c00, "Mac Pro", ALC885_MACPRO),
8471 SND_PCI_QUIRK(0x106b, 0x1000, "iMac 24", ALC885_IMAC24),
8472 SND_PCI_QUIRK(0x106b, 0x2800, "AppleTV", ALC885_IMAC24),
8473 SND_PCI_QUIRK(0x106b, 0x2c00, "MacbookPro rev3", ALC885_MBP3),
8474 SND_PCI_QUIRK(0x106b, 0x3600, "Macbook 3,1", ALC889A_MB31),
8475 SND_PCI_QUIRK(0x106b, 0x3800, "MacbookPro 4,1", ALC885_MBP3),
8476 SND_PCI_QUIRK(0x106b, 0x3e00, "iMac 24 Aluminum", ALC885_IMAC24),
8477 SND_PCI_QUIRK(0x106b, 0x3f00, "Macbook 5,1", ALC885_MB5),
8478 /* FIXME: HP jack sense seems not working for MBP 5,1, so apparently
8479 * no perfect solution yet
8480 */
8481 SND_PCI_QUIRK(0x106b, 0x4000, "MacbookPro 5,1", ALC885_MB5),
8482 {} /* terminator */
9179}; 8483};
9180 8484
9181static struct alc_config_preset alc883_presets[] = { 8485static struct alc_config_preset alc882_presets[] = {
8486 [ALC882_3ST_DIG] = {
8487 .mixers = { alc882_base_mixer },
8488 .init_verbs = { alc882_init_verbs },
8489 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8490 .dac_nids = alc882_dac_nids,
8491 .dig_out_nid = ALC882_DIGOUT_NID,
8492 .dig_in_nid = ALC882_DIGIN_NID,
8493 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
8494 .channel_mode = alc882_ch_modes,
8495 .need_dac_fix = 1,
8496 .input_mux = &alc882_capture_source,
8497 },
8498 [ALC882_6ST_DIG] = {
8499 .mixers = { alc882_base_mixer, alc882_chmode_mixer },
8500 .init_verbs = { alc882_init_verbs },
8501 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8502 .dac_nids = alc882_dac_nids,
8503 .dig_out_nid = ALC882_DIGOUT_NID,
8504 .dig_in_nid = ALC882_DIGIN_NID,
8505 .num_channel_mode = ARRAY_SIZE(alc882_sixstack_modes),
8506 .channel_mode = alc882_sixstack_modes,
8507 .input_mux = &alc882_capture_source,
8508 },
8509 [ALC882_ARIMA] = {
8510 .mixers = { alc882_base_mixer, alc882_chmode_mixer },
8511 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs },
8512 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8513 .dac_nids = alc882_dac_nids,
8514 .num_channel_mode = ARRAY_SIZE(alc882_sixstack_modes),
8515 .channel_mode = alc882_sixstack_modes,
8516 .input_mux = &alc882_capture_source,
8517 },
8518 [ALC882_W2JC] = {
8519 .mixers = { alc882_w2jc_mixer, alc882_chmode_mixer },
8520 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs,
8521 alc880_gpio1_init_verbs },
8522 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8523 .dac_nids = alc882_dac_nids,
8524 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
8525 .channel_mode = alc880_threestack_modes,
8526 .need_dac_fix = 1,
8527 .input_mux = &alc882_capture_source,
8528 .dig_out_nid = ALC882_DIGOUT_NID,
8529 },
8530 [ALC885_MBP3] = {
8531 .mixers = { alc885_mbp3_mixer, alc882_chmode_mixer },
8532 .init_verbs = { alc885_mbp3_init_verbs,
8533 alc880_gpio1_init_verbs },
8534 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8535 .dac_nids = alc882_dac_nids,
8536 .channel_mode = alc885_mbp_6ch_modes,
8537 .num_channel_mode = ARRAY_SIZE(alc885_mbp_6ch_modes),
8538 .input_mux = &alc882_capture_source,
8539 .dig_out_nid = ALC882_DIGOUT_NID,
8540 .dig_in_nid = ALC882_DIGIN_NID,
8541 .unsol_event = alc_automute_amp_unsol_event,
8542 .init_hook = alc885_mbp3_init_hook,
8543 },
8544 [ALC885_MB5] = {
8545 .mixers = { alc885_mb5_mixer, alc882_chmode_mixer },
8546 .init_verbs = { alc885_mb5_init_verbs,
8547 alc880_gpio1_init_verbs },
8548 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8549 .dac_nids = alc882_dac_nids,
8550 .channel_mode = alc885_mb5_6ch_modes,
8551 .num_channel_mode = ARRAY_SIZE(alc885_mb5_6ch_modes),
8552 .input_mux = &mb5_capture_source,
8553 .dig_out_nid = ALC882_DIGOUT_NID,
8554 .dig_in_nid = ALC882_DIGIN_NID,
8555 },
8556 [ALC885_MACPRO] = {
8557 .mixers = { alc882_macpro_mixer },
8558 .init_verbs = { alc882_macpro_init_verbs },
8559 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8560 .dac_nids = alc882_dac_nids,
8561 .dig_out_nid = ALC882_DIGOUT_NID,
8562 .dig_in_nid = ALC882_DIGIN_NID,
8563 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
8564 .channel_mode = alc882_ch_modes,
8565 .input_mux = &alc882_capture_source,
8566 .init_hook = alc885_macpro_init_hook,
8567 },
8568 [ALC885_IMAC24] = {
8569 .mixers = { alc885_imac24_mixer },
8570 .init_verbs = { alc885_imac24_init_verbs },
8571 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8572 .dac_nids = alc882_dac_nids,
8573 .dig_out_nid = ALC882_DIGOUT_NID,
8574 .dig_in_nid = ALC882_DIGIN_NID,
8575 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
8576 .channel_mode = alc882_ch_modes,
8577 .input_mux = &alc882_capture_source,
8578 .unsol_event = alc_automute_amp_unsol_event,
8579 .init_hook = alc885_imac24_init_hook,
8580 },
8581 [ALC882_TARGA] = {
8582 .mixers = { alc882_targa_mixer, alc882_chmode_mixer },
8583 .init_verbs = { alc882_init_verbs, alc882_targa_verbs},
8584 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8585 .dac_nids = alc882_dac_nids,
8586 .dig_out_nid = ALC882_DIGOUT_NID,
8587 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
8588 .adc_nids = alc882_adc_nids,
8589 .capsrc_nids = alc882_capsrc_nids,
8590 .num_channel_mode = ARRAY_SIZE(alc882_3ST_6ch_modes),
8591 .channel_mode = alc882_3ST_6ch_modes,
8592 .need_dac_fix = 1,
8593 .input_mux = &alc882_capture_source,
8594 .unsol_event = alc882_targa_unsol_event,
8595 .init_hook = alc882_targa_init_hook,
8596 },
8597 [ALC882_ASUS_A7J] = {
8598 .mixers = { alc882_asus_a7j_mixer, alc882_chmode_mixer },
8599 .init_verbs = { alc882_init_verbs, alc882_asus_a7j_verbs},
8600 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8601 .dac_nids = alc882_dac_nids,
8602 .dig_out_nid = ALC882_DIGOUT_NID,
8603 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
8604 .adc_nids = alc882_adc_nids,
8605 .capsrc_nids = alc882_capsrc_nids,
8606 .num_channel_mode = ARRAY_SIZE(alc882_3ST_6ch_modes),
8607 .channel_mode = alc882_3ST_6ch_modes,
8608 .need_dac_fix = 1,
8609 .input_mux = &alc882_capture_source,
8610 },
8611 [ALC882_ASUS_A7M] = {
8612 .mixers = { alc882_asus_a7m_mixer, alc882_chmode_mixer },
8613 .init_verbs = { alc882_init_verbs, alc882_eapd_verbs,
8614 alc880_gpio1_init_verbs,
8615 alc882_asus_a7m_verbs },
8616 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
8617 .dac_nids = alc882_dac_nids,
8618 .dig_out_nid = ALC882_DIGOUT_NID,
8619 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
8620 .channel_mode = alc880_threestack_modes,
8621 .need_dac_fix = 1,
8622 .input_mux = &alc882_capture_source,
8623 },
9182 [ALC883_3ST_2ch_DIG] = { 8624 [ALC883_3ST_2ch_DIG] = {
9183 .mixers = { alc883_3ST_2ch_mixer }, 8625 .mixers = { alc883_3ST_2ch_mixer },
9184 .init_verbs = { alc883_init_verbs }, 8626 .init_verbs = { alc883_init_verbs },
@@ -9613,9 +9055,32 @@ static struct alc_config_preset alc883_presets[] = {
9613 9055
9614 9056
9615/* 9057/*
9058 * Pin config fixes
9059 */
9060enum {
9061 PINFIX_ABIT_AW9D_MAX
9062};
9063
9064static struct alc_pincfg alc882_abit_aw9d_pinfix[] = {
9065 { 0x15, 0x01080104 }, /* side */
9066 { 0x16, 0x01011012 }, /* rear */
9067 { 0x17, 0x01016011 }, /* clfe */
9068 { }
9069};
9070
9071static const struct alc_pincfg *alc882_pin_fixes[] = {
9072 [PINFIX_ABIT_AW9D_MAX] = alc882_abit_aw9d_pinfix,
9073};
9074
9075static struct snd_pci_quirk alc882_pinfix_tbl[] = {
9076 SND_PCI_QUIRK(0x147b, 0x107a, "Abit AW9D-MAX", PINFIX_ABIT_AW9D_MAX),
9077 {}
9078};
9079
9080/*
9616 * BIOS auto configuration 9081 * BIOS auto configuration
9617 */ 9082 */
9618static void alc883_auto_set_output_and_unmute(struct hda_codec *codec, 9083static void alc882_auto_set_output_and_unmute(struct hda_codec *codec,
9619 hda_nid_t nid, int pin_type, 9084 hda_nid_t nid, int pin_type,
9620 int dac_idx) 9085 int dac_idx)
9621{ 9086{
@@ -9632,7 +9097,7 @@ static void alc883_auto_set_output_and_unmute(struct hda_codec *codec,
9632 9097
9633} 9098}
9634 9099
9635static void alc883_auto_init_multi_out(struct hda_codec *codec) 9100static void alc882_auto_init_multi_out(struct hda_codec *codec)
9636{ 9101{
9637 struct alc_spec *spec = codec->spec; 9102 struct alc_spec *spec = codec->spec;
9638 int i; 9103 int i;
@@ -9641,12 +9106,12 @@ static void alc883_auto_init_multi_out(struct hda_codec *codec)
9641 hda_nid_t nid = spec->autocfg.line_out_pins[i]; 9106 hda_nid_t nid = spec->autocfg.line_out_pins[i];
9642 int pin_type = get_pin_type(spec->autocfg.line_out_type); 9107 int pin_type = get_pin_type(spec->autocfg.line_out_type);
9643 if (nid) 9108 if (nid)
9644 alc883_auto_set_output_and_unmute(codec, nid, pin_type, 9109 alc882_auto_set_output_and_unmute(codec, nid, pin_type,
9645 i); 9110 i);
9646 } 9111 }
9647} 9112}
9648 9113
9649static void alc883_auto_init_hp_out(struct hda_codec *codec) 9114static void alc882_auto_init_hp_out(struct hda_codec *codec)
9650{ 9115{
9651 struct alc_spec *spec = codec->spec; 9116 struct alc_spec *spec = codec->spec;
9652 hda_nid_t pin; 9117 hda_nid_t pin;
@@ -9654,42 +9119,114 @@ static void alc883_auto_init_hp_out(struct hda_codec *codec)
9654 pin = spec->autocfg.hp_pins[0]; 9119 pin = spec->autocfg.hp_pins[0];
9655 if (pin) /* connect to front */ 9120 if (pin) /* connect to front */
9656 /* use dac 0 */ 9121 /* use dac 0 */
9657 alc883_auto_set_output_and_unmute(codec, pin, PIN_HP, 0); 9122 alc882_auto_set_output_and_unmute(codec, pin, PIN_HP, 0);
9658 pin = spec->autocfg.speaker_pins[0]; 9123 pin = spec->autocfg.speaker_pins[0];
9659 if (pin) 9124 if (pin)
9660 alc883_auto_set_output_and_unmute(codec, pin, PIN_OUT, 0); 9125 alc882_auto_set_output_and_unmute(codec, pin, PIN_OUT, 0);
9661} 9126}
9662 9127
9663#define alc883_is_input_pin(nid) alc880_is_input_pin(nid) 9128#define alc882_is_input_pin(nid) alc880_is_input_pin(nid)
9664#define ALC883_PIN_CD_NID ALC880_PIN_CD_NID 9129#define ALC882_PIN_CD_NID ALC880_PIN_CD_NID
9665 9130
9666static void alc883_auto_init_analog_input(struct hda_codec *codec) 9131static void alc882_auto_init_analog_input(struct hda_codec *codec)
9667{ 9132{
9668 struct alc_spec *spec = codec->spec; 9133 struct alc_spec *spec = codec->spec;
9669 int i; 9134 int i;
9670 9135
9671 for (i = 0; i < AUTO_PIN_LAST; i++) { 9136 for (i = 0; i < AUTO_PIN_LAST; i++) {
9672 hda_nid_t nid = spec->autocfg.input_pins[i]; 9137 hda_nid_t nid = spec->autocfg.input_pins[i];
9673 if (alc883_is_input_pin(nid)) { 9138 if (!nid)
9674 alc_set_input_pin(codec, nid, i); 9139 continue;
9675 if (nid != ALC883_PIN_CD_NID && 9140 alc_set_input_pin(codec, nid, AUTO_PIN_FRONT_MIC /*i*/);
9676 (get_wcaps(codec, nid) & AC_WCAP_OUT_AMP)) 9141 if (get_wcaps(codec, nid) & AC_WCAP_OUT_AMP)
9142 snd_hda_codec_write(codec, nid, 0,
9143 AC_VERB_SET_AMP_GAIN_MUTE,
9144 AMP_OUT_MUTE);
9145 }
9146}
9147
9148static void alc882_auto_init_input_src(struct hda_codec *codec)
9149{
9150 struct alc_spec *spec = codec->spec;
9151 int c;
9152
9153 for (c = 0; c < spec->num_adc_nids; c++) {
9154 hda_nid_t conn_list[HDA_MAX_NUM_INPUTS];
9155 hda_nid_t nid = spec->capsrc_nids[c];
9156 unsigned int mux_idx;
9157 const struct hda_input_mux *imux;
9158 int conns, mute, idx, item;
9159
9160 conns = snd_hda_get_connections(codec, nid, conn_list,
9161 ARRAY_SIZE(conn_list));
9162 if (conns < 0)
9163 continue;
9164 mux_idx = c >= spec->num_mux_defs ? 0 : c;
9165 imux = &spec->input_mux[mux_idx];
9166 for (idx = 0; idx < conns; idx++) {
9167 /* if the current connection is the selected one,
9168 * unmute it as default - otherwise mute it
9169 */
9170 mute = AMP_IN_MUTE(idx);
9171 for (item = 0; item < imux->num_items; item++) {
9172 if (imux->items[item].index == idx) {
9173 if (spec->cur_mux[c] == item)
9174 mute = AMP_IN_UNMUTE(idx);
9175 break;
9176 }
9177 }
9178 /* check if we have a selector or mixer
9179 * we could check for the widget type instead, but
9180 * just check for Amp-In presence (in case of mixer
9181 * without amp-in there is something wrong, this
9182 * function shouldn't be used or capsrc nid is wrong)
9183 */
9184 if (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)
9677 snd_hda_codec_write(codec, nid, 0, 9185 snd_hda_codec_write(codec, nid, 0,
9678 AC_VERB_SET_AMP_GAIN_MUTE, 9186 AC_VERB_SET_AMP_GAIN_MUTE,
9679 AMP_OUT_MUTE); 9187 mute);
9188 else if (mute != AMP_IN_MUTE(idx))
9189 snd_hda_codec_write(codec, nid, 0,
9190 AC_VERB_SET_CONNECT_SEL,
9191 idx);
9680 } 9192 }
9681 } 9193 }
9682} 9194}
9683 9195
9684#define alc883_auto_init_input_src alc882_auto_init_input_src 9196/* add mic boosts if needed */
9197static int alc_auto_add_mic_boost(struct hda_codec *codec)
9198{
9199 struct alc_spec *spec = codec->spec;
9200 int err;
9201 hda_nid_t nid;
9202
9203 nid = spec->autocfg.input_pins[AUTO_PIN_MIC];
9204 if (nid && (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)) {
9205 err = add_control(spec, ALC_CTL_WIDGET_VOL,
9206 "Mic Boost",
9207 HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_INPUT));
9208 if (err < 0)
9209 return err;
9210 }
9211 nid = spec->autocfg.input_pins[AUTO_PIN_FRONT_MIC];
9212 if (nid && (get_wcaps(codec, nid) & AC_WCAP_IN_AMP)) {
9213 err = add_control(spec, ALC_CTL_WIDGET_VOL,
9214 "Front Mic Boost",
9215 HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_INPUT));
9216 if (err < 0)
9217 return err;
9218 }
9219 return 0;
9220}
9685 9221
9686/* almost identical with ALC880 parser... */ 9222/* almost identical with ALC880 parser... */
9687static int alc883_parse_auto_config(struct hda_codec *codec) 9223static int alc882_parse_auto_config(struct hda_codec *codec)
9688{ 9224{
9689 struct alc_spec *spec = codec->spec; 9225 struct alc_spec *spec = codec->spec;
9690 int err = alc880_parse_auto_config(codec); 9226 struct auto_pin_cfg *autocfg = &spec->autocfg;
9691 struct auto_pin_cfg *cfg = &spec->autocfg; 9227 unsigned int wcap;
9692 int i; 9228 int i;
9229 int err = alc880_parse_auto_config(codec);
9693 9230
9694 if (err < 0) 9231 if (err < 0)
9695 return err; 9232 return err;
@@ -9702,43 +9239,45 @@ static int alc883_parse_auto_config(struct hda_codec *codec)
9702 9239
9703 /* hack - override the init verbs */ 9240 /* hack - override the init verbs */
9704 spec->init_verbs[0] = alc883_auto_init_verbs; 9241 spec->init_verbs[0] = alc883_auto_init_verbs;
9242 /* if ADC 0x07 is available, initialize it, too */
9243 wcap = get_wcaps(codec, 0x07);
9244 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT;
9245 if (wcap == AC_WID_AUD_IN)
9246 add_verb(spec, alc882_adc1_init_verbs);
9705 9247
9706 /* setup input_mux for ALC889 */ 9248 /* digital-mic input pin is excluded in alc880_auto_create..()
9707 if (codec->vendor_id == 0x10ec0889) { 9249 * because it's under 0x18
9708 /* digital-mic input pin is excluded in alc880_auto_create..() 9250 */
9709 * because it's under 0x18 9251 if (autocfg->input_pins[AUTO_PIN_MIC] == 0x12 ||
9710 */ 9252 autocfg->input_pins[AUTO_PIN_FRONT_MIC] == 0x12) {
9711 if (cfg->input_pins[AUTO_PIN_MIC] == 0x12 || 9253 struct hda_input_mux *imux = &spec->private_imux[0];
9712 cfg->input_pins[AUTO_PIN_FRONT_MIC] == 0x12) { 9254 for (i = 1; i < 3; i++)
9713 struct hda_input_mux *imux = &spec->private_imux[0]; 9255 memcpy(&spec->private_imux[i],
9714 for (i = 1; i < 3; i++) 9256 &spec->private_imux[0],
9715 memcpy(&spec->private_imux[i], 9257 sizeof(spec->private_imux[0]));
9716 &spec->private_imux[0], 9258 imux->items[imux->num_items].label = "Int DMic";
9717 sizeof(spec->private_imux[0])); 9259 imux->items[imux->num_items].index = 0x0b;
9718 imux->items[imux->num_items].label = "Int DMic"; 9260 imux->num_items++;
9719 imux->items[imux->num_items].index = 0x0b; 9261 spec->num_mux_defs = 3;
9720 imux->num_items++; 9262 spec->input_mux = spec->private_imux;
9721 spec->num_mux_defs = 3;
9722 spec->input_mux = spec->private_imux;
9723 }
9724 } 9263 }
9725 9264
9726 return 1; /* config found */ 9265 return 1; /* config found */
9727} 9266}
9728 9267
9729/* additional initialization for auto-configuration model */ 9268/* additional initialization for auto-configuration model */
9730static void alc883_auto_init(struct hda_codec *codec) 9269static void alc882_auto_init(struct hda_codec *codec)
9731{ 9270{
9732 struct alc_spec *spec = codec->spec; 9271 struct alc_spec *spec = codec->spec;
9733 alc883_auto_init_multi_out(codec); 9272 alc882_auto_init_multi_out(codec);
9734 alc883_auto_init_hp_out(codec); 9273 alc882_auto_init_hp_out(codec);
9735 alc883_auto_init_analog_input(codec); 9274 alc882_auto_init_analog_input(codec);
9736 alc883_auto_init_input_src(codec); 9275 alc882_auto_init_input_src(codec);
9737 if (spec->unsol_event) 9276 if (spec->unsol_event)
9738 alc_inithook(codec); 9277 alc_inithook(codec);
9739} 9278}
9740 9279
9741static int patch_alc883(struct hda_codec *codec) 9280static int patch_alc882(struct hda_codec *codec)
9742{ 9281{
9743 struct alc_spec *spec; 9282 struct alc_spec *spec;
9744 int err, board_config; 9283 int err, board_config;
@@ -9749,28 +9288,36 @@ static int patch_alc883(struct hda_codec *codec)
9749 9288
9750 codec->spec = spec; 9289 codec->spec = spec;
9751 9290
9752 alc_fix_pll_init(codec, 0x20, 0x0a, 10); 9291 switch (codec->vendor_id) {
9292 case 0x10ec0882:
9293 case 0x10ec0885:
9294 break;
9295 default:
9296 /* ALC883 and variants */
9297 alc_fix_pll_init(codec, 0x20, 0x0a, 10);
9298 break;
9299 }
9753 9300
9754 board_config = snd_hda_check_board_config(codec, ALC883_MODEL_LAST, 9301 board_config = snd_hda_check_board_config(codec, ALC882_MODEL_LAST,
9755 alc883_models, 9302 alc882_models,
9756 alc883_cfg_tbl); 9303 alc882_cfg_tbl);
9757 if (board_config < 0 || board_config >= ALC883_MODEL_LAST) { 9304
9758 /* Pick up systems that don't supply PCI SSID */ 9305 if (board_config < 0 || board_config >= ALC882_MODEL_LAST)
9759 switch (codec->subsystem_id) { 9306 board_config = snd_hda_check_board_codec_sid_config(codec,
9760 case 0x106b3600: /* Macbook 3.1 */ 9307 ALC882_MODEL_LAST, alc882_models, alc882_ssid_cfg_tbl);
9761 board_config = ALC889A_MB31; 9308
9762 break; 9309 if (board_config < 0 || board_config >= ALC882_MODEL_LAST) {
9763 default: 9310 printk(KERN_INFO "hda_codec: Unknown model for %s, "
9764 printk(KERN_INFO 9311 "trying auto-probe from BIOS...\n",
9765 "hda_codec: Unknown model for %s, trying " 9312 codec->chip_name);
9766 "auto-probe from BIOS...\n", codec->chip_name); 9313 board_config = ALC882_AUTO;
9767 board_config = ALC883_AUTO;
9768 }
9769 } 9314 }
9770 9315
9771 if (board_config == ALC883_AUTO) { 9316 alc_fix_pincfg(codec, alc882_pinfix_tbl, alc882_pin_fixes);
9317
9318 if (board_config == ALC882_AUTO) {
9772 /* automatic parse from the BIOS config */ 9319 /* automatic parse from the BIOS config */
9773 err = alc883_parse_auto_config(codec); 9320 err = alc882_parse_auto_config(codec);
9774 if (err < 0) { 9321 if (err < 0) {
9775 alc_free(codec); 9322 alc_free(codec);
9776 return err; 9323 return err;
@@ -9778,7 +9325,7 @@ static int patch_alc883(struct hda_codec *codec)
9778 printk(KERN_INFO 9325 printk(KERN_INFO
9779 "hda_codec: Cannot set up configuration " 9326 "hda_codec: Cannot set up configuration "
9780 "from BIOS. Using base mode...\n"); 9327 "from BIOS. Using base mode...\n");
9781 board_config = ALC883_3ST_2ch_DIG; 9328 board_config = ALC882_3ST_DIG;
9782 } 9329 }
9783 } 9330 }
9784 9331
@@ -9788,63 +9335,61 @@ static int patch_alc883(struct hda_codec *codec)
9788 return err; 9335 return err;
9789 } 9336 }
9790 9337
9791 if (board_config != ALC883_AUTO) 9338 if (board_config != ALC882_AUTO)
9792 setup_preset(spec, &alc883_presets[board_config]); 9339 setup_preset(spec, &alc882_presets[board_config]);
9793 9340
9794 switch (codec->vendor_id) { 9341 spec->stream_analog_playback = &alc882_pcm_analog_playback;
9795 case 0x10ec0888: 9342 spec->stream_analog_capture = &alc882_pcm_analog_capture;
9796 if (!spec->num_adc_nids) { 9343 /* FIXME: setup DAC5 */
9797 spec->num_adc_nids = ARRAY_SIZE(alc883_adc_nids); 9344 /*spec->stream_analog_alt_playback = &alc880_pcm_analog_alt_playback;*/
9798 spec->adc_nids = alc883_adc_nids; 9345 spec->stream_analog_alt_capture = &alc880_pcm_analog_alt_capture;
9799 } 9346
9800 if (!spec->capsrc_nids) 9347 spec->stream_digital_playback = &alc882_pcm_digital_playback;
9801 spec->capsrc_nids = alc883_capsrc_nids; 9348 spec->stream_digital_capture = &alc882_pcm_digital_capture;
9349
9350 if (codec->vendor_id == 0x10ec0888)
9802 spec->init_amp = ALC_INIT_DEFAULT; /* always initialize */ 9351 spec->init_amp = ALC_INIT_DEFAULT; /* always initialize */
9803 break; 9352
9804 case 0x10ec0889: 9353 if (!spec->adc_nids && spec->input_mux) {
9805 if (!spec->num_adc_nids) { 9354 int i;
9806 spec->num_adc_nids = ARRAY_SIZE(alc889_adc_nids); 9355 spec->num_adc_nids = 0;
9807 spec->adc_nids = alc889_adc_nids; 9356 for (i = 0; i < ARRAY_SIZE(alc882_adc_nids); i++) {
9808 } 9357 hda_nid_t cap;
9809 if (!spec->capsrc_nids) 9358 hda_nid_t nid = alc882_adc_nids[i];
9810 spec->capsrc_nids = alc889_capsrc_nids; 9359 unsigned int wcap = get_wcaps(codec, nid);
9811 break; 9360 /* get type */
9812 default: 9361 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT;
9813 if (!spec->num_adc_nids) { 9362 if (wcap != AC_WID_AUD_IN)
9814 spec->num_adc_nids = ARRAY_SIZE(alc883_adc_nids); 9363 continue;
9815 spec->adc_nids = alc883_adc_nids; 9364 spec->private_adc_nids[spec->num_adc_nids] = nid;
9365 err = snd_hda_get_connections(codec, nid, &cap, 1);
9366 if (err < 0)
9367 continue;
9368 spec->private_capsrc_nids[spec->num_adc_nids] = cap;
9369 spec->num_adc_nids++;
9816 } 9370 }
9817 if (!spec->capsrc_nids) 9371 spec->adc_nids = spec->private_adc_nids;
9818 spec->capsrc_nids = alc883_capsrc_nids; 9372 spec->capsrc_nids = spec->private_capsrc_nids;
9819 break;
9820 } 9373 }
9821 9374
9822 spec->stream_analog_playback = &alc883_pcm_analog_playback; 9375 set_capture_mixer(spec);
9823 spec->stream_analog_capture = &alc883_pcm_analog_capture;
9824 spec->stream_analog_alt_capture = &alc883_pcm_analog_alt_capture;
9825
9826 spec->stream_digital_playback = &alc883_pcm_digital_playback;
9827 spec->stream_digital_capture = &alc883_pcm_digital_capture;
9828
9829 if (!spec->cap_mixer)
9830 set_capture_mixer(spec);
9831 set_beep_amp(spec, 0x0b, 0x05, HDA_INPUT); 9376 set_beep_amp(spec, 0x0b, 0x05, HDA_INPUT);
9832 9377
9833 spec->vmaster_nid = 0x0c; 9378 spec->vmaster_nid = 0x0c;
9834 9379
9835 codec->patch_ops = alc_patch_ops; 9380 codec->patch_ops = alc_patch_ops;
9836 if (board_config == ALC883_AUTO) 9381 if (board_config == ALC882_AUTO)
9837 spec->init_hook = alc883_auto_init; 9382 spec->init_hook = alc882_auto_init;
9838
9839#ifdef CONFIG_SND_HDA_POWER_SAVE 9383#ifdef CONFIG_SND_HDA_POWER_SAVE
9840 if (!spec->loopback.amplist) 9384 if (!spec->loopback.amplist)
9841 spec->loopback.amplist = alc883_loopbacks; 9385 spec->loopback.amplist = alc882_loopbacks;
9842#endif 9386#endif
9843 codec->proc_widget_hook = print_realtek_coef; 9387 codec->proc_widget_hook = print_realtek_coef;
9844 9388
9845 return 0; 9389 return 0;
9846} 9390}
9847 9391
9392
9848/* 9393/*
9849 * ALC262 support 9394 * ALC262 support
9850 */ 9395 */
@@ -17546,23 +17091,23 @@ static struct hda_codec_preset snd_hda_preset_realtek[] = {
17546 { .id = 0x10ec0861, .name = "ALC861", .patch = patch_alc861 }, 17091 { .id = 0x10ec0861, .name = "ALC861", .patch = patch_alc861 },
17547 { .id = 0x10ec0862, .name = "ALC861-VD", .patch = patch_alc861vd }, 17092 { .id = 0x10ec0862, .name = "ALC861-VD", .patch = patch_alc861vd },
17548 { .id = 0x10ec0662, .rev = 0x100002, .name = "ALC662 rev2", 17093 { .id = 0x10ec0662, .rev = 0x100002, .name = "ALC662 rev2",
17549 .patch = patch_alc883 }, 17094 .patch = patch_alc882 },
17550 { .id = 0x10ec0662, .rev = 0x100101, .name = "ALC662 rev1", 17095 { .id = 0x10ec0662, .rev = 0x100101, .name = "ALC662 rev1",
17551 .patch = patch_alc662 }, 17096 .patch = patch_alc662 },
17552 { .id = 0x10ec0663, .name = "ALC663", .patch = patch_alc662 }, 17097 { .id = 0x10ec0663, .name = "ALC663", .patch = patch_alc662 },
17553 { .id = 0x10ec0880, .name = "ALC880", .patch = patch_alc880 }, 17098 { .id = 0x10ec0880, .name = "ALC880", .patch = patch_alc880 },
17554 { .id = 0x10ec0882, .name = "ALC882", .patch = patch_alc882 }, 17099 { .id = 0x10ec0882, .name = "ALC882", .patch = patch_alc882 },
17555 { .id = 0x10ec0883, .name = "ALC883", .patch = patch_alc883 }, 17100 { .id = 0x10ec0883, .name = "ALC883", .patch = patch_alc882 },
17556 { .id = 0x10ec0885, .rev = 0x100101, .name = "ALC889A", 17101 { .id = 0x10ec0885, .rev = 0x100101, .name = "ALC889A",
17557 .patch = patch_alc882 }, /* should be patch_alc883() in future */ 17102 .patch = patch_alc882 },
17558 { .id = 0x10ec0885, .rev = 0x100103, .name = "ALC889A", 17103 { .id = 0x10ec0885, .rev = 0x100103, .name = "ALC889A",
17559 .patch = patch_alc882 }, /* should be patch_alc883() in future */ 17104 .patch = patch_alc882 },
17560 { .id = 0x10ec0885, .name = "ALC885", .patch = patch_alc882 }, 17105 { .id = 0x10ec0885, .name = "ALC885", .patch = patch_alc882 },
17561 { .id = 0x10ec0887, .name = "ALC887", .patch = patch_alc883 }, 17106 { .id = 0x10ec0887, .name = "ALC887", .patch = patch_alc882 },
17562 { .id = 0x10ec0888, .rev = 0x100101, .name = "ALC1200", 17107 { .id = 0x10ec0888, .rev = 0x100101, .name = "ALC1200",
17563 .patch = patch_alc883 }, 17108 .patch = patch_alc882 },
17564 { .id = 0x10ec0888, .name = "ALC888", .patch = patch_alc883 }, 17109 { .id = 0x10ec0888, .name = "ALC888", .patch = patch_alc882 },
17565 { .id = 0x10ec0889, .name = "ALC889", .patch = patch_alc883 }, 17110 { .id = 0x10ec0889, .name = "ALC889", .patch = patch_alc882 },
17566 {} /* terminator */ 17111 {} /* terminator */
17567}; 17112};
17568 17113