]>
Commit | Line | Data |
---|---|---|
00e5a55c BS |
1 | From: Takashi Iwai <tiwai@suse.de> |
2 | Subject: ALSA: hda - Realtek codec updates | |
3 | Patch-mainline: 2.6.28-rc1 | |
4 | References: bnc#418181, bnc#417736, bnc#399289, bnc#341339 | |
5 | ||
6 | A pile of updates for Realtek codecs: | |
7 | - DC7600 model | |
8 | - ALC262 Toshiba laptop fixes | |
9 | - Acer Aspire-one support | |
10 | - Support of ALC66x ASUS boards | |
11 | - Support of ALC883 Lenovo and ASUS boards | |
12 | - Fix ALC260 auto-probe bugs | |
13 | - Fix resume with a broken BIOS | |
14 | ||
15 | Signed-off-by: Takashi Iwai <tiwai@suse.de> | |
16 | ||
17 | --- | |
18 | --- | |
19 | Documentation/sound/alsa/ALSA-Configuration.txt | 17 | |
20 | sound/pci/hda/patch_realtek.c | 1881 ++++++++++++++++++++---- | |
21 | 2 files changed, 1660 insertions(+), 238 deletions(-) | |
22 | ||
23 | --- a/Documentation/sound/alsa/ALSA-Configuration.txt | |
24 | +++ b/Documentation/sound/alsa/ALSA-Configuration.txt | |
25 | @@ -809,6 +809,7 @@ Prior to version 0.9.0rc4 options had a | |
26 | ALC260 | |
27 | hp HP machines | |
28 | hp-3013 HP machines (3013-variant) | |
29 | + hp-dc7600 HP DC7600 | |
30 | fujitsu Fujitsu S7020 | |
31 | acer Acer TravelMate | |
32 | will Will laptops (PB V7900) | |
33 | @@ -830,8 +831,11 @@ Prior to version 0.9.0rc4 options had a | |
34 | hippo Hippo (ATI) with jack detection, Sony UX-90s | |
35 | hippo_1 Hippo (Benq) with jack detection | |
36 | sony-assamd Sony ASSAMD | |
37 | + toshiba-s06 Toshiba S06 | |
38 | + toshiba-rx1 Toshiba RX1 | |
39 | ultra Samsung Q1 Ultra Vista model | |
40 | lenovo-3000 Lenovo 3000 y410 | |
41 | + nec NEC Versa S9100 | |
42 | basic fixed pin assignment w/o SPDIF | |
43 | auto auto-config reading BIOS (default) | |
44 | ||
45 | @@ -840,6 +844,7 @@ Prior to version 0.9.0rc4 options had a | |
46 | 3stack 3-stack model | |
47 | toshiba Toshiba A205 | |
48 | acer Acer laptops | |
49 | + acer-aspire Acer Aspire One | |
50 | dell Dell OEM laptops (Vostro 1200) | |
51 | zepto Zepto laptops | |
52 | test for testing/debugging purpose, almost all controls can | |
53 | @@ -849,6 +854,9 @@ Prior to version 0.9.0rc4 options had a | |
54 | ||
55 | ALC269 | |
56 | basic Basic preset | |
57 | + quanta Quanta FL1 | |
58 | + eeepc-p703 ASUS Eeepc P703 P900A | |
59 | + eeepc-p901 ASUS Eeepc P901 S101 | |
60 | ||
61 | ALC662/663 | |
62 | 3stack-dig 3-stack (2-channel) with SPDIF | |
63 | @@ -858,10 +866,17 @@ Prior to version 0.9.0rc4 options had a | |
64 | lenovo-101e Lenovo laptop | |
65 | eeepc-p701 ASUS Eeepc P701 | |
66 | eeepc-ep20 ASUS Eeepc EP20 | |
67 | + ecs ECS/Foxconn mobo | |
68 | m51va ASUS M51VA | |
69 | g71v ASUS G71V | |
70 | h13 ASUS H13 | |
71 | g50v ASUS G50V | |
72 | + asus-mode1 ASUS | |
73 | + asus-mode2 ASUS | |
74 | + asus-mode3 ASUS | |
75 | + asus-mode4 ASUS | |
76 | + asus-mode5 ASUS | |
77 | + asus-mode6 ASUS | |
78 | auto auto-config reading BIOS (default) | |
79 | ||
80 | ALC882/885 | |
81 | @@ -893,12 +908,14 @@ Prior to version 0.9.0rc4 options had a | |
82 | lenovo-101e Lenovo 101E | |
83 | lenovo-nb0763 Lenovo NB0763 | |
84 | lenovo-ms7195-dig Lenovo MS7195 | |
85 | + lenovo-sky Lenovo Sky | |
86 | haier-w66 Haier W66 | |
87 | 3stack-hp HP machines with 3stack (Lucknow, Samba boards) | |
88 | 6stack-dell Dell machines with 6stack (Inspiron 530) | |
89 | mitac Mitac 8252D | |
90 | clevo-m720 Clevo M720 laptop series | |
91 | fujitsu-pi2515 Fujitsu AMILO Pi2515 | |
92 | + 3stack-6ch-intel Intel DG33* boards | |
93 | auto auto-config reading BIOS (default) | |
94 | ||
95 | ALC861/660 | |
96 | --- a/sound/pci/hda/patch_realtek.c | |
97 | +++ b/sound/pci/hda/patch_realtek.c | |
98 | @@ -72,6 +72,7 @@ enum { | |
99 | enum { | |
100 | ALC260_BASIC, | |
101 | ALC260_HP, | |
102 | + ALC260_HP_DC7600, | |
103 | ALC260_HP_3013, | |
104 | ALC260_FUJITSU_S702X, | |
105 | ALC260_ACER, | |
106 | @@ -101,6 +102,8 @@ enum { | |
107 | ALC262_ULTRA, | |
108 | ALC262_LENOVO_3000, | |
109 | ALC262_NEC, | |
110 | + ALC262_TOSHIBA_S06, | |
111 | + ALC262_TOSHIBA_RX1, | |
112 | ALC262_AUTO, | |
113 | ALC262_MODEL_LAST /* last tag */ | |
114 | }; | |
115 | @@ -111,6 +114,7 @@ enum { | |
116 | ALC268_3ST, | |
117 | ALC268_TOSHIBA, | |
118 | ALC268_ACER, | |
119 | + ALC268_ACER_ASPIRE_ONE, | |
120 | ALC268_DELL, | |
121 | ALC268_ZEPTO, | |
122 | #ifdef CONFIG_SND_DEBUG | |
123 | @@ -123,6 +127,7 @@ enum { | |
124 | /* ALC269 models */ | |
125 | enum { | |
126 | ALC269_BASIC, | |
127 | + ALC269_QUANTA_FL1, | |
128 | ALC269_ASUS_EEEPC_P703, | |
129 | ALC269_ASUS_EEEPC_P901, | |
130 | ALC269_AUTO, | |
131 | @@ -170,6 +175,13 @@ enum { | |
132 | ALC663_ASUS_G71V, | |
133 | ALC663_ASUS_H13, | |
134 | ALC663_ASUS_G50V, | |
135 | + ALC662_ECS, | |
136 | + ALC663_ASUS_MODE1, | |
137 | + ALC662_ASUS_MODE2, | |
138 | + ALC663_ASUS_MODE3, | |
139 | + ALC663_ASUS_MODE4, | |
140 | + ALC663_ASUS_MODE5, | |
141 | + ALC663_ASUS_MODE6, | |
142 | ALC662_AUTO, | |
143 | ALC662_MODEL_LAST, | |
144 | }; | |
145 | @@ -201,18 +213,21 @@ enum { | |
146 | ALC883_ACER, | |
147 | ALC883_ACER_ASPIRE, | |
148 | ALC883_MEDION, | |
149 | - ALC883_MEDION_MD2, | |
150 | + ALC883_MEDION_MD2, | |
151 | ALC883_LAPTOP_EAPD, | |
152 | ALC883_LENOVO_101E_2ch, | |
153 | ALC883_LENOVO_NB0763, | |
154 | ALC888_LENOVO_MS7195_DIG, | |
155 | - ALC883_HAIER_W66, | |
156 | + ALC888_LENOVO_SKY, | |
157 | + ALC883_HAIER_W66, | |
158 | ALC888_3ST_HP, | |
159 | ALC888_6ST_DELL, | |
160 | ALC883_MITAC, | |
161 | ALC883_CLEVO_M720, | |
162 | ALC883_FUJITSU_PI2515, | |
163 | ALC883_3ST_6ch_INTEL, | |
164 | + ALC888_ASUS_M90V, | |
165 | + ALC888_ASUS_EEE1601, | |
166 | ALC883_AUTO, | |
167 | ALC883_MODEL_LAST, | |
168 | }; | |
169 | @@ -406,7 +421,7 @@ static int alc_ch_mode_put(struct snd_kc | |
170 | ||
171 | /* | |
172 | * Control the mode of pin widget settings via the mixer. "pc" is used | |
173 | - * instead of "%" to avoid consequences of accidently treating the % as | |
174 | + * instead of "%" to avoid consequences of accidently treating the % as | |
175 | * being part of a format specifier. Maximum allowed length of a value is | |
176 | * 63 characters plus NULL terminator. | |
177 | * | |
178 | @@ -437,7 +452,7 @@ static unsigned char alc_pin_mode_values | |
179 | #define ALC_PIN_DIR_IN_NOMICBIAS 0x03 | |
180 | #define ALC_PIN_DIR_INOUT_NOMICBIAS 0x04 | |
181 | ||
182 | -/* Info about the pin modes supported by the different pin direction modes. | |
183 | +/* Info about the pin modes supported by the different pin direction modes. | |
184 | * For each direction the minimum and maximum values are given. | |
185 | */ | |
186 | static signed char alc_pin_mode_dir_info[5][2] = { | |
187 | @@ -510,7 +525,7 @@ static int alc_pin_mode_put(struct snd_k | |
188 | AC_VERB_SET_PIN_WIDGET_CONTROL, | |
189 | alc_pin_mode_values[val]); | |
190 | ||
191 | - /* Also enable the retasking pin's input/output as required | |
192 | + /* Also enable the retasking pin's input/output as required | |
193 | * for the requested pin mode. Enum values of 2 or less are | |
194 | * input modes. | |
195 | * | |
196 | @@ -715,7 +730,7 @@ static void setup_preset(struct alc_spec | |
197 | i++) | |
198 | spec->init_verbs[spec->num_init_verbs++] = | |
199 | preset->init_verbs[i]; | |
200 | - | |
201 | + | |
202 | spec->channel_mode = preset->channel_mode; | |
203 | spec->num_channel_mode = preset->num_channel_mode; | |
204 | spec->need_dac_fix = preset->need_dac_fix; | |
205 | @@ -726,7 +741,7 @@ static void setup_preset(struct alc_spec | |
206 | spec->multiout.dac_nids = preset->dac_nids; | |
207 | spec->multiout.dig_out_nid = preset->dig_out_nid; | |
208 | spec->multiout.hp_nid = preset->hp_nid; | |
209 | - | |
210 | + | |
211 | spec->num_mux_defs = preset->num_mux_defs; | |
212 | if (!spec->num_mux_defs) | |
213 | spec->num_mux_defs = 1; | |
214 | @@ -814,6 +829,27 @@ static void alc_sku_automute(struct hda_ | |
215 | spec->jack_present ? 0 : PIN_OUT); | |
216 | } | |
217 | ||
218 | +static void alc_mic_automute(struct hda_codec *codec) | |
219 | +{ | |
220 | + struct alc_spec *spec = codec->spec; | |
221 | + unsigned int present; | |
222 | + unsigned int mic_nid = spec->autocfg.input_pins[AUTO_PIN_MIC]; | |
223 | + unsigned int fmic_nid = spec->autocfg.input_pins[AUTO_PIN_FRONT_MIC]; | |
224 | + unsigned int mix_nid = spec->capsrc_nids[0]; | |
225 | + unsigned int capsrc_idx_mic, capsrc_idx_fmic; | |
226 | + | |
227 | + capsrc_idx_mic = mic_nid - 0x18; | |
228 | + capsrc_idx_fmic = fmic_nid - 0x18; | |
229 | + present = snd_hda_codec_read(codec, mic_nid, 0, | |
230 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
231 | + snd_hda_codec_write(codec, mix_nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
232 | + 0x7000 | (capsrc_idx_mic << 8) | (present ? 0 : 0x80)); | |
233 | + snd_hda_codec_write(codec, mix_nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
234 | + 0x7000 | (capsrc_idx_fmic << 8) | (present ? 0x80 : 0)); | |
235 | + snd_hda_codec_amp_stereo(codec, 0x0b, HDA_INPUT, capsrc_idx_fmic, | |
236 | + HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0); | |
237 | +} | |
238 | + | |
239 | /* unsolicited event for HP jack sensing */ | |
240 | static void alc_sku_unsol_event(struct hda_codec *codec, unsigned int res) | |
241 | { | |
242 | @@ -821,10 +857,17 @@ static void alc_sku_unsol_event(struct h | |
243 | res >>= 28; | |
244 | else | |
245 | res >>= 26; | |
246 | - if (res != ALC880_HP_EVENT) | |
247 | - return; | |
248 | + if (res == ALC880_HP_EVENT) | |
249 | + alc_sku_automute(codec); | |
250 | + | |
251 | + if (res == ALC880_MIC_EVENT) | |
252 | + alc_mic_automute(codec); | |
253 | +} | |
254 | ||
255 | +static void alc_inithook(struct hda_codec *codec) | |
256 | +{ | |
257 | alc_sku_automute(codec); | |
258 | + alc_mic_automute(codec); | |
259 | } | |
260 | ||
261 | /* additional initialization for ALC888 variants */ | |
262 | @@ -863,7 +906,7 @@ static void alc_subsystem_id(struct hda_ | |
263 | if ((ass != codec->bus->pci->subsystem_device) && (ass & 1)) | |
264 | goto do_sku; | |
265 | ||
266 | - /* | |
267 | + /* | |
268 | * 31~30 : port conetcivity | |
269 | * 29~21 : reserve | |
270 | * 20 : PCBEEP input | |
271 | @@ -956,7 +999,7 @@ do_sku: | |
272 | tmp = snd_hda_codec_read(codec, 0x20, 0, | |
273 | AC_VERB_GET_PROC_COEF, 0); | |
274 | snd_hda_codec_write(codec, 0x20, 0, | |
275 | - AC_VERB_SET_COEF_INDEX, 7); | |
276 | + AC_VERB_SET_COEF_INDEX, 7); | |
277 | snd_hda_codec_write(codec, 0x20, 0, | |
278 | AC_VERB_SET_PROC_COEF, | |
279 | tmp | 0x2010); | |
280 | @@ -971,7 +1014,7 @@ do_sku: | |
281 | tmp = snd_hda_codec_read(codec, 0x20, 0, | |
282 | AC_VERB_GET_PROC_COEF, 0); | |
283 | snd_hda_codec_write(codec, 0x20, 0, | |
284 | - AC_VERB_SET_COEF_INDEX, 7); | |
285 | + AC_VERB_SET_COEF_INDEX, 7); | |
286 | snd_hda_codec_write(codec, 0x20, 0, | |
287 | AC_VERB_SET_PROC_COEF, | |
288 | tmp | 0x3000); | |
289 | @@ -980,7 +1023,7 @@ do_sku: | |
290 | default: | |
291 | break; | |
292 | } | |
293 | - | |
294 | + | |
295 | /* is laptop or Desktop and enable the function "Mute internal speaker | |
296 | * when the external headphone out jack is plugged" | |
297 | */ | |
298 | @@ -1012,10 +1055,18 @@ do_sku: | |
299 | else | |
300 | return; | |
301 | } | |
302 | + if (spec->autocfg.hp_pins[0]) | |
303 | + snd_hda_codec_write(codec, spec->autocfg.hp_pins[0], 0, | |
304 | + AC_VERB_SET_UNSOLICITED_ENABLE, | |
305 | + AC_USRSP_EN | ALC880_HP_EVENT); | |
306 | + | |
307 | + if (spec->autocfg.input_pins[AUTO_PIN_MIC] && | |
308 | + spec->autocfg.input_pins[AUTO_PIN_FRONT_MIC]) | |
309 | + snd_hda_codec_write(codec, | |
310 | + spec->autocfg.input_pins[AUTO_PIN_MIC], 0, | |
311 | + AC_VERB_SET_UNSOLICITED_ENABLE, | |
312 | + AC_USRSP_EN | ALC880_MIC_EVENT); | |
313 | ||
314 | - snd_hda_codec_write(codec, spec->autocfg.hp_pins[0], 0, | |
315 | - AC_VERB_SET_UNSOLICITED_ENABLE, | |
316 | - AC_USRSP_EN | ALC880_HP_EVENT); | |
317 | spec->unsol_event = alc_sku_unsol_event; | |
318 | } | |
319 | ||
320 | @@ -1306,7 +1357,7 @@ static struct snd_kcontrol_new alc880_si | |
321 | * | |
322 | * The system also has a pair of internal speakers, and a headphone jack. | |
323 | * These are both connected to Line2 on the codec, hence to DAC 02. | |
324 | - * | |
325 | + * | |
326 | * There is a variable resistor to control the speaker or headphone | |
327 | * volume. This is a hardware-only device without a software API. | |
328 | * | |
329 | @@ -1834,7 +1885,7 @@ static struct hda_verb alc880_pin_6stack | |
330 | {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
331 | {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
332 | {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
333 | - | |
334 | + | |
335 | { } | |
336 | }; | |
337 | ||
338 | @@ -1879,7 +1930,7 @@ static struct hda_verb alc880_uniwill_in | |
339 | ||
340 | /* | |
341 | * Uniwill P53 | |
342 | -* HP = 0x14, InternalSpeaker = 0x15, mic = 0x19, | |
343 | +* HP = 0x14, InternalSpeaker = 0x15, mic = 0x19, | |
344 | */ | |
345 | static struct hda_verb alc880_uniwill_p53_init_verbs[] = { | |
346 | {0x13, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */ | |
347 | @@ -1978,7 +2029,7 @@ static void alc880_uniwill_p53_hp_automu | |
348 | static void alc880_uniwill_p53_dcvol_automute(struct hda_codec *codec) | |
349 | { | |
350 | unsigned int present; | |
351 | - | |
352 | + | |
353 | present = snd_hda_codec_read(codec, 0x21, 0, | |
354 | AC_VERB_GET_VOLUME_KNOB_CONTROL, 0); | |
355 | present &= HDA_AMP_VOLMASK; | |
356 | @@ -2060,7 +2111,7 @@ static struct hda_verb alc880_pin_asus_i | |
357 | {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
358 | {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
359 | {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
360 | - | |
361 | + | |
362 | { } | |
363 | }; | |
364 | ||
365 | @@ -2677,6 +2728,8 @@ static int alc_build_pcms(struct hda_cod | |
366 | info->stream[SNDRV_PCM_STREAM_CAPTURE] = *(spec->stream_digital_capture); | |
367 | info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->dig_in_nid; | |
368 | } | |
369 | + /* FIXME: do we need this for all Realtek codec models? */ | |
370 | + codec->spdif_status_reset = 1; | |
371 | } | |
372 | ||
373 | /* If the use of more than one ADC is requested for the current | |
374 | @@ -3754,7 +3807,7 @@ static void alc880_auto_init_multi_out(s | |
375 | { | |
376 | struct alc_spec *spec = codec->spec; | |
377 | int i; | |
378 | - | |
379 | + | |
380 | alc_subsystem_id(codec, 0x15, 0x1b, 0x14); | |
381 | for (i = 0; i < spec->autocfg.line_outs; i++) { | |
382 | hda_nid_t nid = spec->autocfg.line_out_pins[i]; | |
383 | @@ -3859,7 +3912,7 @@ static void alc880_auto_init(struct hda_ | |
384 | alc880_auto_init_extra_out(codec); | |
385 | alc880_auto_init_analog_input(codec); | |
386 | if (spec->unsol_event) | |
387 | - alc_sku_automute(codec); | |
388 | + alc_inithook(codec); | |
389 | } | |
390 | ||
391 | /* | |
392 | @@ -4196,6 +4249,33 @@ static struct snd_kcontrol_new alc260_hp | |
393 | { } /* end */ | |
394 | }; | |
395 | ||
396 | +static struct hda_bind_ctls alc260_dc7600_bind_master_vol = { | |
397 | + .ops = &snd_hda_bind_vol, | |
398 | + .values = { | |
399 | + HDA_COMPOSE_AMP_VAL(0x08, 3, 0, HDA_OUTPUT), | |
400 | + HDA_COMPOSE_AMP_VAL(0x09, 3, 0, HDA_OUTPUT), | |
401 | + HDA_COMPOSE_AMP_VAL(0x0a, 3, 0, HDA_OUTPUT), | |
402 | + 0 | |
403 | + }, | |
404 | +}; | |
405 | + | |
406 | +static struct hda_bind_ctls alc260_dc7600_bind_switch = { | |
407 | + .ops = &snd_hda_bind_sw, | |
408 | + .values = { | |
409 | + HDA_COMPOSE_AMP_VAL(0x11, 3, 0, HDA_OUTPUT), | |
410 | + HDA_COMPOSE_AMP_VAL(0x15, 3, 0, HDA_OUTPUT), | |
411 | + 0 | |
412 | + }, | |
413 | +}; | |
414 | + | |
415 | +static struct snd_kcontrol_new alc260_hp_dc7600_mixer[] = { | |
416 | + HDA_BIND_VOL("Master Playback Volume", &alc260_dc7600_bind_master_vol), | |
417 | + HDA_BIND_SW("LineOut Playback Switch", &alc260_dc7600_bind_switch), | |
418 | + HDA_CODEC_MUTE("Speaker Playback Switch", 0x0f, 0x0, HDA_OUTPUT), | |
419 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x10, 0x0, HDA_OUTPUT), | |
420 | + { } /* end */ | |
421 | +}; | |
422 | + | |
423 | static struct hda_verb alc260_hp_3013_unsol_verbs[] = { | |
424 | {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
425 | {}, | |
426 | @@ -4219,7 +4299,30 @@ static void alc260_hp_3013_unsol_event(s | |
427 | alc260_hp_3013_automute(codec); | |
428 | } | |
429 | ||
430 | -/* Fujitsu S702x series laptops. ALC260 pin usage: Mic/Line jack = 0x12, | |
431 | +static void alc260_hp_3012_automute(struct hda_codec *codec) | |
432 | +{ | |
433 | + unsigned int present, bits; | |
434 | + | |
435 | + present = snd_hda_codec_read(codec, 0x10, 0, | |
436 | + AC_VERB_GET_PIN_SENSE, 0) & AC_PINSENSE_PRESENCE; | |
437 | + | |
438 | + bits = present ? 0 : PIN_OUT; | |
439 | + snd_hda_codec_write(codec, 0x0f, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
440 | + bits); | |
441 | + snd_hda_codec_write(codec, 0x11, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
442 | + bits); | |
443 | + snd_hda_codec_write(codec, 0x15, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
444 | + bits); | |
445 | +} | |
446 | + | |
447 | +static void alc260_hp_3012_unsol_event(struct hda_codec *codec, | |
448 | + unsigned int res) | |
449 | +{ | |
450 | + if ((res >> 26) == ALC880_HP_EVENT) | |
451 | + alc260_hp_3012_automute(codec); | |
452 | +} | |
453 | + | |
454 | +/* Fujitsu S702x series laptops. ALC260 pin usage: Mic/Line jack = 0x12, | |
455 | * HP jack = 0x14, CD audio = 0x16, internal speaker = 0x10. | |
456 | */ | |
457 | static struct snd_kcontrol_new alc260_fujitsu_mixer[] = { | |
458 | @@ -4550,7 +4653,7 @@ static struct hda_verb alc260_fujitsu_in | |
459 | {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
460 | {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
461 | ||
462 | - /* Ensure Line1 pin widget takes its input from the OUT1 sum bus | |
463 | + /* Ensure Line1 pin widget takes its input from the OUT1 sum bus | |
464 | * when acting as an output. | |
465 | */ | |
466 | {0x0d, AC_VERB_SET_CONNECT_SEL, 0}, | |
467 | @@ -4575,14 +4678,14 @@ static struct hda_verb alc260_fujitsu_in | |
468 | * stage. | |
469 | */ | |
470 | {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
471 | - /* Unmute input buffer of pin widget used for Line-in (no equiv | |
472 | + /* Unmute input buffer of pin widget used for Line-in (no equiv | |
473 | * mixer ctrl) | |
474 | */ | |
475 | {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
476 | ||
477 | /* Mute capture amp left and right */ | |
478 | {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
479 | - /* Set ADC connection select to match default mixer setting - line | |
480 | + /* Set ADC connection select to match default mixer setting - line | |
481 | * in (on mic1 pin) | |
482 | */ | |
483 | {0x04, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
484 | @@ -4636,7 +4739,7 @@ static struct hda_verb alc260_acer_init_ | |
485 | {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
486 | {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
487 | ||
488 | - /* Ensure Mic1 and Line1 pin widgets take input from the OUT1 sum | |
489 | + /* Ensure Mic1 and Line1 pin widgets take input from the OUT1 sum | |
490 | * bus when acting as outputs. | |
491 | */ | |
492 | {0x0b, AC_VERB_SET_CONNECT_SEL, 0}, | |
493 | @@ -4747,6 +4850,20 @@ static void alc260_replacer_672v_unsol_e | |
494 | alc260_replacer_672v_automute(codec); | |
495 | } | |
496 | ||
497 | +static struct hda_verb alc260_hp_dc7600_verbs[] = { | |
498 | + {0x05, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
499 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
500 | + {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
501 | + {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
502 | + {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
503 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
504 | + {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
505 | + {0x10, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
506 | + {0x11, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
507 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
508 | + {} | |
509 | +}; | |
510 | + | |
511 | /* Test configuration for debugging, modelled after the ALC880 test | |
512 | * configuration. | |
513 | */ | |
514 | @@ -4758,7 +4875,7 @@ static hda_nid_t alc260_test_adc_nids[2] | |
515 | 0x04, 0x05, | |
516 | }; | |
517 | /* For testing the ALC260, each input MUX needs its own definition since | |
518 | - * the signal assignments are different. This assumes that the first ADC | |
519 | + * the signal assignments are different. This assumes that the first ADC | |
520 | * is NID 0x04. | |
521 | */ | |
522 | static struct hda_input_mux alc260_test_capture_sources[2] = { | |
523 | @@ -4841,7 +4958,7 @@ static struct snd_kcontrol_new alc260_te | |
524 | ||
525 | /* Switches to allow the digital IO pins to be enabled. The datasheet | |
526 | * is ambigious as to which NID is which; testing on laptops which | |
527 | - * make this output available should provide clarification. | |
528 | + * make this output available should provide clarification. | |
529 | */ | |
530 | ALC_SPDIF_CTRL_SWITCH("SPDIF Playback Switch", 0x03, 0x01), | |
531 | ALC_SPDIF_CTRL_SWITCH("SPDIF Capture Switch", 0x06, 0x01), | |
532 | @@ -4877,7 +4994,7 @@ static struct hda_verb alc260_test_init_ | |
533 | {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
534 | {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0}, | |
535 | ||
536 | - /* Ensure mic1, mic2, line1 and line2 pin widgets take input from the | |
537 | + /* Ensure mic1, mic2, line1 and line2 pin widgets take input from the | |
538 | * OUT1 sum bus when acting as an output. | |
539 | */ | |
540 | {0x0b, AC_VERB_SET_CONNECT_SEL, 0}, | |
541 | @@ -4948,7 +5065,7 @@ static struct hda_verb alc260_test_init_ | |
542 | */ | |
543 | ||
544 | static int alc260_add_playback_controls(struct alc_spec *spec, hda_nid_t nid, | |
545 | - const char *pfx) | |
546 | + const char *pfx, int *vol_bits) | |
547 | { | |
548 | hda_nid_t nid_vol; | |
549 | unsigned long vol_val, sw_val; | |
550 | @@ -4969,11 +5086,15 @@ static int alc260_add_playback_controls( | |
551 | sw_val = HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT); | |
552 | } else | |
553 | return 0; /* N/A */ | |
554 | - | |
555 | - snprintf(name, sizeof(name), "%s Playback Volume", pfx); | |
556 | - err = add_control(spec, ALC_CTL_WIDGET_VOL, name, vol_val); | |
557 | - if (err < 0) | |
558 | - return err; | |
559 | + | |
560 | + if (!(*vol_bits & (1 << nid_vol))) { | |
561 | + /* first control for the volume widget */ | |
562 | + snprintf(name, sizeof(name), "%s Playback Volume", pfx); | |
563 | + err = add_control(spec, ALC_CTL_WIDGET_VOL, name, vol_val); | |
564 | + if (err < 0) | |
565 | + return err; | |
566 | + *vol_bits |= (1 << nid_vol); | |
567 | + } | |
568 | snprintf(name, sizeof(name), "%s Playback Switch", pfx); | |
569 | err = add_control(spec, ALC_CTL_WIDGET_MUTE, name, sw_val); | |
570 | if (err < 0) | |
571 | @@ -4987,6 +5108,7 @@ static int alc260_auto_create_multi_out_ | |
572 | { | |
573 | hda_nid_t nid; | |
574 | int err; | |
575 | + int vols = 0; | |
576 | ||
577 | spec->multiout.num_dacs = 1; | |
578 | spec->multiout.dac_nids = spec->private_dac_nids; | |
579 | @@ -4994,21 +5116,22 @@ static int alc260_auto_create_multi_out_ | |
580 | ||
581 | nid = cfg->line_out_pins[0]; | |
582 | if (nid) { | |
583 | - err = alc260_add_playback_controls(spec, nid, "Front"); | |
584 | + err = alc260_add_playback_controls(spec, nid, "Front", &vols); | |
585 | if (err < 0) | |
586 | return err; | |
587 | } | |
588 | ||
589 | nid = cfg->speaker_pins[0]; | |
590 | if (nid) { | |
591 | - err = alc260_add_playback_controls(spec, nid, "Speaker"); | |
592 | + err = alc260_add_playback_controls(spec, nid, "Speaker", &vols); | |
593 | if (err < 0) | |
594 | return err; | |
595 | } | |
596 | ||
597 | nid = cfg->hp_pins[0]; | |
598 | if (nid) { | |
599 | - err = alc260_add_playback_controls(spec, nid, "Headphone"); | |
600 | + err = alc260_add_playback_controls(spec, nid, "Headphone", | |
601 | + &vols); | |
602 | if (err < 0) | |
603 | return err; | |
604 | } | |
605 | @@ -5075,7 +5198,7 @@ static void alc260_auto_init_multi_out(s | |
606 | int pin_type = get_pin_type(spec->autocfg.line_out_type); | |
607 | alc260_auto_set_output_and_unmute(codec, nid, pin_type, 0); | |
608 | } | |
609 | - | |
610 | + | |
611 | nid = spec->autocfg.speaker_pins[0]; | |
612 | if (nid) | |
613 | alc260_auto_set_output_and_unmute(codec, nid, PIN_OUT, 0); | |
614 | @@ -5117,7 +5240,7 @@ static struct hda_verb alc260_volume_ini | |
615 | {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
616 | {0x05, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
617 | {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
618 | - | |
619 | + | |
620 | /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback | |
621 | * mixer widget | |
622 | * Note: PASD motherboards uses the Line In 2 as the input for | |
623 | @@ -5146,7 +5269,7 @@ static struct hda_verb alc260_volume_ini | |
624 | {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
625 | {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
626 | {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
627 | - | |
628 | + | |
629 | { } | |
630 | }; | |
631 | ||
632 | @@ -5207,7 +5330,7 @@ static void alc260_auto_init(struct hda_ | |
633 | alc260_auto_init_multi_out(codec); | |
634 | alc260_auto_init_analog_input(codec); | |
635 | if (spec->unsol_event) | |
636 | - alc_sku_automute(codec); | |
637 | + alc_inithook(codec); | |
638 | } | |
639 | ||
640 | #ifdef CONFIG_SND_HDA_POWER_SAVE | |
641 | @@ -5228,6 +5351,7 @@ static const char *alc260_models[ALC260_ | |
642 | [ALC260_BASIC] = "basic", | |
643 | [ALC260_HP] = "hp", | |
644 | [ALC260_HP_3013] = "hp-3013", | |
645 | + [ALC260_HP_DC7600] = "hp-dc7600", | |
646 | [ALC260_FUJITSU_S702X] = "fujitsu", | |
647 | [ALC260_ACER] = "acer", | |
648 | [ALC260_WILL] = "will", | |
649 | @@ -5245,7 +5369,7 @@ static struct snd_pci_quirk alc260_cfg_t | |
650 | SND_PCI_QUIRK(0x103c, 0x280a, "HP d5750", ALC260_HP_3013), | |
651 | SND_PCI_QUIRK(0x103c, 0x3010, "HP", ALC260_HP_3013), | |
652 | SND_PCI_QUIRK(0x103c, 0x3011, "HP", ALC260_HP_3013), | |
653 | - SND_PCI_QUIRK(0x103c, 0x3012, "HP", ALC260_HP_3013), | |
654 | + SND_PCI_QUIRK(0x103c, 0x3012, "HP", ALC260_HP_DC7600), | |
655 | SND_PCI_QUIRK(0x103c, 0x3013, "HP", ALC260_HP_3013), | |
656 | SND_PCI_QUIRK(0x103c, 0x3014, "HP", ALC260_HP), | |
657 | SND_PCI_QUIRK(0x103c, 0x3015, "HP", ALC260_HP), | |
658 | @@ -5291,6 +5415,22 @@ static struct alc_config_preset alc260_p | |
659 | .unsol_event = alc260_hp_unsol_event, | |
660 | .init_hook = alc260_hp_automute, | |
661 | }, | |
662 | + [ALC260_HP_DC7600] = { | |
663 | + .mixers = { alc260_hp_dc7600_mixer, | |
664 | + alc260_input_mixer, | |
665 | + alc260_capture_alt_mixer }, | |
666 | + .init_verbs = { alc260_init_verbs, | |
667 | + alc260_hp_dc7600_verbs }, | |
668 | + .num_dacs = ARRAY_SIZE(alc260_dac_nids), | |
669 | + .dac_nids = alc260_dac_nids, | |
670 | + .num_adc_nids = ARRAY_SIZE(alc260_hp_adc_nids), | |
671 | + .adc_nids = alc260_hp_adc_nids, | |
672 | + .num_channel_mode = ARRAY_SIZE(alc260_modes), | |
673 | + .channel_mode = alc260_modes, | |
674 | + .input_mux = &alc260_capture_source, | |
675 | + .unsol_event = alc260_hp_3012_unsol_event, | |
676 | + .init_hook = alc260_hp_3012_automute, | |
677 | + }, | |
678 | [ALC260_HP_3013] = { | |
679 | .mixers = { alc260_hp_3013_mixer, | |
680 | alc260_input_mixer, | |
681 | @@ -6006,7 +6146,7 @@ static struct hda_verb alc882_targa_verb | |
682 | ||
683 | {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
684 | {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
685 | - | |
686 | + | |
687 | {0x18, AC_VERB_SET_CONNECT_SEL, 0x02}, /* mic/clfe */ | |
688 | {0x1a, AC_VERB_SET_CONNECT_SEL, 0x01}, /* line/surround */ | |
689 | {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */ | |
690 | @@ -6022,7 +6162,7 @@ static struct hda_verb alc882_targa_verb | |
691 | static void alc882_targa_automute(struct hda_codec *codec) | |
692 | { | |
693 | unsigned int present; | |
694 | - | |
695 | + | |
696 | present = snd_hda_codec_read(codec, 0x14, 0, | |
697 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
698 | snd_hda_codec_amp_stereo(codec, 0x1b, HDA_OUTPUT, 0, | |
699 | @@ -6048,7 +6188,7 @@ static struct hda_verb alc882_asus_a7j_v | |
700 | {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
701 | {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
702 | {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
703 | - | |
704 | + | |
705 | {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Front */ | |
706 | {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */ | |
707 | {0x16, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Front */ | |
708 | @@ -6066,7 +6206,7 @@ static struct hda_verb alc882_asus_a7m_v | |
709 | {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
710 | {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
711 | {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
712 | - | |
713 | + | |
714 | {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Front */ | |
715 | {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */ | |
716 | {0x16, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Front */ | |
717 | @@ -6392,7 +6532,7 @@ static struct alc_config_preset alc882_p | |
718 | .channel_mode = alc882_3ST_6ch_modes, | |
719 | .need_dac_fix = 1, | |
720 | .input_mux = &alc882_capture_source, | |
721 | - }, | |
722 | + }, | |
723 | [ALC882_ASUS_A7M] = { | |
724 | .mixers = { alc882_asus_a7m_mixer, alc882_chmode_mixer }, | |
725 | .init_verbs = { alc882_init_verbs, alc882_eapd_verbs, | |
726 | @@ -6405,14 +6545,14 @@ static struct alc_config_preset alc882_p | |
727 | .channel_mode = alc880_threestack_modes, | |
728 | .need_dac_fix = 1, | |
729 | .input_mux = &alc882_capture_source, | |
730 | - }, | |
731 | + }, | |
732 | }; | |
733 | ||
734 | ||
735 | /* | |
736 | * Pin config fixes | |
737 | */ | |
738 | -enum { | |
739 | +enum { | |
740 | PINFIX_ABIT_AW9D_MAX | |
741 | }; | |
742 | ||
743 | @@ -6600,7 +6740,7 @@ static void alc882_auto_init(struct hda_ | |
744 | alc882_auto_init_analog_input(codec); | |
745 | alc882_auto_init_input_src(codec); | |
746 | if (spec->unsol_event) | |
747 | - alc_sku_automute(codec); | |
748 | + alc_inithook(codec); | |
749 | } | |
750 | ||
751 | static int patch_alc883(struct hda_codec *codec); /* called in patch_alc882() */ | |
752 | @@ -6632,6 +6772,7 @@ static int patch_alc882(struct hda_codec | |
753 | break; | |
754 | case 0x106b00a0: /* MacBookPro3,1 - Another revision */ | |
755 | case 0x106b00a1: /* Macbook (might be wrong - PCI SSID?) */ | |
756 | + case 0x106b00a4: /* MacbookPro4,1 */ | |
757 | case 0x106b2c00: /* Macbook Pro rev3 */ | |
758 | case 0x106b3600: /* Macbook 3.1 */ | |
759 | case 0x106b3800: /* MacbookPro4,1 - latter revision */ | |
760 | @@ -6795,6 +6936,23 @@ static struct hda_input_mux alc883_fujit | |
761 | }, | |
762 | }; | |
763 | ||
764 | +static struct hda_input_mux alc883_lenovo_sky_capture_source = { | |
765 | + .num_items = 3, | |
766 | + .items = { | |
767 | + { "Mic", 0x0 }, | |
768 | + { "Front Mic", 0x1 }, | |
769 | + { "Line", 0x4 }, | |
770 | + }, | |
771 | +}; | |
772 | + | |
773 | +static struct hda_input_mux alc883_asus_eee1601_capture_source = { | |
774 | + .num_items = 2, | |
775 | + .items = { | |
776 | + { "Mic", 0x0 }, | |
777 | + { "Line", 0x2 }, | |
778 | + }, | |
779 | +}; | |
780 | + | |
781 | #define alc883_mux_enum_info alc_mux_enum_info | |
782 | #define alc883_mux_enum_get alc_mux_enum_get | |
783 | /* ALC883 has the ALC882-type input selection */ | |
784 | @@ -7109,13 +7267,11 @@ static struct snd_kcontrol_new alc883_3S | |
785 | HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x05, HDA_INPUT), | |
786 | HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT), | |
787 | HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT), | |
788 | - HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x09, 0x0, HDA_INPUT), | |
789 | - HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x09, 0x0, HDA_INPUT), | |
790 | { | |
791 | .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
792 | /* .name = "Capture Source", */ | |
793 | .name = "Input Source", | |
794 | - .count = 2, | |
795 | + .count = 1, | |
796 | .info = alc883_mux_enum_info, | |
797 | .get = alc883_mux_enum_get, | |
798 | .put = alc883_mux_enum_put, | |
799 | @@ -7333,7 +7489,7 @@ static struct snd_kcontrol_new alc883_me | |
800 | .put = alc883_mux_enum_put, | |
801 | }, | |
802 | { } /* end */ | |
803 | -}; | |
804 | +}; | |
805 | ||
806 | static struct snd_kcontrol_new alc883_acer_aspire_mixer[] = { | |
807 | HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | |
808 | @@ -7360,6 +7516,87 @@ static struct snd_kcontrol_new alc883_ac | |
809 | { } /* end */ | |
810 | }; | |
811 | ||
812 | +static struct snd_kcontrol_new alc888_lenovo_sky_mixer[] = { | |
813 | + HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | |
814 | + HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), | |
815 | + HDA_CODEC_VOLUME("Surround Playback Volume", 0x0e, 0x0, HDA_OUTPUT), | |
816 | + HDA_BIND_MUTE("Surround Playback Switch", 0x0e, 2, HDA_INPUT), | |
817 | + HDA_CODEC_VOLUME_MONO("Center Playback Volume", | |
818 | + 0x0d, 1, 0x0, HDA_OUTPUT), | |
819 | + HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0d, 2, 0x0, HDA_OUTPUT), | |
820 | + HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0d, 1, 2, HDA_INPUT), | |
821 | + HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0d, 2, 2, HDA_INPUT), | |
822 | + HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT), | |
823 | + HDA_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT), | |
824 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT), | |
825 | + HDA_CODEC_MUTE("iSpeaker Playback Switch", 0x1a, 0x0, HDA_OUTPUT), | |
826 | + HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT), | |
827 | + HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT), | |
828 | + HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT), | |
829 | + HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT), | |
830 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
831 | + HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
832 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
833 | + HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
834 | + HDA_CODEC_VOLUME("Front Mic Boost", 0x19, 0, HDA_INPUT), | |
835 | + HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
836 | + HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT), | |
837 | + HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT), | |
838 | + HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x09, 0x0, HDA_INPUT), | |
839 | + HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x09, 0x0, HDA_INPUT), | |
840 | + { | |
841 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
842 | + /* .name = "Capture Source", */ | |
843 | + .name = "Input Source", | |
844 | + .count = 2, | |
845 | + .info = alc883_mux_enum_info, | |
846 | + .get = alc883_mux_enum_get, | |
847 | + .put = alc883_mux_enum_put, | |
848 | + }, | |
849 | + { } /* end */ | |
850 | +}; | |
851 | + | |
852 | +static struct hda_bind_ctls alc883_bind_cap_vol = { | |
853 | + .ops = &snd_hda_bind_vol, | |
854 | + .values = { | |
855 | + HDA_COMPOSE_AMP_VAL(0x08, 3, 0, HDA_INPUT), | |
856 | + HDA_COMPOSE_AMP_VAL(0x09, 3, 0, HDA_INPUT), | |
857 | + 0 | |
858 | + }, | |
859 | +}; | |
860 | + | |
861 | +static struct hda_bind_ctls alc883_bind_cap_switch = { | |
862 | + .ops = &snd_hda_bind_sw, | |
863 | + .values = { | |
864 | + HDA_COMPOSE_AMP_VAL(0x08, 3, 0, HDA_INPUT), | |
865 | + HDA_COMPOSE_AMP_VAL(0x09, 3, 0, HDA_INPUT), | |
866 | + 0 | |
867 | + }, | |
868 | +}; | |
869 | + | |
870 | +static struct snd_kcontrol_new alc883_asus_eee1601_mixer[] = { | |
871 | + HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | |
872 | + HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT), | |
873 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
874 | + HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT), | |
875 | + HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT), | |
876 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
877 | + HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
878 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
879 | + HDA_BIND_VOL("Capture Volume", &alc883_bind_cap_vol), | |
880 | + HDA_BIND_SW("Capture Switch", &alc883_bind_cap_switch), | |
881 | + { | |
882 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
883 | + /* .name = "Capture Source", */ | |
884 | + .name = "Input Source", | |
885 | + .count = 1, | |
886 | + .info = alc883_mux_enum_info, | |
887 | + .get = alc883_mux_enum_get, | |
888 | + .put = alc883_mux_enum_put, | |
889 | + }, | |
890 | + { } /* end */ | |
891 | +}; | |
892 | + | |
893 | static struct snd_kcontrol_new alc883_chmode_mixer[] = { | |
894 | { | |
895 | .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
896 | @@ -7373,7 +7610,7 @@ static struct snd_kcontrol_new alc883_ch | |
897 | ||
898 | static struct hda_verb alc883_init_verbs[] = { | |
899 | /* ADC1: mute amp left and right */ | |
900 | - {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
901 | + {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
902 | {0x08, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
903 | /* ADC2: mute amp left and right */ | |
904 | {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
905 | @@ -7438,14 +7675,14 @@ static struct hda_verb alc883_init_verbs | |
906 | /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */ | |
907 | /* Input mixer2 */ | |
908 | {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
909 | - {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
910 | - {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)}, | |
911 | - {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)}, | |
912 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
913 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
914 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
915 | /* Input mixer3 */ | |
916 | {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
917 | - {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
918 | - {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)}, | |
919 | - {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)}, | |
920 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
921 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
922 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
923 | { } | |
924 | }; | |
925 | ||
926 | @@ -7545,7 +7782,7 @@ static struct hda_verb alc883_tagra_verb | |
927 | ||
928 | {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
929 | {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
930 | - | |
931 | + | |
932 | {0x18, AC_VERB_SET_CONNECT_SEL, 0x02}, /* mic/clfe */ | |
933 | {0x1a, AC_VERB_SET_CONNECT_SEL, 0x01}, /* line/surround */ | |
934 | {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */ | |
935 | @@ -7595,6 +7832,18 @@ static struct hda_verb alc883_haier_w66_ | |
936 | { } /* end */ | |
937 | }; | |
938 | ||
939 | +static struct hda_verb alc888_lenovo_sky_verbs[] = { | |
940 | + {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
941 | + {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
942 | + {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
943 | + {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
944 | + {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
945 | + {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
946 | + {0x1a, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
947 | + {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
948 | + { } /* end */ | |
949 | +}; | |
950 | + | |
951 | static struct hda_verb alc888_3st_hp_verbs[] = { | |
952 | {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Front: output 0 (0x0c) */ | |
953 | {0x16, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Rear : output 1 (0x0d) */ | |
954 | @@ -7632,7 +7881,7 @@ static struct hda_channel_mode alc888_3s | |
955 | static void alc888_lenovo_ms7195_front_automute(struct hda_codec *codec) | |
956 | { | |
957 | unsigned int present; | |
958 | - | |
959 | + | |
960 | present = snd_hda_codec_read(codec, 0x1b, 0, | |
961 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
962 | snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, | |
963 | @@ -7645,7 +7894,7 @@ static void alc888_lenovo_ms7195_front_a | |
964 | static void alc888_lenovo_ms7195_rca_automute(struct hda_codec *codec) | |
965 | { | |
966 | unsigned int present; | |
967 | - | |
968 | + | |
969 | present = snd_hda_codec_read(codec, 0x14, 0, | |
970 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
971 | snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, | |
972 | @@ -7675,7 +7924,7 @@ static struct hda_verb alc883_medion_md2 | |
973 | static void alc883_medion_md2_automute(struct hda_codec *codec) | |
974 | { | |
975 | unsigned int present; | |
976 | - | |
977 | + | |
978 | present = snd_hda_codec_read(codec, 0x14, 0, | |
979 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
980 | snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, | |
981 | @@ -7830,7 +8079,7 @@ static void alc883_lenovo_101e_unsol_eve | |
982 | static void alc883_acer_aspire_automute(struct hda_codec *codec) | |
983 | { | |
984 | unsigned int present; | |
985 | - | |
986 | + | |
987 | present = snd_hda_codec_read(codec, 0x14, 0, | |
988 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
989 | snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, | |
990 | @@ -7867,7 +8116,7 @@ static struct hda_verb alc883_acer_eapd_ | |
991 | static void alc888_6st_dell_front_automute(struct hda_codec *codec) | |
992 | { | |
993 | unsigned int present; | |
994 | - | |
995 | + | |
996 | present = snd_hda_codec_read(codec, 0x1b, 0, | |
997 | AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
998 | snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, | |
999 | @@ -7891,6 +8140,50 @@ static void alc888_6st_dell_unsol_event( | |
1000 | } | |
1001 | } | |
1002 | ||
1003 | +static void alc888_lenovo_sky_front_automute(struct hda_codec *codec) | |
1004 | +{ | |
1005 | + unsigned int mute; | |
1006 | + unsigned int present; | |
1007 | + | |
1008 | + snd_hda_codec_read(codec, 0x1b, 0, AC_VERB_SET_PIN_SENSE, 0); | |
1009 | + present = snd_hda_codec_read(codec, 0x1b, 0, | |
1010 | + AC_VERB_GET_PIN_SENSE, 0); | |
1011 | + present = (present & 0x80000000) != 0; | |
1012 | + if (present) { | |
1013 | + /* mute internal speaker */ | |
1014 | + snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, | |
1015 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
1016 | + snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, | |
1017 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
1018 | + snd_hda_codec_amp_stereo(codec, 0x16, HDA_OUTPUT, 0, | |
1019 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
1020 | + snd_hda_codec_amp_stereo(codec, 0x17, HDA_OUTPUT, 0, | |
1021 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
1022 | + snd_hda_codec_amp_stereo(codec, 0x1a, HDA_OUTPUT, 0, | |
1023 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
1024 | + } else { | |
1025 | + /* unmute internal speaker if necessary */ | |
1026 | + mute = snd_hda_codec_amp_read(codec, 0x1b, 0, HDA_OUTPUT, 0); | |
1027 | + snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, | |
1028 | + HDA_AMP_MUTE, mute); | |
1029 | + snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, | |
1030 | + HDA_AMP_MUTE, mute); | |
1031 | + snd_hda_codec_amp_stereo(codec, 0x16, HDA_OUTPUT, 0, | |
1032 | + HDA_AMP_MUTE, mute); | |
1033 | + snd_hda_codec_amp_stereo(codec, 0x17, HDA_OUTPUT, 0, | |
1034 | + HDA_AMP_MUTE, mute); | |
1035 | + snd_hda_codec_amp_stereo(codec, 0x1a, HDA_OUTPUT, 0, | |
1036 | + HDA_AMP_MUTE, mute); | |
1037 | + } | |
1038 | +} | |
1039 | + | |
1040 | +static void alc883_lenovo_sky_unsol_event(struct hda_codec *codec, | |
1041 | + unsigned int res) | |
1042 | +{ | |
1043 | + if ((res >> 26) == ALC880_HP_EVENT) | |
1044 | + alc888_lenovo_sky_front_automute(codec); | |
1045 | +} | |
1046 | + | |
1047 | /* | |
1048 | * generic initialization of ADC, input mixers and output mixers | |
1049 | */ | |
1050 | @@ -7975,16 +8268,115 @@ static struct snd_kcontrol_new alc883_ca | |
1051 | { } /* end */ | |
1052 | }; | |
1053 | ||
1054 | -#ifdef CONFIG_SND_HDA_POWER_SAVE | |
1055 | -#define alc883_loopbacks alc880_loopbacks | |
1056 | -#endif | |
1057 | +static struct hda_verb alc888_asus_m90v_verbs[] = { | |
1058 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
1059 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
1060 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
1061 | + /* enable unsolicited event */ | |
1062 | + {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
1063 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_MIC_EVENT | AC_USRSP_EN}, | |
1064 | + { } /* end */ | |
1065 | +}; | |
1066 | ||
1067 | -/* pcm configuration: identiacal with ALC880 */ | |
1068 | -#define alc883_pcm_analog_playback alc880_pcm_analog_playback | |
1069 | -#define alc883_pcm_analog_capture alc880_pcm_analog_capture | |
1070 | -#define alc883_pcm_analog_alt_capture alc880_pcm_analog_alt_capture | |
1071 | -#define alc883_pcm_digital_playback alc880_pcm_digital_playback | |
1072 | -#define alc883_pcm_digital_capture alc880_pcm_digital_capture | |
1073 | +static void alc883_nb_mic_automute(struct hda_codec *codec) | |
1074 | +{ | |
1075 | + unsigned int present; | |
1076 | + | |
1077 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
1078 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1079 | + snd_hda_codec_write(codec, 0x23, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
1080 | + 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
1081 | + snd_hda_codec_write(codec, 0x23, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
1082 | + 0x7000 | (0x01 << 8) | (present ? 0x80 : 0)); | |
1083 | +} | |
1084 | + | |
1085 | +static void alc883_M90V_speaker_automute(struct hda_codec *codec) | |
1086 | +{ | |
1087 | + unsigned int present; | |
1088 | + unsigned char bits; | |
1089 | + | |
1090 | + present = snd_hda_codec_read(codec, 0x1b, 0, | |
1091 | + AC_VERB_GET_PIN_SENSE, 0) | |
1092 | + & AC_PINSENSE_PRESENCE; | |
1093 | + bits = present ? 0 : PIN_OUT; | |
1094 | + snd_hda_codec_write(codec, 0x14, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
1095 | + bits); | |
1096 | + snd_hda_codec_write(codec, 0x15, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
1097 | + bits); | |
1098 | + snd_hda_codec_write(codec, 0x16, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
1099 | + bits); | |
1100 | +} | |
1101 | + | |
1102 | +static void alc883_mode2_unsol_event(struct hda_codec *codec, | |
1103 | + unsigned int res) | |
1104 | +{ | |
1105 | + switch (res >> 26) { | |
1106 | + case ALC880_HP_EVENT: | |
1107 | + alc883_M90V_speaker_automute(codec); | |
1108 | + break; | |
1109 | + case ALC880_MIC_EVENT: | |
1110 | + alc883_nb_mic_automute(codec); | |
1111 | + break; | |
1112 | + } | |
1113 | +} | |
1114 | + | |
1115 | +static void alc883_mode2_inithook(struct hda_codec *codec) | |
1116 | +{ | |
1117 | + alc883_M90V_speaker_automute(codec); | |
1118 | + alc883_nb_mic_automute(codec); | |
1119 | +} | |
1120 | + | |
1121 | +static struct hda_verb alc888_asus_eee1601_verbs[] = { | |
1122 | + {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1123 | + {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
1124 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
1125 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1126 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
1127 | + {0x20, AC_VERB_SET_COEF_INDEX, 0x0b}, | |
1128 | + {0x20, AC_VERB_SET_PROC_COEF, 0x0838}, | |
1129 | + /* enable unsolicited event */ | |
1130 | + {0x14, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
1131 | + { } /* end */ | |
1132 | +}; | |
1133 | + | |
1134 | +static void alc883_eee1601_speaker_automute(struct hda_codec *codec) | |
1135 | +{ | |
1136 | + unsigned int present; | |
1137 | + unsigned char bits; | |
1138 | + | |
1139 | + present = snd_hda_codec_read(codec, 0x14, 0, | |
1140 | + AC_VERB_GET_PIN_SENSE, 0) | |
1141 | + & AC_PINSENSE_PRESENCE; | |
1142 | + bits = present ? 0 : PIN_OUT; | |
1143 | + snd_hda_codec_write(codec, 0x1b, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, | |
1144 | + bits); | |
1145 | +} | |
1146 | + | |
1147 | +static void alc883_eee1601_unsol_event(struct hda_codec *codec, | |
1148 | + unsigned int res) | |
1149 | +{ | |
1150 | + switch (res >> 26) { | |
1151 | + case ALC880_HP_EVENT: | |
1152 | + alc883_eee1601_speaker_automute(codec); | |
1153 | + break; | |
1154 | + } | |
1155 | +} | |
1156 | + | |
1157 | +static void alc883_eee1601_inithook(struct hda_codec *codec) | |
1158 | +{ | |
1159 | + alc883_eee1601_speaker_automute(codec); | |
1160 | +} | |
1161 | + | |
1162 | +#ifdef CONFIG_SND_HDA_POWER_SAVE | |
1163 | +#define alc883_loopbacks alc880_loopbacks | |
1164 | +#endif | |
1165 | + | |
1166 | +/* pcm configuration: identiacal with ALC880 */ | |
1167 | +#define alc883_pcm_analog_playback alc880_pcm_analog_playback | |
1168 | +#define alc883_pcm_analog_capture alc880_pcm_analog_capture | |
1169 | +#define alc883_pcm_analog_alt_capture alc880_pcm_analog_alt_capture | |
1170 | +#define alc883_pcm_digital_playback alc880_pcm_digital_playback | |
1171 | +#define alc883_pcm_digital_capture alc880_pcm_digital_capture | |
1172 | ||
1173 | /* | |
1174 | * configuration and preset | |
1175 | @@ -8004,6 +8396,7 @@ static const char *alc883_models[ALC883_ | |
1176 | [ALC883_LENOVO_101E_2ch] = "lenovo-101e", | |
1177 | [ALC883_LENOVO_NB0763] = "lenovo-nb0763", | |
1178 | [ALC888_LENOVO_MS7195_DIG] = "lenovo-ms7195-dig", | |
1179 | + [ALC888_LENOVO_SKY] = "lenovo-sky", | |
1180 | [ALC883_HAIER_W66] = "haier-w66", | |
1181 | [ALC888_3ST_HP] = "3stack-hp", | |
1182 | [ALC888_6ST_DELL] = "6stack-dell", | |
1183 | @@ -8020,18 +8413,21 @@ static struct snd_pci_quirk alc883_cfg_t | |
1184 | SND_PCI_QUIRK(0x1025, 0x0090, "Acer Aspire", ALC883_ACER_ASPIRE), | |
1185 | SND_PCI_QUIRK(0x1025, 0x0110, "Acer Aspire", ALC883_ACER_ASPIRE), | |
1186 | SND_PCI_QUIRK(0x1025, 0x0112, "Acer Aspire 9303", ALC883_ACER_ASPIRE), | |
1187 | - SND_PCI_QUIRK(0x1025, 0x0121, "Acer Aspire 5920G", ALC883_ACER_ASPIRE), | |
1188 | + SND_PCI_QUIRK(0x1025, 0x0121, "Acer Aspire 5920G", ALC883_ACER_ASPIRE), | |
1189 | SND_PCI_QUIRK(0x1025, 0, "Acer laptop", ALC883_ACER), /* default Acer */ | |
1190 | SND_PCI_QUIRK(0x1028, 0x020d, "Dell Inspiron 530", ALC888_6ST_DELL), | |
1191 | SND_PCI_QUIRK(0x103c, 0x2a3d, "HP Pavillion", ALC883_6ST_DIG), | |
1192 | SND_PCI_QUIRK(0x103c, 0x2a4f, "HP Samba", ALC888_3ST_HP), | |
1193 | SND_PCI_QUIRK(0x103c, 0x2a60, "HP Lucknow", ALC888_3ST_HP), | |
1194 | SND_PCI_QUIRK(0x103c, 0x2a61, "HP Nettle", ALC883_6ST_DIG), | |
1195 | + SND_PCI_QUIRK(0x1043, 0x1873, "Asus M90V", ALC888_ASUS_M90V), | |
1196 | SND_PCI_QUIRK(0x1043, 0x8249, "Asus M2A-VM HDMI", ALC883_3ST_6ch_DIG), | |
1197 | + SND_PCI_QUIRK(0x1043, 0x835f, "Asus Eee 1601", ALC888_ASUS_EEE1601), | |
1198 | SND_PCI_QUIRK(0x105b, 0x0ce8, "Foxconn P35AX-S", ALC883_6ST_DIG), | |
1199 | SND_PCI_QUIRK(0x105b, 0x6668, "Foxconn", ALC883_6ST_DIG), | |
1200 | SND_PCI_QUIRK(0x1071, 0x8253, "Mitac 8252d", ALC883_MITAC), | |
1201 | SND_PCI_QUIRK(0x1071, 0x8258, "Evesham Voyaeger", ALC883_LAPTOP_EAPD), | |
1202 | + SND_PCI_QUIRK(0x10f1, 0x2350, "TYAN-S2350", ALC888_6ST_DELL), | |
1203 | SND_PCI_QUIRK(0x108e, 0x534d, NULL, ALC883_3ST_6ch), | |
1204 | SND_PCI_QUIRK(0x1458, 0xa002, "MSI", ALC883_6ST_DIG), | |
1205 | SND_PCI_QUIRK(0x1462, 0x0349, "MSI", ALC883_TARGA_2ch_DIG), | |
1206 | @@ -8069,6 +8465,7 @@ static struct snd_pci_quirk alc883_cfg_t | |
1207 | SND_PCI_QUIRK(0x17aa, 0x2085, "Lenovo NB0763", ALC883_LENOVO_NB0763), | |
1208 | SND_PCI_QUIRK(0x17aa, 0x3bfc, "Lenovo NB0763", ALC883_LENOVO_NB0763), | |
1209 | SND_PCI_QUIRK(0x17aa, 0x3bfd, "Lenovo NB0763", ALC883_LENOVO_NB0763), | |
1210 | + SND_PCI_QUIRK(0x17aa, 0x101d, "Lenovo Sky", ALC888_LENOVO_SKY), | |
1211 | SND_PCI_QUIRK(0x17c0, 0x4071, "MEDION MD2", ALC883_MEDION_MD2), | |
1212 | SND_PCI_QUIRK(0x17c0, 0x4085, "MEDION MD96630", ALC888_LENOVO_MS7195_DIG), | |
1213 | SND_PCI_QUIRK(0x17f2, 0x5000, "Albatron KI690-AM2", ALC883_6ST_DIG), | |
1214 | @@ -8209,7 +8606,7 @@ static struct alc_config_preset alc883_p | |
1215 | .input_mux = &alc883_capture_source, | |
1216 | .unsol_event = alc883_medion_md2_unsol_event, | |
1217 | .init_hook = alc883_medion_md2_automute, | |
1218 | - }, | |
1219 | + }, | |
1220 | [ALC883_LAPTOP_EAPD] = { | |
1221 | .mixers = { alc883_base_mixer }, | |
1222 | .init_verbs = { alc883_init_verbs, alc882_eapd_verbs }, | |
1223 | @@ -8326,6 +8723,49 @@ static struct alc_config_preset alc883_p | |
1224 | .unsol_event = alc883_2ch_fujitsu_pi2515_unsol_event, | |
1225 | .init_hook = alc883_2ch_fujitsu_pi2515_automute, | |
1226 | }, | |
1227 | + [ALC888_LENOVO_SKY] = { | |
1228 | + .mixers = { alc888_lenovo_sky_mixer, alc883_chmode_mixer }, | |
1229 | + .init_verbs = { alc883_init_verbs, alc888_lenovo_sky_verbs}, | |
1230 | + .num_dacs = ARRAY_SIZE(alc883_dac_nids), | |
1231 | + .dac_nids = alc883_dac_nids, | |
1232 | + .dig_out_nid = ALC883_DIGOUT_NID, | |
1233 | + .num_adc_nids = ARRAY_SIZE(alc883_adc_nids), | |
1234 | + .adc_nids = alc883_adc_nids, | |
1235 | + .num_channel_mode = ARRAY_SIZE(alc883_sixstack_modes), | |
1236 | + .channel_mode = alc883_sixstack_modes, | |
1237 | + .need_dac_fix = 1, | |
1238 | + .input_mux = &alc883_lenovo_sky_capture_source, | |
1239 | + .unsol_event = alc883_lenovo_sky_unsol_event, | |
1240 | + .init_hook = alc888_lenovo_sky_front_automute, | |
1241 | + }, | |
1242 | + [ALC888_ASUS_M90V] = { | |
1243 | + .mixers = { alc883_3ST_6ch_mixer, alc883_chmode_mixer }, | |
1244 | + .init_verbs = { alc883_init_verbs, alc888_asus_m90v_verbs }, | |
1245 | + .num_dacs = ARRAY_SIZE(alc883_dac_nids), | |
1246 | + .dac_nids = alc883_dac_nids, | |
1247 | + .dig_out_nid = ALC883_DIGOUT_NID, | |
1248 | + .dig_in_nid = ALC883_DIGIN_NID, | |
1249 | + .num_channel_mode = ARRAY_SIZE(alc883_3ST_6ch_modes), | |
1250 | + .channel_mode = alc883_3ST_6ch_modes, | |
1251 | + .need_dac_fix = 1, | |
1252 | + .input_mux = &alc883_fujitsu_pi2515_capture_source, | |
1253 | + .unsol_event = alc883_mode2_unsol_event, | |
1254 | + .init_hook = alc883_mode2_inithook, | |
1255 | + }, | |
1256 | + [ALC888_ASUS_EEE1601] = { | |
1257 | + .mixers = { alc883_asus_eee1601_mixer }, | |
1258 | + .init_verbs = { alc883_init_verbs, alc888_asus_eee1601_verbs }, | |
1259 | + .num_dacs = ARRAY_SIZE(alc883_dac_nids), | |
1260 | + .dac_nids = alc883_dac_nids, | |
1261 | + .dig_out_nid = ALC883_DIGOUT_NID, | |
1262 | + .dig_in_nid = ALC883_DIGIN_NID, | |
1263 | + .num_channel_mode = ARRAY_SIZE(alc883_3ST_2ch_modes), | |
1264 | + .channel_mode = alc883_3ST_2ch_modes, | |
1265 | + .need_dac_fix = 1, | |
1266 | + .input_mux = &alc883_asus_eee1601_capture_source, | |
1267 | + .unsol_event = alc883_eee1601_unsol_event, | |
1268 | + .init_hook = alc883_eee1601_inithook, | |
1269 | + }, | |
1270 | }; | |
1271 | ||
1272 | ||
1273 | @@ -8435,7 +8875,7 @@ static void alc883_auto_init(struct hda_ | |
1274 | alc883_auto_init_analog_input(codec); | |
1275 | alc883_auto_init_input_src(codec); | |
1276 | if (spec->unsol_event) | |
1277 | - alc_sku_automute(codec); | |
1278 | + alc_inithook(codec); | |
1279 | } | |
1280 | ||
1281 | static int patch_alc883(struct hda_codec *codec) | |
1282 | @@ -8479,8 +8919,13 @@ static int patch_alc883(struct hda_codec | |
1283 | ||
1284 | switch (codec->vendor_id) { | |
1285 | case 0x10ec0888: | |
1286 | - spec->stream_name_analog = "ALC888 Analog"; | |
1287 | - spec->stream_name_digital = "ALC888 Digital"; | |
1288 | + if (codec->revision_id == 0x100101) { | |
1289 | + spec->stream_name_analog = "ALC1200 Analog"; | |
1290 | + spec->stream_name_digital = "ALC1200 Digital"; | |
1291 | + } else { | |
1292 | + spec->stream_name_analog = "ALC888 Analog"; | |
1293 | + spec->stream_name_digital = "ALC888 Digital"; | |
1294 | + } | |
1295 | break; | |
1296 | case 0x10ec0889: | |
1297 | spec->stream_name_analog = "ALC889 Analog"; | |
1298 | @@ -8533,6 +8978,13 @@ static int patch_alc883(struct hda_codec | |
1299 | #define alc262_modes alc260_modes | |
1300 | #define alc262_capture_source alc882_capture_source | |
1301 | ||
1302 | +static hda_nid_t alc262_dmic_adc_nids[1] = { | |
1303 | + /* ADC0 */ | |
1304 | + 0x09 | |
1305 | +}; | |
1306 | + | |
1307 | +static hda_nid_t alc262_dmic_capsrc_nids[1] = { 0x22 }; | |
1308 | + | |
1309 | static struct snd_kcontrol_new alc262_base_mixer[] = { | |
1310 | HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | |
1311 | HDA_CODEC_MUTE("Front Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
1312 | @@ -8914,10 +9366,10 @@ static struct hda_verb alc262_init_verbs | |
1313 | {0x16, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000}, | |
1314 | {0x18, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000}, | |
1315 | {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000}, | |
1316 | - | |
1317 | + | |
1318 | {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1319 | {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
1320 | - | |
1321 | + | |
1322 | /* FIXME: use matrix-type input source selection */ | |
1323 | /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */ | |
1324 | /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */ | |
1325 | @@ -8939,6 +9391,12 @@ static struct hda_verb alc262_init_verbs | |
1326 | { } | |
1327 | }; | |
1328 | ||
1329 | +static struct hda_verb alc262_eapd_verbs[] = { | |
1330 | + {0x14, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
1331 | + {0x15, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
1332 | + { } | |
1333 | +}; | |
1334 | + | |
1335 | static struct hda_verb alc262_hippo_unsol_verbs[] = { | |
1336 | {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
1337 | {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1338 | @@ -8965,6 +9423,91 @@ static struct hda_verb alc262_sony_unsol | |
1339 | {} | |
1340 | }; | |
1341 | ||
1342 | +static struct hda_input_mux alc262_dmic_capture_source = { | |
1343 | + .num_items = 2, | |
1344 | + .items = { | |
1345 | + { "Int DMic", 0x9 }, | |
1346 | + { "Mic", 0x0 }, | |
1347 | + }, | |
1348 | +}; | |
1349 | + | |
1350 | +static struct snd_kcontrol_new alc262_toshiba_s06_mixer[] = { | |
1351 | + HDA_CODEC_VOLUME("Speaker Playback Volume", 0x0c, 0x0, HDA_OUTPUT), | |
1352 | + HDA_CODEC_MUTE("Speaker Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
1353 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x15, 0x0, HDA_OUTPUT), | |
1354 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
1355 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
1356 | + HDA_CODEC_VOLUME("Capture Volume", 0x09, 0x0, HDA_INPUT), | |
1357 | + HDA_CODEC_MUTE("Capture Switch", 0x09, 0x0, HDA_INPUT), | |
1358 | + { | |
1359 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
1360 | + /* The multiple "Capture Source" controls confuse alsamixer | |
1361 | + * So call somewhat different.. | |
1362 | + */ | |
1363 | + /* .name = "Capture Source", */ | |
1364 | + .name = "Input Source", | |
1365 | + .count = 1, | |
1366 | + .info = alc_mux_enum_info, | |
1367 | + .get = alc_mux_enum_get, | |
1368 | + .put = alc_mux_enum_put, | |
1369 | + }, | |
1370 | + { } /* end */ | |
1371 | +}; | |
1372 | + | |
1373 | +static struct hda_verb alc262_toshiba_s06_verbs[] = { | |
1374 | + {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1375 | + {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
1376 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1377 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1378 | + {0x22, AC_VERB_SET_CONNECT_SEL, 0x09}, | |
1379 | + {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24}, | |
1380 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
1381 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
1382 | + {} | |
1383 | +}; | |
1384 | + | |
1385 | +static void alc262_dmic_automute(struct hda_codec *codec) | |
1386 | +{ | |
1387 | + unsigned int present; | |
1388 | + | |
1389 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
1390 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1391 | + snd_hda_codec_write(codec, 0x22, 0, | |
1392 | + AC_VERB_SET_CONNECT_SEL, present ? 0x0 : 0x09); | |
1393 | +} | |
1394 | + | |
1395 | +/* toggle speaker-output according to the hp-jack state */ | |
1396 | +static void alc262_toshiba_s06_speaker_automute(struct hda_codec *codec) | |
1397 | +{ | |
1398 | + unsigned int present; | |
1399 | + unsigned char bits; | |
1400 | + | |
1401 | + present = snd_hda_codec_read(codec, 0x15, 0, | |
1402 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1403 | + bits = present ? 0 : PIN_OUT; | |
1404 | + snd_hda_codec_write(codec, 0x14, 0, | |
1405 | + AC_VERB_SET_PIN_WIDGET_CONTROL, bits); | |
1406 | +} | |
1407 | + | |
1408 | + | |
1409 | + | |
1410 | +/* unsolicited event for HP jack sensing */ | |
1411 | +static void alc262_toshiba_s06_unsol_event(struct hda_codec *codec, | |
1412 | + unsigned int res) | |
1413 | +{ | |
1414 | + if ((res >> 26) == ALC880_HP_EVENT) | |
1415 | + alc262_toshiba_s06_speaker_automute(codec); | |
1416 | + if ((res >> 26) == ALC880_MIC_EVENT) | |
1417 | + alc262_dmic_automute(codec); | |
1418 | + | |
1419 | +} | |
1420 | + | |
1421 | +static void alc262_toshiba_s06_init_hook(struct hda_codec *codec) | |
1422 | +{ | |
1423 | + alc262_toshiba_s06_speaker_automute(codec); | |
1424 | + alc262_dmic_automute(codec); | |
1425 | +} | |
1426 | + | |
1427 | /* mute/unmute internal speaker according to the hp jack and mute state */ | |
1428 | static void alc262_hippo_automute(struct hda_codec *codec) | |
1429 | { | |
1430 | @@ -9295,6 +9838,25 @@ static struct snd_kcontrol_new alc262_le | |
1431 | { } /* end */ | |
1432 | }; | |
1433 | ||
1434 | +static struct snd_kcontrol_new alc262_toshiba_rx1_mixer[] = { | |
1435 | + HDA_BIND_VOL("Master Playback Volume", &alc262_fujitsu_bind_master_vol), | |
1436 | + { | |
1437 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
1438 | + .name = "Master Playback Switch", | |
1439 | + .info = snd_hda_mixer_amp_switch_info, | |
1440 | + .get = snd_hda_mixer_amp_switch_get, | |
1441 | + .put = alc262_sony_master_sw_put, | |
1442 | + .private_value = HDA_COMPOSE_AMP_VAL(0x15, 3, 0, HDA_OUTPUT), | |
1443 | + }, | |
1444 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
1445 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
1446 | + HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
1447 | + HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x01, HDA_INPUT), | |
1448 | + HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x01, HDA_INPUT), | |
1449 | + HDA_CODEC_VOLUME("Front Mic Boost", 0x19, 0, HDA_INPUT), | |
1450 | + { } /* end */ | |
1451 | +}; | |
1452 | + | |
1453 | /* additional init verbs for Benq laptops */ | |
1454 | static struct hda_verb alc262_EAPD_verbs[] = { | |
1455 | {0x20, AC_VERB_SET_COEF_INDEX, 0x07}, | |
1456 | @@ -9543,7 +10105,7 @@ static struct hda_verb alc262_volume_ini | |
1457 | {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
1458 | {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
1459 | {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
1460 | - | |
1461 | + | |
1462 | /* set up input amps for analog loopback */ | |
1463 | /* Amp Indices: DAC = 0, mixer = 1 */ | |
1464 | {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1465 | @@ -9598,7 +10160,7 @@ static struct hda_verb alc262_HP_BPC_ini | |
1466 | {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
1467 | {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)}, | |
1468 | {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)}, | |
1469 | - | |
1470 | + | |
1471 | /* | |
1472 | * Set up output mixers (0x0c - 0x0e) | |
1473 | */ | |
1474 | @@ -9759,6 +10321,24 @@ static struct hda_verb alc262_HP_BPC_Wil | |
1475 | { } | |
1476 | }; | |
1477 | ||
1478 | +static struct hda_verb alc262_toshiba_rx1_unsol_verbs[] = { | |
1479 | + | |
1480 | + {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT }, /* Front Speaker */ | |
1481 | + {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE }, | |
1482 | + {0x14, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
1483 | + | |
1484 | + {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* MIC jack */ | |
1485 | + {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* Front MIC */ | |
1486 | + {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0) }, | |
1487 | + {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0) }, | |
1488 | + | |
1489 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP }, /* HP jack */ | |
1490 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1491 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
1492 | + {} | |
1493 | +}; | |
1494 | + | |
1495 | + | |
1496 | #ifdef CONFIG_SND_HDA_POWER_SAVE | |
1497 | #define alc262_loopbacks alc880_loopbacks | |
1498 | #endif | |
1499 | @@ -9828,7 +10408,7 @@ static void alc262_auto_init(struct hda_ | |
1500 | alc262_auto_init_analog_input(codec); | |
1501 | alc262_auto_init_input_src(codec); | |
1502 | if (spec->unsol_event) | |
1503 | - alc_sku_automute(codec); | |
1504 | + alc_inithook(codec); | |
1505 | } | |
1506 | ||
1507 | /* | |
1508 | @@ -9846,6 +10426,8 @@ static const char *alc262_models[ALC262_ | |
1509 | [ALC262_BENQ_ED8] = "benq", | |
1510 | [ALC262_BENQ_T31] = "benq-t31", | |
1511 | [ALC262_SONY_ASSAMD] = "sony-assamd", | |
1512 | + [ALC262_TOSHIBA_S06] = "toshiba-s06", | |
1513 | + [ALC262_TOSHIBA_RX1] = "toshiba-rx1", | |
1514 | [ALC262_ULTRA] = "ultra", | |
1515 | [ALC262_LENOVO_3000] = "lenovo-3000", | |
1516 | [ALC262_NEC] = "nec", | |
1517 | @@ -9883,7 +10465,8 @@ static struct snd_pci_quirk alc262_cfg_t | |
1518 | SND_PCI_QUIRK(0x104d, 0x900e, "Sony ASSAMD", ALC262_SONY_ASSAMD), | |
1519 | SND_PCI_QUIRK(0x104d, 0x9015, "Sony 0x9015", ALC262_SONY_ASSAMD), | |
1520 | SND_PCI_QUIRK(0x1179, 0x0001, "Toshiba dynabook SS RX1", | |
1521 | - ALC262_SONY_ASSAMD), | |
1522 | + ALC262_TOSHIBA_RX1), | |
1523 | + SND_PCI_QUIRK(0x1179, 0xff7b, "Toshiba S06", ALC262_TOSHIBA_S06), | |
1524 | SND_PCI_QUIRK(0x10cf, 0x1397, "Fujitsu", ALC262_FUJITSU), | |
1525 | SND_PCI_QUIRK(0x10cf, 0x142d, "Fujitsu Lifebook E8410", ALC262_FUJITSU), | |
1526 | SND_PCI_QUIRK(0x144d, 0xc032, "Samsung Q1 Ultra", ALC262_ULTRA), | |
1527 | @@ -10038,7 +10621,7 @@ static struct alc_config_preset alc262_p | |
1528 | .input_mux = &alc262_capture_source, | |
1529 | .unsol_event = alc262_hippo_unsol_event, | |
1530 | .init_hook = alc262_hippo_automute, | |
1531 | - }, | |
1532 | + }, | |
1533 | [ALC262_ULTRA] = { | |
1534 | .mixers = { alc262_ultra_mixer, alc262_ultra_capture_mixer }, | |
1535 | .init_verbs = { alc262_ultra_verbs }, | |
1536 | @@ -10076,6 +10659,33 @@ static struct alc_config_preset alc262_p | |
1537 | .channel_mode = alc262_modes, | |
1538 | .input_mux = &alc262_capture_source, | |
1539 | }, | |
1540 | + [ALC262_TOSHIBA_S06] = { | |
1541 | + .mixers = { alc262_toshiba_s06_mixer }, | |
1542 | + .init_verbs = { alc262_init_verbs, alc262_toshiba_s06_verbs, | |
1543 | + alc262_eapd_verbs }, | |
1544 | + .num_dacs = ARRAY_SIZE(alc262_dac_nids), | |
1545 | + .capsrc_nids = alc262_dmic_capsrc_nids, | |
1546 | + .dac_nids = alc262_dac_nids, | |
1547 | + .adc_nids = alc262_dmic_adc_nids, /* ADC0 */ | |
1548 | + .dig_out_nid = ALC262_DIGOUT_NID, | |
1549 | + .num_channel_mode = ARRAY_SIZE(alc262_modes), | |
1550 | + .channel_mode = alc262_modes, | |
1551 | + .input_mux = &alc262_dmic_capture_source, | |
1552 | + .unsol_event = alc262_toshiba_s06_unsol_event, | |
1553 | + .init_hook = alc262_toshiba_s06_init_hook, | |
1554 | + }, | |
1555 | + [ALC262_TOSHIBA_RX1] = { | |
1556 | + .mixers = { alc262_toshiba_rx1_mixer }, | |
1557 | + .init_verbs = { alc262_init_verbs, alc262_toshiba_rx1_unsol_verbs }, | |
1558 | + .num_dacs = ARRAY_SIZE(alc262_dac_nids), | |
1559 | + .dac_nids = alc262_dac_nids, | |
1560 | + .hp_nid = 0x03, | |
1561 | + .num_channel_mode = ARRAY_SIZE(alc262_modes), | |
1562 | + .channel_mode = alc262_modes, | |
1563 | + .input_mux = &alc262_capture_source, | |
1564 | + .unsol_event = alc262_hippo_unsol_event, | |
1565 | + .init_hook = alc262_hippo_automute, | |
1566 | + }, | |
1567 | }; | |
1568 | ||
1569 | static int patch_alc262(struct hda_codec *codec) | |
1570 | @@ -10134,7 +10744,7 @@ static int patch_alc262(struct hda_codec | |
1571 | spec->stream_name_analog = "ALC262 Analog"; | |
1572 | spec->stream_analog_playback = &alc262_pcm_analog_playback; | |
1573 | spec->stream_analog_capture = &alc262_pcm_analog_capture; | |
1574 | - | |
1575 | + | |
1576 | spec->stream_name_digital = "ALC262 Digital"; | |
1577 | spec->stream_digital_playback = &alc262_pcm_digital_playback; | |
1578 | spec->stream_digital_capture = &alc262_pcm_digital_capture; | |
1579 | @@ -10170,7 +10780,7 @@ static int patch_alc262(struct hda_codec | |
1580 | if (!spec->loopback.amplist) | |
1581 | spec->loopback.amplist = alc262_loopbacks; | |
1582 | #endif | |
1583 | - | |
1584 | + | |
1585 | return 0; | |
1586 | } | |
1587 | ||
1588 | @@ -10179,7 +10789,7 @@ static int patch_alc262(struct hda_codec | |
1589 | */ | |
1590 | #define ALC268_DIGOUT_NID ALC880_DIGOUT_NID | |
1591 | #define alc268_modes alc260_modes | |
1592 | - | |
1593 | + | |
1594 | static hda_nid_t alc268_dac_nids[2] = { | |
1595 | /* front, hp */ | |
1596 | 0x02, 0x03 | |
1597 | @@ -10239,6 +10849,14 @@ static struct hda_verb alc268_toshiba_ve | |
1598 | { } /* end */ | |
1599 | }; | |
1600 | ||
1601 | +static struct hda_input_mux alc268_acer_lc_capture_source = { | |
1602 | + .num_items = 2, | |
1603 | + .items = { | |
1604 | + { "i-Mic", 0x6 }, | |
1605 | + { "E-Mic", 0x0 }, | |
1606 | + }, | |
1607 | +}; | |
1608 | + | |
1609 | /* Acer specific */ | |
1610 | /* bind volumes of both NID 0x02 and 0x03 */ | |
1611 | static struct hda_bind_ctls alc268_acer_bind_master_vol = { | |
1612 | @@ -10291,6 +10909,21 @@ static int alc268_acer_master_sw_put(str | |
1613 | return change; | |
1614 | } | |
1615 | ||
1616 | +static struct snd_kcontrol_new alc268_acer_aspire_one_mixer[] = { | |
1617 | + /* output mixer control */ | |
1618 | + HDA_BIND_VOL("Master Playback Volume", &alc268_acer_bind_master_vol), | |
1619 | + { | |
1620 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
1621 | + .name = "Master Playback Switch", | |
1622 | + .info = snd_hda_mixer_amp_switch_info, | |
1623 | + .get = snd_hda_mixer_amp_switch_get, | |
1624 | + .put = alc268_acer_master_sw_put, | |
1625 | + .private_value = HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
1626 | + }, | |
1627 | + HDA_CODEC_VOLUME("Mic Boost Capture Volume", 0x18, 0, HDA_INPUT), | |
1628 | + { } | |
1629 | +}; | |
1630 | + | |
1631 | static struct snd_kcontrol_new alc268_acer_mixer[] = { | |
1632 | /* output mixer control */ | |
1633 | HDA_BIND_VOL("Master Playback Volume", &alc268_acer_bind_master_vol), | |
1634 | @@ -10308,6 +10941,16 @@ static struct snd_kcontrol_new alc268_ac | |
1635 | { } | |
1636 | }; | |
1637 | ||
1638 | +static struct hda_verb alc268_acer_aspire_one_verbs[] = { | |
1639 | + {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1640 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1641 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
1642 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
1643 | + {0x23, AC_VERB_SET_CONNECT_SEL, 0x06}, | |
1644 | + {0x23, AC_VERB_SET_AMP_GAIN_MUTE, 0xa017}, | |
1645 | + { } | |
1646 | +}; | |
1647 | + | |
1648 | static struct hda_verb alc268_acer_verbs[] = { | |
1649 | {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, /* internal dmic? */ | |
1650 | {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1651 | @@ -10315,7 +10958,6 @@ static struct hda_verb alc268_acer_verbs | |
1652 | {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
1653 | {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
1654 | {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
1655 | - | |
1656 | {0x14, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
1657 | { } | |
1658 | }; | |
1659 | @@ -10342,10 +10984,51 @@ static void alc268_acer_init_hook(struct | |
1660 | alc268_acer_automute(codec, 1); | |
1661 | } | |
1662 | ||
1663 | -static struct snd_kcontrol_new alc268_dell_mixer[] = { | |
1664 | - /* output mixer control */ | |
1665 | - HDA_CODEC_VOLUME("Speaker Playback Volume", 0x02, 0x0, HDA_OUTPUT), | |
1666 | - HDA_CODEC_MUTE("Speaker Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
1667 | +/* toggle speaker-output according to the hp-jack state */ | |
1668 | +static void alc268_aspire_one_speaker_automute(struct hda_codec *codec) | |
1669 | +{ | |
1670 | + unsigned int present; | |
1671 | + unsigned char bits; | |
1672 | + | |
1673 | + present = snd_hda_codec_read(codec, 0x15, 0, | |
1674 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1675 | + bits = present ? AMP_IN_MUTE(0) : 0; | |
1676 | + snd_hda_codec_amp_stereo(codec, 0x0f, HDA_INPUT, 0, | |
1677 | + AMP_IN_MUTE(0), bits); | |
1678 | + snd_hda_codec_amp_stereo(codec, 0x0f, HDA_INPUT, 1, | |
1679 | + AMP_IN_MUTE(0), bits); | |
1680 | +} | |
1681 | + | |
1682 | + | |
1683 | +static void alc268_acer_mic_automute(struct hda_codec *codec) | |
1684 | +{ | |
1685 | + unsigned int present; | |
1686 | + | |
1687 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
1688 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1689 | + snd_hda_codec_write(codec, 0x23, 0, AC_VERB_SET_CONNECT_SEL, | |
1690 | + present ? 0x0 : 0x6); | |
1691 | +} | |
1692 | + | |
1693 | +static void alc268_acer_lc_unsol_event(struct hda_codec *codec, | |
1694 | + unsigned int res) | |
1695 | +{ | |
1696 | + if ((res >> 26) == ALC880_HP_EVENT) | |
1697 | + alc268_aspire_one_speaker_automute(codec); | |
1698 | + if ((res >> 26) == ALC880_MIC_EVENT) | |
1699 | + alc268_acer_mic_automute(codec); | |
1700 | +} | |
1701 | + | |
1702 | +static void alc268_acer_lc_init_hook(struct hda_codec *codec) | |
1703 | +{ | |
1704 | + alc268_aspire_one_speaker_automute(codec); | |
1705 | + alc268_acer_mic_automute(codec); | |
1706 | +} | |
1707 | + | |
1708 | +static struct snd_kcontrol_new alc268_dell_mixer[] = { | |
1709 | + /* output mixer control */ | |
1710 | + HDA_CODEC_VOLUME("Speaker Playback Volume", 0x02, 0x0, HDA_OUTPUT), | |
1711 | + HDA_CODEC_MUTE("Speaker Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
1712 | HDA_CODEC_VOLUME("Headphone Playback Volume", 0x03, 0x0, HDA_OUTPUT), | |
1713 | HDA_CODEC_MUTE("Headphone Playback Switch", 0x15, 0x0, HDA_OUTPUT), | |
1714 | HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
1715 | @@ -10490,7 +11173,7 @@ static struct hda_verb alc268_base_init_ | |
1716 | {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
1717 | ||
1718 | /* Unmute Selector 23h,24h and set the default input to mic-in */ | |
1719 | - | |
1720 | + | |
1721 | {0x23, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1722 | {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
1723 | {0x24, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1724 | @@ -10689,7 +11372,7 @@ static int alc268_auto_create_multi_out_ | |
1725 | ||
1726 | nid = cfg->line_out_pins[0]; | |
1727 | if (nid) | |
1728 | - alc268_new_analog_output(spec, nid, "Front", 0); | |
1729 | + alc268_new_analog_output(spec, nid, "Front", 0); | |
1730 | ||
1731 | nid = cfg->speaker_pins[0]; | |
1732 | if (nid == 0x1d) { | |
1733 | @@ -10711,7 +11394,7 @@ static int alc268_auto_create_multi_out_ | |
1734 | if (err < 0) | |
1735 | return err; | |
1736 | } | |
1737 | - return 0; | |
1738 | + return 0; | |
1739 | } | |
1740 | ||
1741 | /* create playback/capture controls for input pins */ | |
1742 | @@ -10732,7 +11415,7 @@ static int alc268_auto_create_analog_inp | |
1743 | case 0x1a: | |
1744 | idx1 = 2; /* Line In */ | |
1745 | break; | |
1746 | - case 0x1c: | |
1747 | + case 0x1c: | |
1748 | idx1 = 3; /* CD */ | |
1749 | break; | |
1750 | case 0x12: | |
1751 | @@ -10744,7 +11427,7 @@ static int alc268_auto_create_analog_inp | |
1752 | } | |
1753 | imux->items[imux->num_items].label = auto_pin_cfg_labels[i]; | |
1754 | imux->items[imux->num_items].index = idx1; | |
1755 | - imux->num_items++; | |
1756 | + imux->num_items++; | |
1757 | } | |
1758 | return 0; | |
1759 | } | |
1760 | @@ -10774,11 +11457,11 @@ static void alc268_auto_init_mono_speake | |
1761 | } | |
1762 | ||
1763 | dac_vol1 = dac_vol2 = 0xb000 | 0x40; /* set max volume */ | |
1764 | - if (line_nid == 0x14) | |
1765 | + if (line_nid == 0x14) | |
1766 | dac_vol2 = AMP_OUT_ZERO; | |
1767 | else if (line_nid == 0x15) | |
1768 | dac_vol1 = AMP_OUT_ZERO; | |
1769 | - if (hp_nid == 0x14) | |
1770 | + if (hp_nid == 0x14) | |
1771 | dac_vol2 = AMP_OUT_ZERO; | |
1772 | else if (hp_nid == 0x15) | |
1773 | dac_vol1 = AMP_OUT_ZERO; | |
1774 | @@ -10859,7 +11542,7 @@ static void alc268_auto_init(struct hda_ | |
1775 | alc268_auto_init_mono_speaker_out(codec); | |
1776 | alc268_auto_init_analog_input(codec); | |
1777 | if (spec->unsol_event) | |
1778 | - alc_sku_automute(codec); | |
1779 | + alc_inithook(codec); | |
1780 | } | |
1781 | ||
1782 | /* | |
1783 | @@ -10870,6 +11553,7 @@ static const char *alc268_models[ALC268_ | |
1784 | [ALC268_3ST] = "3stack", | |
1785 | [ALC268_TOSHIBA] = "toshiba", | |
1786 | [ALC268_ACER] = "acer", | |
1787 | + [ALC268_ACER_ASPIRE_ONE] = "acer-aspire", | |
1788 | [ALC268_DELL] = "dell", | |
1789 | [ALC268_ZEPTO] = "zepto", | |
1790 | #ifdef CONFIG_SND_DEBUG | |
1791 | @@ -10884,6 +11568,8 @@ static struct snd_pci_quirk alc268_cfg_t | |
1792 | SND_PCI_QUIRK(0x1025, 0x012e, "Acer Aspire 5310", ALC268_ACER), | |
1793 | SND_PCI_QUIRK(0x1025, 0x0130, "Acer Extensa 5210", ALC268_ACER), | |
1794 | SND_PCI_QUIRK(0x1025, 0x0136, "Acer Aspire 5315", ALC268_ACER), | |
1795 | + SND_PCI_QUIRK(0x1025, 0x015b, "Acer Aspire One", | |
1796 | + ALC268_ACER_ASPIRE_ONE), | |
1797 | SND_PCI_QUIRK(0x1028, 0x0253, "Dell OEM", ALC268_DELL), | |
1798 | SND_PCI_QUIRK(0x103c, 0x30cc, "TOSHIBA", ALC268_TOSHIBA), | |
1799 | SND_PCI_QUIRK(0x1043, 0x1205, "ASUS W7J", ALC268_3ST), | |
1800 | @@ -10962,6 +11648,23 @@ static struct alc_config_preset alc268_p | |
1801 | .unsol_event = alc268_acer_unsol_event, | |
1802 | .init_hook = alc268_acer_init_hook, | |
1803 | }, | |
1804 | + [ALC268_ACER_ASPIRE_ONE] = { | |
1805 | + .mixers = { alc268_acer_aspire_one_mixer, | |
1806 | + alc268_capture_alt_mixer }, | |
1807 | + .init_verbs = { alc268_base_init_verbs, alc268_eapd_verbs, | |
1808 | + alc268_acer_aspire_one_verbs }, | |
1809 | + .num_dacs = ARRAY_SIZE(alc268_dac_nids), | |
1810 | + .dac_nids = alc268_dac_nids, | |
1811 | + .num_adc_nids = ARRAY_SIZE(alc268_adc_nids_alt), | |
1812 | + .adc_nids = alc268_adc_nids_alt, | |
1813 | + .capsrc_nids = alc268_capsrc_nids, | |
1814 | + .hp_nid = 0x03, | |
1815 | + .num_channel_mode = ARRAY_SIZE(alc268_modes), | |
1816 | + .channel_mode = alc268_modes, | |
1817 | + .input_mux = &alc268_acer_lc_capture_source, | |
1818 | + .unsol_event = alc268_acer_lc_unsol_event, | |
1819 | + .init_hook = alc268_acer_lc_init_hook, | |
1820 | + }, | |
1821 | [ALC268_DELL] = { | |
1822 | .mixers = { alc268_dell_mixer, alc268_beep_mixer }, | |
1823 | .init_verbs = { alc268_base_init_verbs, alc268_eapd_verbs, | |
1824 | @@ -11106,7 +11809,7 @@ static int patch_alc268(struct hda_codec | |
1825 | codec->patch_ops = alc_patch_ops; | |
1826 | if (board_config == ALC268_AUTO) | |
1827 | spec->init_hook = alc268_auto_init; | |
1828 | - | |
1829 | + | |
1830 | return 0; | |
1831 | } | |
1832 | ||
1833 | @@ -11156,6 +11859,8 @@ static struct snd_kcontrol_new alc269_ba | |
1834 | HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT), | |
1835 | HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
1836 | HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
1837 | + HDA_CODEC_VOLUME("Beep Playback Volume", 0x0b, 0x4, HDA_INPUT), | |
1838 | + HDA_CODEC_MUTE("Beep Playback Switch", 0x0b, 0x4, HDA_INPUT), | |
1839 | HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
1840 | HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x01, HDA_INPUT), | |
1841 | HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x01, HDA_INPUT), | |
1842 | @@ -11165,6 +11870,28 @@ static struct snd_kcontrol_new alc269_ba | |
1843 | { } /* end */ | |
1844 | }; | |
1845 | ||
1846 | +static struct snd_kcontrol_new alc269_quanta_fl1_mixer[] = { | |
1847 | + /* output mixer control */ | |
1848 | + HDA_BIND_VOL("Master Playback Volume", &alc268_acer_bind_master_vol), | |
1849 | + { | |
1850 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
1851 | + .name = "Master Playback Switch", | |
1852 | + .info = snd_hda_mixer_amp_switch_info, | |
1853 | + .get = snd_hda_mixer_amp_switch_get, | |
1854 | + .put = alc268_acer_master_sw_put, | |
1855 | + .private_value = HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
1856 | + }, | |
1857 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
1858 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
1859 | + HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT), | |
1860 | + HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x0b, 0x01, HDA_INPUT), | |
1861 | + HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x0b, 0x01, HDA_INPUT), | |
1862 | + HDA_CODEC_VOLUME("Internal Mic Boost", 0x19, 0, HDA_INPUT), | |
1863 | + HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x0b, 0x04, HDA_INPUT), | |
1864 | + HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x04, HDA_INPUT), | |
1865 | + { } | |
1866 | +}; | |
1867 | + | |
1868 | /* bind volumes of both NID 0x0c and 0x0d */ | |
1869 | static struct hda_bind_ctls alc269_epc_bind_vol = { | |
1870 | .ops = &snd_hda_bind_vol, | |
1871 | @@ -11208,75 +11935,72 @@ static struct snd_kcontrol_new alc269_ep | |
1872 | { } /* end */ | |
1873 | }; | |
1874 | ||
1875 | -/* | |
1876 | - * generic initialization of ADC, input mixers and output mixers | |
1877 | - */ | |
1878 | -static struct hda_verb alc269_init_verbs[] = { | |
1879 | - /* | |
1880 | - * Unmute ADC0 and set the default input to mic-in | |
1881 | - */ | |
1882 | - {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1883 | +/* beep control */ | |
1884 | +static struct snd_kcontrol_new alc269_beep_mixer[] = { | |
1885 | + HDA_CODEC_VOLUME("Beep Playback Volume", 0x0b, 0x4, HDA_INPUT), | |
1886 | + HDA_CODEC_MUTE("Beep Playback Switch", 0x0b, 0x4, HDA_INPUT), | |
1887 | + { } /* end */ | |
1888 | +}; | |
1889 | ||
1890 | - /* Mute input amps (PCBeep, Line In, Mic 1 & Mic 2) of the | |
1891 | - * analog-loopback mixer widget | |
1892 | - * Note: PASD motherboards uses the Line In 2 as the input for | |
1893 | - * front panel mic (mic 2) | |
1894 | - */ | |
1895 | - /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */ | |
1896 | - {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
1897 | - {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
1898 | - {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
1899 | - {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, | |
1900 | - {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
1901 | +static struct hda_verb alc269_quanta_fl1_verbs[] = { | |
1902 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
1903 | + {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1904 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1905 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, ALC880_HP_EVENT | AC_USRSP_EN}, | |
1906 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
1907 | + {0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1908 | + { } | |
1909 | +}; | |
1910 | ||
1911 | - /* | |
1912 | - * Set up output mixers (0x0c - 0x0e) | |
1913 | - */ | |
1914 | - /* set vol=0 to output mixers */ | |
1915 | - {0x02, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
1916 | - {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
1917 | +/* toggle speaker-output according to the hp-jack state */ | |
1918 | +static void alc269_quanta_fl1_speaker_automute(struct hda_codec *codec) | |
1919 | +{ | |
1920 | + unsigned int present; | |
1921 | + unsigned char bits; | |
1922 | ||
1923 | - /* set up input amps for analog loopback */ | |
1924 | - /* Amp Indices: DAC = 0, mixer = 1 */ | |
1925 | - {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1926 | - {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
1927 | - {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1928 | - {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
1929 | - {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1930 | - {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
1931 | + present = snd_hda_codec_read(codec, 0x15, 0, | |
1932 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1933 | + bits = present ? AMP_IN_MUTE(0) : 0; | |
1934 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
1935 | + AMP_IN_MUTE(0), bits); | |
1936 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
1937 | + AMP_IN_MUTE(0), bits); | |
1938 | ||
1939 | - {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
1940 | - {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
1941 | - {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
1942 | - {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
1943 | - {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
1944 | - {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1945 | - {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
1946 | + snd_hda_codec_write(codec, 0x20, 0, | |
1947 | + AC_VERB_SET_COEF_INDEX, 0x0c); | |
1948 | + snd_hda_codec_write(codec, 0x20, 0, | |
1949 | + AC_VERB_SET_PROC_COEF, 0x680); | |
1950 | ||
1951 | - {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
1952 | - {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
1953 | - {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
1954 | - {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
1955 | - {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
1956 | - {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
1957 | - {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
1958 | + snd_hda_codec_write(codec, 0x20, 0, | |
1959 | + AC_VERB_SET_COEF_INDEX, 0x0c); | |
1960 | + snd_hda_codec_write(codec, 0x20, 0, | |
1961 | + AC_VERB_SET_PROC_COEF, 0x480); | |
1962 | +} | |
1963 | ||
1964 | - {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1965 | - {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
1966 | +static void alc269_quanta_fl1_mic_automute(struct hda_codec *codec) | |
1967 | +{ | |
1968 | + unsigned int present; | |
1969 | ||
1970 | - /* FIXME: use matrix-type input source selection */ | |
1971 | - /* Mixer elements: 0x18, 19, 1a, 1b, 1d, 0b */ | |
1972 | - /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */ | |
1973 | - {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
1974 | - {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
1975 | - {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
1976 | - {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, | |
1977 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
1978 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
1979 | + snd_hda_codec_write(codec, 0x23, 0, | |
1980 | + AC_VERB_SET_CONNECT_SEL, present ? 0x0 : 0x1); | |
1981 | +} | |
1982 | ||
1983 | - /* set EAPD */ | |
1984 | - {0x14, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
1985 | - {0x15, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
1986 | - { } | |
1987 | -}; | |
1988 | +static void alc269_quanta_fl1_unsol_event(struct hda_codec *codec, | |
1989 | + unsigned int res) | |
1990 | +{ | |
1991 | + if ((res >> 26) == ALC880_HP_EVENT) | |
1992 | + alc269_quanta_fl1_speaker_automute(codec); | |
1993 | + if ((res >> 26) == ALC880_MIC_EVENT) | |
1994 | + alc269_quanta_fl1_mic_automute(codec); | |
1995 | +} | |
1996 | + | |
1997 | +static void alc269_quanta_fl1_init_hook(struct hda_codec *codec) | |
1998 | +{ | |
1999 | + alc269_quanta_fl1_speaker_automute(codec); | |
2000 | + alc269_quanta_fl1_mic_automute(codec); | |
2001 | +} | |
2002 | ||
2003 | static struct hda_verb alc269_eeepc_dmic_init_verbs[] = { | |
2004 | {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, | |
2005 | @@ -11303,42 +12027,42 @@ static struct hda_verb alc269_eeepc_amic | |
2006 | static void alc269_speaker_automute(struct hda_codec *codec) | |
2007 | { | |
2008 | unsigned int present; | |
2009 | - unsigned int bits; | |
2010 | + unsigned char bits; | |
2011 | ||
2012 | present = snd_hda_codec_read(codec, 0x15, 0, | |
2013 | - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
2014 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
2015 | bits = present ? AMP_IN_MUTE(0) : 0; | |
2016 | snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2017 | - AMP_IN_MUTE(0), bits); | |
2018 | + AMP_IN_MUTE(0), bits); | |
2019 | snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2020 | - AMP_IN_MUTE(0), bits); | |
2021 | + AMP_IN_MUTE(0), bits); | |
2022 | } | |
2023 | ||
2024 | static void alc269_eeepc_dmic_automute(struct hda_codec *codec) | |
2025 | { | |
2026 | unsigned int present; | |
2027 | ||
2028 | - present = snd_hda_codec_read(codec, 0x18, 0, AC_VERB_GET_PIN_SENSE, 0) | |
2029 | - & AC_PINSENSE_PRESENCE; | |
2030 | - snd_hda_codec_write(codec, 0x23, 0, AC_VERB_SET_CONNECT_SEL, | |
2031 | - present ? 0 : 5); | |
2032 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
2033 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
2034 | + snd_hda_codec_write(codec, 0x23, 0, | |
2035 | + AC_VERB_SET_CONNECT_SEL, (present ? 0 : 5)); | |
2036 | } | |
2037 | ||
2038 | static void alc269_eeepc_amic_automute(struct hda_codec *codec) | |
2039 | { | |
2040 | unsigned int present; | |
2041 | ||
2042 | - present = snd_hda_codec_read(codec, 0x18, 0, AC_VERB_GET_PIN_SENSE, 0) | |
2043 | - & AC_PINSENSE_PRESENCE; | |
2044 | + present = snd_hda_codec_read(codec, 0x18, 0, | |
2045 | + AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; | |
2046 | snd_hda_codec_write(codec, 0x24, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2047 | - present ? AMP_IN_UNMUTE(0) : AMP_IN_MUTE(0)); | |
2048 | + 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
2049 | snd_hda_codec_write(codec, 0x24, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2050 | - present ? AMP_IN_MUTE(1) : AMP_IN_UNMUTE(1)); | |
2051 | + 0x7000 | (0x01 << 8) | (present ? 0x80 : 0)); | |
2052 | } | |
2053 | ||
2054 | /* unsolicited event for HP jack sensing */ | |
2055 | static void alc269_eeepc_dmic_unsol_event(struct hda_codec *codec, | |
2056 | - unsigned int res) | |
2057 | + unsigned int res) | |
2058 | { | |
2059 | if ((res >> 26) == ALC880_HP_EVENT) | |
2060 | alc269_speaker_automute(codec); | |
2061 | @@ -11355,7 +12079,7 @@ static void alc269_eeepc_dmic_inithook(s | |
2062 | ||
2063 | /* unsolicited event for HP jack sensing */ | |
2064 | static void alc269_eeepc_amic_unsol_event(struct hda_codec *codec, | |
2065 | - unsigned int res) | |
2066 | + unsigned int res) | |
2067 | { | |
2068 | if ((res >> 26) == ALC880_HP_EVENT) | |
2069 | alc269_speaker_automute(codec); | |
2070 | @@ -11370,6 +12094,76 @@ static void alc269_eeepc_amic_inithook(s | |
2071 | alc269_eeepc_amic_automute(codec); | |
2072 | } | |
2073 | ||
2074 | +/* | |
2075 | + * generic initialization of ADC, input mixers and output mixers | |
2076 | + */ | |
2077 | +static struct hda_verb alc269_init_verbs[] = { | |
2078 | + /* | |
2079 | + * Unmute ADC0 and set the default input to mic-in | |
2080 | + */ | |
2081 | + {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2082 | + | |
2083 | + /* Mute input amps (PCBeep, Line In, Mic 1 & Mic 2) of the | |
2084 | + * analog-loopback mixer widget | |
2085 | + * Note: PASD motherboards uses the Line In 2 as the input for | |
2086 | + * front panel mic (mic 2) | |
2087 | + */ | |
2088 | + /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */ | |
2089 | + {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2090 | + {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
2091 | + {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
2092 | + {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, | |
2093 | + {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
2094 | + | |
2095 | + /* | |
2096 | + * Set up output mixers (0x0c - 0x0e) | |
2097 | + */ | |
2098 | + /* set vol=0 to output mixers */ | |
2099 | + {0x02, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
2100 | + {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, | |
2101 | + | |
2102 | + /* set up input amps for analog loopback */ | |
2103 | + /* Amp Indices: DAC = 0, mixer = 1 */ | |
2104 | + {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2105 | + {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2106 | + {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2107 | + {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2108 | + {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2109 | + {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2110 | + | |
2111 | + {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
2112 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2113 | + {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
2114 | + {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
2115 | + {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, | |
2116 | + {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2117 | + {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2118 | + | |
2119 | + {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2120 | + {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2121 | + {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2122 | + {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2123 | + {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2124 | + {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2125 | + {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2126 | + | |
2127 | + {0x14, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
2128 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
2129 | + | |
2130 | + /* FIXME: use matrix-type input source selection */ | |
2131 | + /* Mixer elements: 0x18, 19, 1a, 1b, 1d, 0b */ | |
2132 | + /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */ | |
2133 | + {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2134 | + {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2135 | + {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, | |
2136 | + {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, | |
2137 | + | |
2138 | + /* set EAPD */ | |
2139 | + {0x14, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
2140 | + {0x15, AC_VERB_SET_EAPD_BTLENABLE, 2}, | |
2141 | + { } | |
2142 | +}; | |
2143 | + | |
2144 | /* add playback controls from the parsed DAC table */ | |
2145 | static int alc269_auto_create_multi_out_ctls(struct alc_spec *spec, | |
2146 | const struct auto_pin_cfg *cfg) | |
2147 | @@ -11470,7 +12264,7 @@ static int alc269_auto_create_multi_out_ | |
2148 | static int alc269_parse_auto_config(struct hda_codec *codec) | |
2149 | { | |
2150 | struct alc_spec *spec = codec->spec; | |
2151 | - int err; | |
2152 | + int i, err; | |
2153 | static hda_nid_t alc269_ignore[] = { 0x1d, 0 }; | |
2154 | ||
2155 | err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, | |
2156 | @@ -11493,6 +12287,13 @@ static int alc269_parse_auto_config(stru | |
2157 | if (spec->kctl_alloc) | |
2158 | spec->mixers[spec->num_mixers++] = spec->kctl_alloc; | |
2159 | ||
2160 | + /* create a beep mixer control if the pin 0x1d isn't assigned */ | |
2161 | + for (i = 0; i < ARRAY_SIZE(spec->autocfg.input_pins); i++) | |
2162 | + if (spec->autocfg.input_pins[i] == 0x1d) | |
2163 | + break; | |
2164 | + if (i >= ARRAY_SIZE(spec->autocfg.input_pins)) | |
2165 | + spec->mixers[spec->num_mixers++] = alc269_beep_mixer; | |
2166 | + | |
2167 | spec->init_verbs[spec->num_init_verbs++] = alc269_init_verbs; | |
2168 | spec->num_mux_defs = 1; | |
2169 | spec->input_mux = &spec->private_imux; | |
2170 | @@ -11525,21 +12326,27 @@ static void alc269_auto_init(struct hda_ | |
2171 | alc269_auto_init_hp_out(codec); | |
2172 | alc269_auto_init_analog_input(codec); | |
2173 | if (spec->unsol_event) | |
2174 | - alc_sku_automute(codec); | |
2175 | + alc_inithook(codec); | |
2176 | } | |
2177 | ||
2178 | /* | |
2179 | * configuration and preset | |
2180 | */ | |
2181 | static const char *alc269_models[ALC269_MODEL_LAST] = { | |
2182 | - [ALC269_BASIC] = "basic", | |
2183 | + [ALC269_BASIC] = "basic", | |
2184 | + [ALC269_QUANTA_FL1] = "quanta", | |
2185 | + [ALC269_ASUS_EEEPC_P703] = "eeepc-p703", | |
2186 | + [ALC269_ASUS_EEEPC_P901] = "eeepc-p901" | |
2187 | }; | |
2188 | ||
2189 | static struct snd_pci_quirk alc269_cfg_tbl[] = { | |
2190 | + SND_PCI_QUIRK(0x17aa, 0x3bf8, "Quanta FL1", ALC269_QUANTA_FL1), | |
2191 | SND_PCI_QUIRK(0x1043, 0x8330, "ASUS Eeepc P703 P900A", | |
2192 | ALC269_ASUS_EEEPC_P703), | |
2193 | SND_PCI_QUIRK(0x1043, 0x831a, "ASUS Eeepc P901", | |
2194 | ALC269_ASUS_EEEPC_P901), | |
2195 | + SND_PCI_QUIRK(0x1043, 0x834a, "ASUS Eeepc S101", | |
2196 | + ALC269_ASUS_EEEPC_P901), | |
2197 | {} | |
2198 | }; | |
2199 | ||
2200 | @@ -11554,17 +12361,29 @@ static struct alc_config_preset alc269_p | |
2201 | .channel_mode = alc269_modes, | |
2202 | .input_mux = &alc269_capture_source, | |
2203 | }, | |
2204 | - [ALC269_ASUS_EEEPC_P703] = { | |
2205 | - .mixers = { alc269_eeepc_mixer, alc269_epc_capture_mixer }, | |
2206 | - .init_verbs = { alc269_init_verbs, | |
2207 | - alc269_eeepc_amic_init_verbs }, | |
2208 | + [ALC269_QUANTA_FL1] = { | |
2209 | + .mixers = { alc269_quanta_fl1_mixer }, | |
2210 | + .init_verbs = { alc269_init_verbs, alc269_quanta_fl1_verbs }, | |
2211 | .num_dacs = ARRAY_SIZE(alc269_dac_nids), | |
2212 | .dac_nids = alc269_dac_nids, | |
2213 | .hp_nid = 0x03, | |
2214 | .num_channel_mode = ARRAY_SIZE(alc269_modes), | |
2215 | .channel_mode = alc269_modes, | |
2216 | - .input_mux = &alc269_eeepc_amic_capture_source, | |
2217 | - .unsol_event = alc269_eeepc_amic_unsol_event, | |
2218 | + .input_mux = &alc269_capture_source, | |
2219 | + .unsol_event = alc269_quanta_fl1_unsol_event, | |
2220 | + .init_hook = alc269_quanta_fl1_init_hook, | |
2221 | + }, | |
2222 | + [ALC269_ASUS_EEEPC_P703] = { | |
2223 | + .mixers = { alc269_eeepc_mixer, alc269_epc_capture_mixer }, | |
2224 | + .init_verbs = { alc269_init_verbs, | |
2225 | + alc269_eeepc_amic_init_verbs }, | |
2226 | + .num_dacs = ARRAY_SIZE(alc269_dac_nids), | |
2227 | + .dac_nids = alc269_dac_nids, | |
2228 | + .hp_nid = 0x03, | |
2229 | + .num_channel_mode = ARRAY_SIZE(alc269_modes), | |
2230 | + .channel_mode = alc269_modes, | |
2231 | + .input_mux = &alc269_eeepc_amic_capture_source, | |
2232 | + .unsol_event = alc269_eeepc_amic_unsol_event, | |
2233 | .init_hook = alc269_eeepc_amic_inithook, | |
2234 | }, | |
2235 | [ALC269_ASUS_EEEPC_P901] = { | |
2236 | @@ -11835,7 +12654,7 @@ static struct snd_kcontrol_new alc861_to | |
2237 | HDA_CODEC_MUTE("Master Playback Switch", 0x03, 0x0, HDA_OUTPUT), | |
2238 | HDA_CODEC_VOLUME("Mic Playback Volume", 0x15, 0x01, HDA_INPUT), | |
2239 | HDA_CODEC_MUTE("Mic Playback Switch", 0x15, 0x01, HDA_INPUT), | |
2240 | - | |
2241 | + | |
2242 | /*Capture mixer control */ | |
2243 | HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT), | |
2244 | HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT), | |
2245 | @@ -11978,20 +12797,20 @@ static struct hda_verb alc861_base_init_ | |
2246 | /* route front mic to ADC1*/ | |
2247 | {0x08, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
2248 | {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2249 | - | |
2250 | + | |
2251 | /* Unmute DAC0~3 & spdif out*/ | |
2252 | {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2253 | {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2254 | {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2255 | {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2256 | {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2257 | - | |
2258 | + | |
2259 | /* Unmute Mixer 14 (mic) 1c (Line in)*/ | |
2260 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2261 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2262 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2263 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2264 | - | |
2265 | + | |
2266 | /* Unmute Stereo Mixer 15 */ | |
2267 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2268 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2269 | @@ -12047,13 +12866,13 @@ static struct hda_verb alc861_threestack | |
2270 | {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2271 | {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2272 | {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2273 | - | |
2274 | + | |
2275 | /* Unmute Mixer 14 (mic) 1c (Line in)*/ | |
2276 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2277 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2278 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2279 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2280 | - | |
2281 | + | |
2282 | /* Unmute Stereo Mixer 15 */ | |
2283 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2284 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2285 | @@ -12109,13 +12928,13 @@ static struct hda_verb alc861_uniwill_m3 | |
2286 | {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2287 | {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2288 | {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2289 | - | |
2290 | + | |
2291 | /* Unmute Mixer 14 (mic) 1c (Line in)*/ | |
2292 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2293 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2294 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2295 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2296 | - | |
2297 | + | |
2298 | /* Unmute Stereo Mixer 15 */ | |
2299 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2300 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2301 | @@ -12180,7 +12999,7 @@ static struct hda_verb alc861_asus_init_ | |
2302 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2303 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2304 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2305 | - | |
2306 | + | |
2307 | /* Unmute Stereo Mixer 15 */ | |
2308 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2309 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2310 | @@ -12217,20 +13036,20 @@ static struct hda_verb alc861_auto_init_ | |
2311 | */ | |
2312 | /* {0x08, AC_VERB_SET_CONNECT_SEL, 0x00}, */ | |
2313 | {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2314 | - | |
2315 | + | |
2316 | /* Unmute DAC0~3 & spdif out*/ | |
2317 | {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2318 | {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2319 | {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2320 | {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, | |
2321 | {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2322 | - | |
2323 | + | |
2324 | /* Unmute Mixer 14 (mic) 1c (Line in)*/ | |
2325 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2326 | {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2327 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2328 | {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2329 | - | |
2330 | + | |
2331 | /* Unmute Stereo Mixer 15 */ | |
2332 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, | |
2333 | {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2334 | @@ -12589,7 +13408,7 @@ static void alc861_auto_init(struct hda_ | |
2335 | alc861_auto_init_hp_out(codec); | |
2336 | alc861_auto_init_analog_input(codec); | |
2337 | if (spec->unsol_event) | |
2338 | - alc_sku_automute(codec); | |
2339 | + alc_inithook(codec); | |
2340 | } | |
2341 | ||
2342 | #ifdef CONFIG_SND_HDA_POWER_SAVE | |
2343 | @@ -12806,7 +13625,7 @@ static int patch_alc861(struct hda_codec | |
2344 | if (!spec->loopback.amplist) | |
2345 | spec->loopback.amplist = alc861_loopbacks; | |
2346 | #endif | |
2347 | - | |
2348 | + | |
2349 | return 0; | |
2350 | } | |
2351 | ||
2352 | @@ -13060,7 +13879,7 @@ static struct snd_kcontrol_new alc861vd_ | |
2353 | HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2354 | HDA_CODEC_VOLUME("ATAPI Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
2355 | HDA_CODEC_MUTE("ATAPI Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
2356 | - | |
2357 | + | |
2358 | { } /* end */ | |
2359 | }; | |
2360 | ||
2361 | @@ -13205,7 +14024,7 @@ static struct hda_verb alc861vd_lenovo_u | |
2362 | {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2363 | {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)}, | |
2364 | {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2365 | - {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2366 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2367 | {} | |
2368 | }; | |
2369 | ||
2370 | @@ -13267,7 +14086,7 @@ static struct hda_verb alc861vd_dallas_v | |
2371 | {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
2372 | {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2373 | {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, | |
2374 | - | |
2375 | + | |
2376 | {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
2377 | {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2378 | {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT}, | |
2379 | @@ -13292,7 +14111,7 @@ static struct hda_verb alc861vd_dallas_v | |
2380 | {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, | |
2381 | ||
2382 | {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2383 | - {0x09, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
2384 | + {0x09, AC_VERB_SET_CONNECT_SEL, 0x00}, | |
2385 | {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2386 | ||
2387 | { } /* end */ | |
2388 | @@ -13451,7 +14270,7 @@ static struct alc_config_preset alc861vd | |
2389 | .input_mux = &alc861vd_hp_capture_source, | |
2390 | .unsol_event = alc861vd_dallas_unsol_event, | |
2391 | .init_hook = alc861vd_dallas_automute, | |
2392 | - }, | |
2393 | + }, | |
2394 | }; | |
2395 | ||
2396 | /* | |
2397 | @@ -13702,7 +14521,7 @@ static void alc861vd_auto_init(struct hd | |
2398 | alc861vd_auto_init_analog_input(codec); | |
2399 | alc861vd_auto_init_input_src(codec); | |
2400 | if (spec->unsol_event) | |
2401 | - alc_sku_automute(codec); | |
2402 | + alc_inithook(codec); | |
2403 | } | |
2404 | ||
2405 | static int patch_alc861vd(struct hda_codec *codec) | |
2406 | @@ -14031,13 +14850,120 @@ static struct snd_kcontrol_new alc662_ee | |
2407 | { } /* end */ | |
2408 | }; | |
2409 | ||
2410 | +static struct hda_bind_ctls alc663_asus_bind_master_vol = { | |
2411 | + .ops = &snd_hda_bind_vol, | |
2412 | + .values = { | |
2413 | + HDA_COMPOSE_AMP_VAL(0x02, 3, 0, HDA_OUTPUT), | |
2414 | + HDA_COMPOSE_AMP_VAL(0x03, 3, 0, HDA_OUTPUT), | |
2415 | + 0 | |
2416 | + }, | |
2417 | +}; | |
2418 | + | |
2419 | +static struct hda_bind_ctls alc663_asus_one_bind_switch = { | |
2420 | + .ops = &snd_hda_bind_sw, | |
2421 | + .values = { | |
2422 | + HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
2423 | + HDA_COMPOSE_AMP_VAL(0x21, 3, 0, HDA_OUTPUT), | |
2424 | + 0 | |
2425 | + }, | |
2426 | +}; | |
2427 | + | |
2428 | static struct snd_kcontrol_new alc663_m51va_mixer[] = { | |
2429 | + HDA_BIND_VOL("Master Playback Volume", &alc663_asus_bind_master_vol), | |
2430 | + HDA_BIND_SW("Master Playback Switch", &alc663_asus_one_bind_switch), | |
2431 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2432 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2433 | + { } /* end */ | |
2434 | +}; | |
2435 | + | |
2436 | +static struct hda_bind_ctls alc663_asus_tree_bind_switch = { | |
2437 | + .ops = &snd_hda_bind_sw, | |
2438 | + .values = { | |
2439 | + HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
2440 | + HDA_COMPOSE_AMP_VAL(0x15, 3, 0, HDA_OUTPUT), | |
2441 | + HDA_COMPOSE_AMP_VAL(0x21, 3, 0, HDA_OUTPUT), | |
2442 | + 0 | |
2443 | + }, | |
2444 | +}; | |
2445 | + | |
2446 | +static struct snd_kcontrol_new alc663_two_hp_m1_mixer[] = { | |
2447 | + HDA_BIND_VOL("Master Playback Volume", &alc663_asus_bind_master_vol), | |
2448 | + HDA_BIND_SW("Master Playback Switch", &alc663_asus_tree_bind_switch), | |
2449 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2450 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2451 | + HDA_CODEC_VOLUME("F-Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
2452 | + HDA_CODEC_MUTE("F-Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
2453 | + | |
2454 | + { } /* end */ | |
2455 | +}; | |
2456 | + | |
2457 | +static struct hda_bind_ctls alc663_asus_four_bind_switch = { | |
2458 | + .ops = &snd_hda_bind_sw, | |
2459 | + .values = { | |
2460 | + HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
2461 | + HDA_COMPOSE_AMP_VAL(0x15, 3, 0, HDA_OUTPUT), | |
2462 | + HDA_COMPOSE_AMP_VAL(0x1b, 3, 0, HDA_OUTPUT), | |
2463 | + 0 | |
2464 | + }, | |
2465 | +}; | |
2466 | + | |
2467 | +static struct snd_kcontrol_new alc663_two_hp_m2_mixer[] = { | |
2468 | + HDA_BIND_VOL("Master Playback Volume", &alc663_asus_bind_master_vol), | |
2469 | + HDA_BIND_SW("Master Playback Switch", &alc663_asus_four_bind_switch), | |
2470 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2471 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2472 | + HDA_CODEC_VOLUME("F-Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
2473 | + HDA_CODEC_MUTE("F-Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
2474 | + { } /* end */ | |
2475 | +}; | |
2476 | + | |
2477 | +static struct snd_kcontrol_new alc662_1bjd_mixer[] = { | |
2478 | HDA_CODEC_VOLUME("Speaker Playback Volume", 0x02, 0x0, HDA_OUTPUT), | |
2479 | HDA_CODEC_MUTE("Speaker Playback Switch", 0x14, 0x0, HDA_OUTPUT), | |
2480 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT), | |
2481 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2482 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2483 | + HDA_CODEC_VOLUME("F-Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
2484 | + HDA_CODEC_MUTE("F-Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
2485 | + { } /* end */ | |
2486 | +}; | |
2487 | + | |
2488 | +static struct hda_bind_ctls alc663_asus_two_bind_master_vol = { | |
2489 | + .ops = &snd_hda_bind_vol, | |
2490 | + .values = { | |
2491 | + HDA_COMPOSE_AMP_VAL(0x02, 3, 0, HDA_OUTPUT), | |
2492 | + HDA_COMPOSE_AMP_VAL(0x04, 3, 0, HDA_OUTPUT), | |
2493 | + 0 | |
2494 | + }, | |
2495 | +}; | |
2496 | + | |
2497 | +static struct hda_bind_ctls alc663_asus_two_bind_switch = { | |
2498 | + .ops = &snd_hda_bind_sw, | |
2499 | + .values = { | |
2500 | + HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT), | |
2501 | + HDA_COMPOSE_AMP_VAL(0x16, 3, 0, HDA_OUTPUT), | |
2502 | + 0 | |
2503 | + }, | |
2504 | +}; | |
2505 | + | |
2506 | +static struct snd_kcontrol_new alc663_asus_21jd_clfe_mixer[] = { | |
2507 | + HDA_BIND_VOL("Master Playback Volume", | |
2508 | + &alc663_asus_two_bind_master_vol), | |
2509 | + HDA_BIND_SW("Master Playback Switch", &alc663_asus_two_bind_switch), | |
2510 | + HDA_CODEC_VOLUME("Headphone Playback Volume", 0x03, 0x0, HDA_OUTPUT), | |
2511 | HDA_CODEC_MUTE("Headphone Playback Switch", 0x21, 0x0, HDA_OUTPUT), | |
2512 | HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2513 | HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2514 | - HDA_CODEC_MUTE("DMic Playback Switch", 0x23, 0x9, HDA_INPUT), | |
2515 | + { } /* end */ | |
2516 | +}; | |
2517 | + | |
2518 | +static struct snd_kcontrol_new alc663_asus_15jd_clfe_mixer[] = { | |
2519 | + HDA_BIND_VOL("Master Playback Volume", &alc663_asus_bind_master_vol), | |
2520 | + HDA_BIND_SW("Master Playback Switch", &alc663_asus_two_bind_switch), | |
2521 | + HDA_CODEC_VOLUME("Headphone Playback Volume", 0x03, 0x0, HDA_OUTPUT), | |
2522 | + HDA_CODEC_MUTE("Headphone Playback Switch", 0x15, 0x0, HDA_OUTPUT), | |
2523 | + HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2524 | + HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2525 | { } /* end */ | |
2526 | }; | |
2527 | ||
2528 | @@ -14222,14 +15148,81 @@ static struct hda_verb alc663_auto_init_ | |
2529 | }; | |
2530 | ||
2531 | static struct hda_verb alc663_m51va_init_verbs[] = { | |
2532 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2533 | + {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2534 | {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2535 | {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2536 | - {0x21, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Headphone */ | |
2537 | + {0x21, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Headphone */ | |
2538 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2539 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(9)}, | |
2540 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2541 | + {0x21, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2542 | + {} | |
2543 | +}; | |
2544 | ||
2545 | - {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(9)}, | |
2546 | +static struct hda_verb alc663_21jd_amic_init_verbs[] = { | |
2547 | + {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2548 | + {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2549 | + {0x21, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Headphone */ | |
2550 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2551 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2552 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2553 | + {0x21, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2554 | + {} | |
2555 | +}; | |
2556 | + | |
2557 | +static struct hda_verb alc662_1bjd_amic_init_verbs[] = { | |
2558 | + {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2559 | + {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2560 | + {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2561 | + {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00}, /* Headphone */ | |
2562 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2563 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2564 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2565 | + {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2566 | + {} | |
2567 | +}; | |
2568 | + | |
2569 | +static struct hda_verb alc663_15jd_amic_init_verbs[] = { | |
2570 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2571 | + {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2572 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Headphone */ | |
2573 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2574 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2575 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2576 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2577 | + {} | |
2578 | +}; | |
2579 | ||
2580 | +static struct hda_verb alc663_two_hp_amic_m1_init_verbs[] = { | |
2581 | + {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2582 | + {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2583 | + {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2584 | + {0x21, AC_VERB_SET_CONNECT_SEL, 0x0}, /* Headphone */ | |
2585 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2586 | + {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2587 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x0}, /* Headphone */ | |
2588 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2589 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2590 | {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2591 | {0x21, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2592 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2593 | + {} | |
2594 | +}; | |
2595 | + | |
2596 | +static struct hda_verb alc663_two_hp_amic_m2_init_verbs[] = { | |
2597 | + {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN}, | |
2598 | + {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2599 | + {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2600 | + {0x1b, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Headphone */ | |
2601 | + {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP}, | |
2602 | + {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, | |
2603 | + {0x15, AC_VERB_SET_CONNECT_SEL, 0x01}, /* Headphone */ | |
2604 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2605 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)}, | |
2606 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2607 | + {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2608 | + {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2609 | {} | |
2610 | }; | |
2611 | ||
2612 | @@ -14258,6 +15251,14 @@ static struct hda_verb alc663_g50v_init_ | |
2613 | {} | |
2614 | }; | |
2615 | ||
2616 | +static struct hda_verb alc662_ecs_init_verbs[] = { | |
2617 | + {0x09, AC_VERB_SET_AMP_GAIN_MUTE, 0x701f}, | |
2618 | + {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, | |
2619 | + {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_MIC_EVENT}, | |
2620 | + {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC880_HP_EVENT}, | |
2621 | + {} | |
2622 | +}; | |
2623 | + | |
2624 | /* capture mixer elements */ | |
2625 | static struct snd_kcontrol_new alc662_capture_mixer[] = { | |
2626 | HDA_CODEC_VOLUME("Capture Volume", 0x09, 0x0, HDA_INPUT), | |
2627 | @@ -14277,6 +15278,12 @@ static struct snd_kcontrol_new alc662_ca | |
2628 | { } /* end */ | |
2629 | }; | |
2630 | ||
2631 | +static struct snd_kcontrol_new alc662_auto_capture_mixer[] = { | |
2632 | + HDA_CODEC_VOLUME("Capture Volume", 0x09, 0x0, HDA_INPUT), | |
2633 | + HDA_CODEC_MUTE("Capture Switch", 0x09, 0x0, HDA_INPUT), | |
2634 | + { } /* end */ | |
2635 | +}; | |
2636 | + | |
2637 | static void alc662_lenovo_101e_ispeaker_automute(struct hda_codec *codec) | |
2638 | { | |
2639 | unsigned int present; | |
2640 | @@ -14357,12 +15364,12 @@ static void alc662_eeepc_ep20_automute(s | |
2641 | if (present) { | |
2642 | /* mute internal speaker */ | |
2643 | snd_hda_codec_amp_stereo(codec, 0x1b, HDA_OUTPUT, 0, | |
2644 | - HDA_AMP_MUTE, HDA_AMP_MUTE); | |
2645 | + HDA_AMP_MUTE, HDA_AMP_MUTE); | |
2646 | } else { | |
2647 | /* unmute internal speaker if necessary */ | |
2648 | mute = snd_hda_codec_amp_read(codec, 0x14, 0, HDA_OUTPUT, 0); | |
2649 | snd_hda_codec_amp_stereo(codec, 0x1b, HDA_OUTPUT, 0, | |
2650 | - HDA_AMP_MUTE, mute); | |
2651 | + HDA_AMP_MUTE, mute); | |
2652 | } | |
2653 | } | |
2654 | ||
2655 | @@ -14385,11 +15392,108 @@ static void alc663_m51va_speaker_automut | |
2656 | unsigned char bits; | |
2657 | ||
2658 | present = snd_hda_codec_read(codec, 0x21, 0, | |
2659 | - AC_VERB_GET_PIN_SENSE, 0) | |
2660 | - & AC_PINSENSE_PRESENCE; | |
2661 | + AC_VERB_GET_PIN_SENSE, 0) | |
2662 | + & AC_PINSENSE_PRESENCE; | |
2663 | bits = present ? HDA_AMP_MUTE : 0; | |
2664 | - snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, | |
2665 | - HDA_AMP_MUTE, bits); | |
2666 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2667 | + AMP_IN_MUTE(0), bits); | |
2668 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2669 | + AMP_IN_MUTE(0), bits); | |
2670 | +} | |
2671 | + | |
2672 | +static void alc663_21jd_two_speaker_automute(struct hda_codec *codec) | |
2673 | +{ | |
2674 | + unsigned int present; | |
2675 | + unsigned char bits; | |
2676 | + | |
2677 | + present = snd_hda_codec_read(codec, 0x21, 0, | |
2678 | + AC_VERB_GET_PIN_SENSE, 0) | |
2679 | + & AC_PINSENSE_PRESENCE; | |
2680 | + bits = present ? HDA_AMP_MUTE : 0; | |
2681 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2682 | + AMP_IN_MUTE(0), bits); | |
2683 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2684 | + AMP_IN_MUTE(0), bits); | |
2685 | + snd_hda_codec_amp_stereo(codec, 0x0e, HDA_INPUT, 0, | |
2686 | + AMP_IN_MUTE(0), bits); | |
2687 | + snd_hda_codec_amp_stereo(codec, 0x0e, HDA_INPUT, 1, | |
2688 | + AMP_IN_MUTE(0), bits); | |
2689 | +} | |
2690 | + | |
2691 | +static void alc663_15jd_two_speaker_automute(struct hda_codec *codec) | |
2692 | +{ | |
2693 | + unsigned int present; | |
2694 | + unsigned char bits; | |
2695 | + | |
2696 | + present = snd_hda_codec_read(codec, 0x15, 0, | |
2697 | + AC_VERB_GET_PIN_SENSE, 0) | |
2698 | + & AC_PINSENSE_PRESENCE; | |
2699 | + bits = present ? HDA_AMP_MUTE : 0; | |
2700 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2701 | + AMP_IN_MUTE(0), bits); | |
2702 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2703 | + AMP_IN_MUTE(0), bits); | |
2704 | + snd_hda_codec_amp_stereo(codec, 0x0e, HDA_INPUT, 0, | |
2705 | + AMP_IN_MUTE(0), bits); | |
2706 | + snd_hda_codec_amp_stereo(codec, 0x0e, HDA_INPUT, 1, | |
2707 | + AMP_IN_MUTE(0), bits); | |
2708 | +} | |
2709 | + | |
2710 | +static void alc662_f5z_speaker_automute(struct hda_codec *codec) | |
2711 | +{ | |
2712 | + unsigned int present; | |
2713 | + unsigned char bits; | |
2714 | + | |
2715 | + present = snd_hda_codec_read(codec, 0x1b, 0, | |
2716 | + AC_VERB_GET_PIN_SENSE, 0) | |
2717 | + & AC_PINSENSE_PRESENCE; | |
2718 | + bits = present ? 0 : PIN_OUT; | |
2719 | + snd_hda_codec_write(codec, 0x14, 0, | |
2720 | + AC_VERB_SET_PIN_WIDGET_CONTROL, bits); | |
2721 | +} | |
2722 | + | |
2723 | +static void alc663_two_hp_m1_speaker_automute(struct hda_codec *codec) | |
2724 | +{ | |
2725 | + unsigned int present1, present2; | |
2726 | + | |
2727 | + present1 = snd_hda_codec_read(codec, 0x21, 0, | |
2728 | + AC_VERB_GET_PIN_SENSE, 0) | |
2729 | + & AC_PINSENSE_PRESENCE; | |
2730 | + present2 = snd_hda_codec_read(codec, 0x15, 0, | |
2731 | + AC_VERB_GET_PIN_SENSE, 0) | |
2732 | + & AC_PINSENSE_PRESENCE; | |
2733 | + | |
2734 | + if (present1 || present2) { | |
2735 | + snd_hda_codec_write_cache(codec, 0x14, 0, | |
2736 | + AC_VERB_SET_PIN_WIDGET_CONTROL, 0); | |
2737 | + } else { | |
2738 | + snd_hda_codec_write_cache(codec, 0x14, 0, | |
2739 | + AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT); | |
2740 | + } | |
2741 | +} | |
2742 | + | |
2743 | +static void alc663_two_hp_m2_speaker_automute(struct hda_codec *codec) | |
2744 | +{ | |
2745 | + unsigned int present1, present2; | |
2746 | + | |
2747 | + present1 = snd_hda_codec_read(codec, 0x1b, 0, | |
2748 | + AC_VERB_GET_PIN_SENSE, 0) | |
2749 | + & AC_PINSENSE_PRESENCE; | |
2750 | + present2 = snd_hda_codec_read(codec, 0x15, 0, | |
2751 | + AC_VERB_GET_PIN_SENSE, 0) | |
2752 | + & AC_PINSENSE_PRESENCE; | |
2753 | + | |
2754 | + if (present1 || present2) { | |
2755 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2756 | + AMP_IN_MUTE(0), AMP_IN_MUTE(0)); | |
2757 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2758 | + AMP_IN_MUTE(0), AMP_IN_MUTE(0)); | |
2759 | + } else { | |
2760 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, | |
2761 | + AMP_IN_MUTE(0), 0); | |
2762 | + snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 1, | |
2763 | + AMP_IN_MUTE(0), 0); | |
2764 | + } | |
2765 | } | |
2766 | ||
2767 | static void alc663_m51va_mic_automute(struct hda_codec *codec) | |
2768 | @@ -14397,16 +15501,16 @@ static void alc663_m51va_mic_automute(st | |
2769 | unsigned int present; | |
2770 | ||
2771 | present = snd_hda_codec_read(codec, 0x18, 0, | |
2772 | - AC_VERB_GET_PIN_SENSE, 0) | |
2773 | - & AC_PINSENSE_PRESENCE; | |
2774 | + AC_VERB_GET_PIN_SENSE, 0) | |
2775 | + & AC_PINSENSE_PRESENCE; | |
2776 | snd_hda_codec_write_cache(codec, 0x22, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2777 | - 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
2778 | + 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
2779 | snd_hda_codec_write_cache(codec, 0x23, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2780 | - 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
2781 | + 0x7000 | (0x00 << 8) | (present ? 0 : 0x80)); | |
2782 | snd_hda_codec_write_cache(codec, 0x22, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2783 | - 0x7000 | (0x09 << 8) | (present ? 0x80 : 0)); | |
2784 | + 0x7000 | (0x09 << 8) | (present ? 0x80 : 0)); | |
2785 | snd_hda_codec_write_cache(codec, 0x23, 0, AC_VERB_SET_AMP_GAIN_MUTE, | |
2786 | - 0x7000 | (0x09 << 8) | (present ? 0x80 : 0)); | |
2787 | + 0x7000 | (0x09 << 8) | (present ? 0x80 : 0)); | |
2788 | } | |
2789 | ||
2790 | static void alc663_m51va_unsol_event(struct hda_codec *codec, | |
2791 | @@ -14428,6 +15532,121 @@ static void alc663_m51va_inithook(struct | |
2792 | alc663_m51va_mic_automute(codec); | |
2793 | } | |
2794 | ||
2795 | +/* ***************** Mode1 ******************************/ | |
2796 | +static void alc663_mode1_unsol_event(struct hda_codec *codec, | |
2797 | + unsigned int res) | |
2798 | +{ | |
2799 | + switch (res >> 26) { | |
2800 | + case ALC880_HP_EVENT: | |
2801 | + alc663_m51va_speaker_automute(codec); | |
2802 | + break; | |
2803 | + case ALC880_MIC_EVENT: | |
2804 | + alc662_eeepc_mic_automute(codec); | |
2805 | + break; | |
2806 | + } | |
2807 | +} | |
2808 | + | |
2809 | +static void alc663_mode1_inithook(struct hda_codec *codec) | |
2810 | +{ | |
2811 | + alc663_m51va_speaker_automute(codec); | |
2812 | + alc662_eeepc_mic_automute(codec); | |
2813 | +} | |
2814 | +/* ***************** Mode2 ******************************/ | |
2815 | +static void alc662_mode2_unsol_event(struct hda_codec *codec, | |
2816 | + unsigned int res) | |
2817 | +{ | |
2818 | + switch (res >> 26) { | |
2819 | + case ALC880_HP_EVENT: | |
2820 | + alc662_f5z_speaker_automute(codec); | |
2821 | + break; | |
2822 | + case ALC880_MIC_EVENT: | |
2823 | + alc662_eeepc_mic_automute(codec); | |
2824 | + break; | |
2825 | + } | |
2826 | +} | |
2827 | + | |
2828 | +static void alc662_mode2_inithook(struct hda_codec *codec) | |
2829 | +{ | |
2830 | + alc662_f5z_speaker_automute(codec); | |
2831 | + alc662_eeepc_mic_automute(codec); | |
2832 | +} | |
2833 | +/* ***************** Mode3 ******************************/ | |
2834 | +static void alc663_mode3_unsol_event(struct hda_codec *codec, | |
2835 | + unsigned int res) | |
2836 | +{ | |
2837 | + switch (res >> 26) { | |
2838 | + case ALC880_HP_EVENT: | |
2839 | + alc663_two_hp_m1_speaker_automute(codec); | |
2840 | + break; | |
2841 | + case ALC880_MIC_EVENT: | |
2842 | + alc662_eeepc_mic_automute(codec); | |
2843 | + break; | |
2844 | + } | |
2845 | +} | |
2846 | + | |
2847 | +static void alc663_mode3_inithook(struct hda_codec *codec) | |
2848 | +{ | |
2849 | + alc663_two_hp_m1_speaker_automute(codec); | |
2850 | + alc662_eeepc_mic_automute(codec); | |
2851 | +} | |
2852 | +/* ***************** Mode4 ******************************/ | |
2853 | +static void alc663_mode4_unsol_event(struct hda_codec *codec, | |
2854 | + unsigned int res) | |
2855 | +{ | |
2856 | + switch (res >> 26) { | |
2857 | + case ALC880_HP_EVENT: | |
2858 | + alc663_21jd_two_speaker_automute(codec); | |
2859 | + break; | |
2860 | + case ALC880_MIC_EVENT: | |
2861 | + alc662_eeepc_mic_automute(codec); | |
2862 | + break; | |
2863 | + } | |
2864 | +} | |
2865 | + | |
2866 | +static void alc663_mode4_inithook(struct hda_codec *codec) | |
2867 | +{ | |
2868 | + alc663_21jd_two_speaker_automute(codec); | |
2869 | + alc662_eeepc_mic_automute(codec); | |
2870 | +} | |
2871 | +/* ***************** Mode5 ******************************/ | |
2872 | +static void alc663_mode5_unsol_event(struct hda_codec *codec, | |
2873 | + unsigned int res) | |
2874 | +{ | |
2875 | + switch (res >> 26) { | |
2876 | + case ALC880_HP_EVENT: | |
2877 | + alc663_15jd_two_speaker_automute(codec); | |
2878 | + break; | |
2879 | + case ALC880_MIC_EVENT: | |
2880 | + alc662_eeepc_mic_automute(codec); | |
2881 | + break; | |
2882 | + } | |
2883 | +} | |
2884 | + | |
2885 | +static void alc663_mode5_inithook(struct hda_codec *codec) | |
2886 | +{ | |
2887 | + alc663_15jd_two_speaker_automute(codec); | |
2888 | + alc662_eeepc_mic_automute(codec); | |
2889 | +} | |
2890 | +/* ***************** Mode6 ******************************/ | |
2891 | +static void alc663_mode6_unsol_event(struct hda_codec *codec, | |
2892 | + unsigned int res) | |
2893 | +{ | |
2894 | + switch (res >> 26) { | |
2895 | + case ALC880_HP_EVENT: | |
2896 | + alc663_two_hp_m2_speaker_automute(codec); | |
2897 | + break; | |
2898 | + case ALC880_MIC_EVENT: | |
2899 | + alc662_eeepc_mic_automute(codec); | |
2900 | + break; | |
2901 | + } | |
2902 | +} | |
2903 | + | |
2904 | +static void alc663_mode6_inithook(struct hda_codec *codec) | |
2905 | +{ | |
2906 | + alc663_two_hp_m2_speaker_automute(codec); | |
2907 | + alc662_eeepc_mic_automute(codec); | |
2908 | +} | |
2909 | + | |
2910 | static void alc663_g71v_hp_automute(struct hda_codec *codec) | |
2911 | { | |
2912 | unsigned int present; | |
2913 | @@ -14498,6 +15717,46 @@ static void alc663_g50v_inithook(struct | |
2914 | alc662_eeepc_mic_automute(codec); | |
2915 | } | |
2916 | ||
2917 | +/* bind hp and internal speaker mute (with plug check) */ | |
2918 | +static int alc662_ecs_master_sw_put(struct snd_kcontrol *kcontrol, | |
2919 | + struct snd_ctl_elem_value *ucontrol) | |
2920 | +{ | |
2921 | + struct hda_codec *codec = snd_kcontrol_chip(kcontrol); | |
2922 | + long *valp = ucontrol->value.integer.value; | |
2923 | + int change; | |
2924 | + | |
2925 | + change = snd_hda_codec_amp_update(codec, 0x1b, 0, HDA_OUTPUT, 0, | |
2926 | + HDA_AMP_MUTE, | |
2927 | + valp[0] ? 0 : HDA_AMP_MUTE); | |
2928 | + change |= snd_hda_codec_amp_update(codec, 0x1b, 1, HDA_OUTPUT, 0, | |
2929 | + HDA_AMP_MUTE, | |
2930 | + valp[1] ? 0 : HDA_AMP_MUTE); | |
2931 | + if (change) | |
2932 | + alc262_hippo1_automute(codec); | |
2933 | + return change; | |
2934 | +} | |
2935 | + | |
2936 | +static struct snd_kcontrol_new alc662_ecs_mixer[] = { | |
2937 | + HDA_CODEC_VOLUME("Master Playback Volume", 0x02, 0x0, HDA_OUTPUT), | |
2938 | + { | |
2939 | + .iface = SNDRV_CTL_ELEM_IFACE_MIXER, | |
2940 | + .name = "Master Playback Switch", | |
2941 | + .info = snd_hda_mixer_amp_switch_info, | |
2942 | + .get = snd_hda_mixer_amp_switch_get, | |
2943 | + .put = alc662_ecs_master_sw_put, | |
2944 | + .private_value = HDA_COMPOSE_AMP_VAL(0x1b, 3, 0, HDA_OUTPUT), | |
2945 | + }, | |
2946 | + | |
2947 | + HDA_CODEC_VOLUME("e-Mic/LineIn Boost", 0x18, 0, HDA_INPUT), | |
2948 | + HDA_CODEC_VOLUME("e-Mic/LineIn Playback Volume", 0x0b, 0x0, HDA_INPUT), | |
2949 | + HDA_CODEC_MUTE("e-Mic/LineIn Playback Switch", 0x0b, 0x0, HDA_INPUT), | |
2950 | + | |
2951 | + HDA_CODEC_VOLUME("i-Mic Boost", 0x19, 0, HDA_INPUT), | |
2952 | + HDA_CODEC_VOLUME("i-Mic Playback Volume", 0x0b, 0x1, HDA_INPUT), | |
2953 | + HDA_CODEC_MUTE("i-Mic Playback Switch", 0x0b, 0x1, HDA_INPUT), | |
2954 | + { } /* end */ | |
2955 | +}; | |
2956 | + | |
2957 | #ifdef CONFIG_SND_HDA_POWER_SAVE | |
2958 | #define alc662_loopbacks alc880_loopbacks | |
2959 | #endif | |
2960 | @@ -14520,21 +15779,68 @@ static const char *alc662_models[ALC662_ | |
2961 | [ALC662_LENOVO_101E] = "lenovo-101e", | |
2962 | [ALC662_ASUS_EEEPC_P701] = "eeepc-p701", | |
2963 | [ALC662_ASUS_EEEPC_EP20] = "eeepc-ep20", | |
2964 | + [ALC662_ECS] = "ecs", | |
2965 | [ALC663_ASUS_M51VA] = "m51va", | |
2966 | [ALC663_ASUS_G71V] = "g71v", | |
2967 | [ALC663_ASUS_H13] = "h13", | |
2968 | [ALC663_ASUS_G50V] = "g50v", | |
2969 | + [ALC663_ASUS_MODE1] = "asus-mode1", | |
2970 | + [ALC662_ASUS_MODE2] = "asus-mode2", | |
2971 | + [ALC663_ASUS_MODE3] = "asus-mode3", | |
2972 | + [ALC663_ASUS_MODE4] = "asus-mode4", | |
2973 | + [ALC663_ASUS_MODE5] = "asus-mode5", | |
2974 | + [ALC663_ASUS_MODE6] = "asus-mode6", | |
2975 | [ALC662_AUTO] = "auto", | |
2976 | }; | |
2977 | ||
2978 | static struct snd_pci_quirk alc662_cfg_tbl[] = { | |
2979 | - SND_PCI_QUIRK(0x1043, 0x11c3, "ASUS G71V", ALC663_ASUS_G71V), | |
2980 | SND_PCI_QUIRK(0x1043, 0x1878, "ASUS M51VA", ALC663_ASUS_M51VA), | |
2981 | - SND_PCI_QUIRK(0x1043, 0x19a3, "ASUS M51VA", ALC663_ASUS_G50V), | |
2982 | + SND_PCI_QUIRK(0x1043, 0x19a3, "ASUS G50V", ALC663_ASUS_G50V), | |
2983 | SND_PCI_QUIRK(0x1043, 0x8290, "ASUS P5GC-MX", ALC662_3ST_6ch_DIG), | |
2984 | SND_PCI_QUIRK(0x1043, 0x82a1, "ASUS Eeepc", ALC662_ASUS_EEEPC_P701), | |
2985 | SND_PCI_QUIRK(0x1043, 0x82d1, "ASUS Eeepc EP20", ALC662_ASUS_EEEPC_EP20), | |
2986 | + SND_PCI_QUIRK(0x1043, 0x1903, "ASUS F5GL", ALC663_ASUS_MODE1), | |
2987 | + SND_PCI_QUIRK(0x1043, 0x1878, "ASUS M50Vr", ALC663_ASUS_MODE1), | |
2988 | + SND_PCI_QUIRK(0x1043, 0x1000, "ASUS N50Vm", ALC663_ASUS_MODE1), | |
2989 | + SND_PCI_QUIRK(0x1043, 0x19b3, "ASUS F7Z", ALC663_ASUS_MODE1), | |
2990 | + SND_PCI_QUIRK(0x1043, 0x1953, "ASUS NB", ALC663_ASUS_MODE1), | |
2991 | + SND_PCI_QUIRK(0x1043, 0x19a3, "ASUS NB", ALC663_ASUS_MODE1), | |
2992 | + SND_PCI_QUIRK(0x1043, 0x11d3, "ASUS NB", ALC663_ASUS_MODE1), | |
2993 | + SND_PCI_QUIRK(0x1043, 0x1203, "ASUS NB", ALC663_ASUS_MODE1), | |
2994 | + SND_PCI_QUIRK(0x1043, 0x19e3, "ASUS NB", ALC663_ASUS_MODE1), | |
2995 | + SND_PCI_QUIRK(0x1043, 0x1993, "ASUS N20", ALC663_ASUS_MODE1), | |
2996 | + SND_PCI_QUIRK(0x1043, 0x19c3, "ASUS F5Z/F6x", ALC662_ASUS_MODE2), | |
2997 | + SND_PCI_QUIRK(0x1043, 0x1339, "ASUS NB", ALC662_ASUS_MODE2), | |
2998 | + SND_PCI_QUIRK(0x1043, 0x1913, "ASUS NB", ALC662_ASUS_MODE2), | |
2999 | + SND_PCI_QUIRK(0x1043, 0x1843, "ASUS NB", ALC662_ASUS_MODE2), | |
3000 | + SND_PCI_QUIRK(0x1043, 0x1813, "ASUS NB", ALC662_ASUS_MODE2), | |
3001 | + SND_PCI_QUIRK(0x1043, 0x11f3, "ASUS NB", ALC662_ASUS_MODE2), | |
3002 | + SND_PCI_QUIRK(0x1043, 0x1876, "ASUS NB", ALC662_ASUS_MODE2), | |
3003 | + SND_PCI_QUIRK(0x1043, 0x1864, "ASUS NB", ALC662_ASUS_MODE2), | |
3004 | + SND_PCI_QUIRK(0x1043, 0x1783, "ASUS NB", ALC662_ASUS_MODE2), | |
3005 | + SND_PCI_QUIRK(0x1043, 0x1753, "ASUS NB", ALC662_ASUS_MODE2), | |
3006 | + SND_PCI_QUIRK(0x1043, 0x16c3, "ASUS NB", ALC662_ASUS_MODE2), | |
3007 | + SND_PCI_QUIRK(0x1043, 0x1933, "ASUS F80Q", ALC662_ASUS_MODE2), | |
3008 | + SND_PCI_QUIRK(0x1043, 0x1893, "ASUS M50Vm", ALC663_ASUS_MODE3), | |
3009 | + SND_PCI_QUIRK(0x1043, 0x11c3, "ASUS M70V", ALC663_ASUS_MODE3), | |
3010 | + SND_PCI_QUIRK(0x1043, 0x1963, "ASUS X71C", ALC663_ASUS_MODE3), | |
3011 | + SND_PCI_QUIRK(0x1043, 0x1894, "ASUS X55", ALC663_ASUS_MODE3), | |
3012 | + SND_PCI_QUIRK(0x1043, 0x1092, "ASUS NB", ALC663_ASUS_MODE3), | |
3013 | + SND_PCI_QUIRK(0x1043, 0x19f3, "ASUS NB", ALC663_ASUS_MODE4), | |
3014 | + SND_PCI_QUIRK(0x1043, 0x1823, "ASUS NB", ALC663_ASUS_MODE5), | |
3015 | + SND_PCI_QUIRK(0x1043, 0x1833, "ASUS NB", ALC663_ASUS_MODE6), | |
3016 | + SND_PCI_QUIRK(0x1043, 0x1763, "ASUS NB", ALC663_ASUS_MODE6), | |
3017 | + SND_PCI_QUIRK(0x1043, 0x1765, "ASUS NB", ALC663_ASUS_MODE6), | |
3018 | + SND_PCI_QUIRK(0x105b, 0x0d47, "Foxconn 45CMX/45GMX/45CMX-K", | |
3019 | + ALC662_3ST_6ch_DIG), | |
3020 | SND_PCI_QUIRK(0x17aa, 0x101e, "Lenovo", ALC662_LENOVO_101E), | |
3021 | + SND_PCI_QUIRK(0x1019, 0x9087, "ECS", ALC662_ECS), | |
3022 | + SND_PCI_QUIRK(0x105b, 0x0cd6, "Foxconn", ALC662_ECS), | |
3023 | + SND_PCI_QUIRK(0x1458, 0xa002, "Gigabyte 945GCM-S2L", | |
3024 | + ALC662_3ST_6ch_DIG), | |
3025 | + SND_PCI_QUIRK(0x1565, 0x820f, "Biostar TA780G M2+", ALC662_3ST_6ch_DIG), | |
3026 | + SND_PCI_QUIRK(0x1849, 0x3662, "ASROCK K10N78FullHD-hSLI R3.0", | |
3027 | + ALC662_3ST_6ch_DIG), | |
3028 | SND_PCI_QUIRK(0x1854, 0x2000, "ASUS H13-2000", ALC663_ASUS_H13), | |
3029 | SND_PCI_QUIRK(0x1854, 0x2001, "ASUS H13-2001", ALC663_ASUS_H13), | |
3030 | SND_PCI_QUIRK(0x1854, 0x2002, "ASUS H13-2002", ALC663_ASUS_H13), | |
3031 | @@ -14625,6 +15931,18 @@ static struct alc_config_preset alc662_p | |
3032 | .unsol_event = alc662_eeepc_ep20_unsol_event, | |
3033 | .init_hook = alc662_eeepc_ep20_inithook, | |
3034 | }, | |
3035 | + [ALC662_ECS] = { | |
3036 | + .mixers = { alc662_ecs_mixer, alc662_capture_mixer }, | |
3037 | + .init_verbs = { alc662_init_verbs, | |
3038 | + alc662_ecs_init_verbs }, | |
3039 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3040 | + .dac_nids = alc662_dac_nids, | |
3041 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3042 | + .channel_mode = alc662_3ST_2ch_modes, | |
3043 | + .input_mux = &alc662_eeepc_capture_source, | |
3044 | + .unsol_event = alc662_eeepc_unsol_event, | |
3045 | + .init_hook = alc662_eeepc_inithook, | |
3046 | + }, | |
3047 | [ALC663_ASUS_M51VA] = { | |
3048 | .mixers = { alc663_m51va_mixer, alc662_capture_mixer}, | |
3049 | .init_verbs = { alc662_init_verbs, alc663_m51va_init_verbs }, | |
3050 | @@ -14672,6 +15990,91 @@ static struct alc_config_preset alc662_p | |
3051 | .unsol_event = alc663_g50v_unsol_event, | |
3052 | .init_hook = alc663_g50v_inithook, | |
3053 | }, | |
3054 | + [ALC663_ASUS_MODE1] = { | |
3055 | + .mixers = { alc663_m51va_mixer, alc662_auto_capture_mixer }, | |
3056 | + .init_verbs = { alc662_init_verbs, | |
3057 | + alc663_21jd_amic_init_verbs }, | |
3058 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3059 | + .hp_nid = 0x03, | |
3060 | + .dac_nids = alc662_dac_nids, | |
3061 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3062 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3063 | + .channel_mode = alc662_3ST_2ch_modes, | |
3064 | + .input_mux = &alc662_eeepc_capture_source, | |
3065 | + .unsol_event = alc663_mode1_unsol_event, | |
3066 | + .init_hook = alc663_mode1_inithook, | |
3067 | + }, | |
3068 | + [ALC662_ASUS_MODE2] = { | |
3069 | + .mixers = { alc662_1bjd_mixer, alc662_auto_capture_mixer }, | |
3070 | + .init_verbs = { alc662_init_verbs, | |
3071 | + alc662_1bjd_amic_init_verbs }, | |
3072 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3073 | + .dac_nids = alc662_dac_nids, | |
3074 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3075 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3076 | + .channel_mode = alc662_3ST_2ch_modes, | |
3077 | + .input_mux = &alc662_eeepc_capture_source, | |
3078 | + .unsol_event = alc662_mode2_unsol_event, | |
3079 | + .init_hook = alc662_mode2_inithook, | |
3080 | + }, | |
3081 | + [ALC663_ASUS_MODE3] = { | |
3082 | + .mixers = { alc663_two_hp_m1_mixer, alc662_auto_capture_mixer }, | |
3083 | + .init_verbs = { alc662_init_verbs, | |
3084 | + alc663_two_hp_amic_m1_init_verbs }, | |
3085 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3086 | + .hp_nid = 0x03, | |
3087 | + .dac_nids = alc662_dac_nids, | |
3088 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3089 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3090 | + .channel_mode = alc662_3ST_2ch_modes, | |
3091 | + .input_mux = &alc662_eeepc_capture_source, | |
3092 | + .unsol_event = alc663_mode3_unsol_event, | |
3093 | + .init_hook = alc663_mode3_inithook, | |
3094 | + }, | |
3095 | + [ALC663_ASUS_MODE4] = { | |
3096 | + .mixers = { alc663_asus_21jd_clfe_mixer, | |
3097 | + alc662_auto_capture_mixer}, | |
3098 | + .init_verbs = { alc662_init_verbs, | |
3099 | + alc663_21jd_amic_init_verbs}, | |
3100 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3101 | + .hp_nid = 0x03, | |
3102 | + .dac_nids = alc662_dac_nids, | |
3103 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3104 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3105 | + .channel_mode = alc662_3ST_2ch_modes, | |
3106 | + .input_mux = &alc662_eeepc_capture_source, | |
3107 | + .unsol_event = alc663_mode4_unsol_event, | |
3108 | + .init_hook = alc663_mode4_inithook, | |
3109 | + }, | |
3110 | + [ALC663_ASUS_MODE5] = { | |
3111 | + .mixers = { alc663_asus_15jd_clfe_mixer, | |
3112 | + alc662_auto_capture_mixer }, | |
3113 | + .init_verbs = { alc662_init_verbs, | |
3114 | + alc663_15jd_amic_init_verbs }, | |
3115 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3116 | + .hp_nid = 0x03, | |
3117 | + .dac_nids = alc662_dac_nids, | |
3118 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3119 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3120 | + .channel_mode = alc662_3ST_2ch_modes, | |
3121 | + .input_mux = &alc662_eeepc_capture_source, | |
3122 | + .unsol_event = alc663_mode5_unsol_event, | |
3123 | + .init_hook = alc663_mode5_inithook, | |
3124 | + }, | |
3125 | + [ALC663_ASUS_MODE6] = { | |
3126 | + .mixers = { alc663_two_hp_m2_mixer, alc662_auto_capture_mixer }, | |
3127 | + .init_verbs = { alc662_init_verbs, | |
3128 | + alc663_two_hp_amic_m2_init_verbs }, | |
3129 | + .num_dacs = ARRAY_SIZE(alc662_dac_nids), | |
3130 | + .hp_nid = 0x03, | |
3131 | + .dac_nids = alc662_dac_nids, | |
3132 | + .dig_out_nid = ALC662_DIGOUT_NID, | |
3133 | + .num_channel_mode = ARRAY_SIZE(alc662_3ST_2ch_modes), | |
3134 | + .channel_mode = alc662_3ST_2ch_modes, | |
3135 | + .input_mux = &alc662_eeepc_capture_source, | |
3136 | + .unsol_event = alc663_mode6_unsol_event, | |
3137 | + .init_hook = alc663_mode6_inithook, | |
3138 | + }, | |
3139 | }; | |
3140 | ||
3141 | ||
3142 | @@ -14708,15 +16111,15 @@ static int alc662_auto_create_multi_out_ | |
3143 | HDA_OUTPUT)); | |
3144 | if (err < 0) | |
3145 | return err; | |
3146 | - err = add_control(spec, ALC_CTL_BIND_MUTE, | |
3147 | + err = add_control(spec, ALC_CTL_WIDGET_MUTE, | |
3148 | "Center Playback Switch", | |
3149 | - HDA_COMPOSE_AMP_VAL(nid, 1, 2, | |
3150 | + HDA_COMPOSE_AMP_VAL(0x0e, 1, 0, | |
3151 | HDA_INPUT)); | |
3152 | if (err < 0) | |
3153 | return err; | |
3154 | - err = add_control(spec, ALC_CTL_BIND_MUTE, | |
3155 | + err = add_control(spec, ALC_CTL_WIDGET_MUTE, | |
3156 | "LFE Playback Switch", | |
3157 | - HDA_COMPOSE_AMP_VAL(nid, 2, 2, | |
3158 | + HDA_COMPOSE_AMP_VAL(0x0e, 2, 0, | |
3159 | HDA_INPUT)); | |
3160 | if (err < 0) | |
3161 | return err; | |
3162 | @@ -14728,9 +16131,9 @@ static int alc662_auto_create_multi_out_ | |
3163 | if (err < 0) | |
3164 | return err; | |
3165 | sprintf(name, "%s Playback Switch", chname[i]); | |
3166 | - err = add_control(spec, ALC_CTL_BIND_MUTE, name, | |
3167 | - HDA_COMPOSE_AMP_VAL(nid, 3, 2, | |
3168 | - HDA_INPUT)); | |
3169 | + err = add_control(spec, ALC_CTL_WIDGET_MUTE, name, | |
3170 | + HDA_COMPOSE_AMP_VAL(alc880_idx_to_mixer(i), | |
3171 | + 3, 0, HDA_INPUT)); | |
3172 | if (err < 0) | |
3173 | return err; | |
3174 | } | |
3175 | @@ -14925,7 +16328,7 @@ static int alc662_parse_auto_config(stru | |
3176 | ||
3177 | spec->num_mux_defs = 1; | |
3178 | spec->input_mux = &spec->private_imux; | |
3179 | - | |
3180 | + | |
3181 | spec->init_verbs[spec->num_init_verbs++] = alc662_auto_init_verbs; | |
3182 | if (codec->vendor_id == 0x10ec0663) | |
3183 | spec->init_verbs[spec->num_init_verbs++] = | |
3184 | @@ -14951,7 +16354,7 @@ static void alc662_auto_init(struct hda_ | |
3185 | alc662_auto_init_analog_input(codec); | |
3186 | alc662_auto_init_input_src(codec); | |
3187 | if (spec->unsol_event) | |
3188 | - alc_sku_automute(codec); | |
3189 | + alc_inithook(codec); | |
3190 | } | |
3191 | ||
3192 | static int patch_alc662(struct hda_codec *codec) | |
3193 | @@ -15057,6 +16460,8 @@ struct hda_codec_preset snd_hda_preset_r | |
3194 | { .id = 0x10ec0885, .name = "ALC885", .patch = patch_alc882 }, | |
3195 | { .id = 0x10ec0887, .name = "ALC887", .patch = patch_alc883 }, | |
3196 | { .id = 0x10ec0888, .name = "ALC888", .patch = patch_alc883 }, | |
3197 | + { .id = 0x10ec0888, .rev = 0x100101, .name = "ALC1200", | |
3198 | + .patch = patch_alc883 }, | |
3199 | { .id = 0x10ec0889, .name = "ALC889", .patch = patch_alc883 }, | |
3200 | {} /* terminator */ | |
3201 | }; |