[ALSA] hda-codec - Add model entry for FIC P4M-915GD1
[pandora-kernel.git] / sound / pci / hda / patch_realtek.c
1 /*
2  * Universal Interface for Intel High Definition Audio Codec
3  *
4  * HD audio interface patch for ALC 260/880/882 codecs
5  *
6  * Copyright (c) 2004 Kailang Yang <kailang@realtek.com.tw>
7  *                    PeiSen Hou <pshou@realtek.com.tw>
8  *                    Takashi Iwai <tiwai@suse.de>
9  *                    Jonathan Woithe <jwoithe@physics.adelaide.edu.au>
10  *
11  *  This driver is free software; you can redistribute it and/or modify
12  *  it under the terms of the GNU General Public License as published by
13  *  the Free Software Foundation; either version 2 of the License, or
14  *  (at your option) any later version.
15  *
16  *  This driver is distributed in the hope that it will be useful,
17  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
18  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  *  GNU General Public License for more details.
20  *
21  *  You should have received a copy of the GNU General Public License
22  *  along with this program; if not, write to the Free Software
23  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
24  */
25
26 #include <sound/driver.h>
27 #include <linux/init.h>
28 #include <linux/delay.h>
29 #include <linux/slab.h>
30 #include <linux/pci.h>
31 #include <sound/core.h>
32 #include "hda_codec.h"
33 #include "hda_local.h"
34
35
36 /* ALC880 board config type */
37 enum {
38         ALC880_3ST,
39         ALC880_3ST_DIG,
40         ALC880_5ST,
41         ALC880_5ST_DIG,
42         ALC880_W810,
43         ALC880_Z71V,
44         ALC880_6ST,
45         ALC880_6ST_DIG,
46         ALC880_F1734,
47         ALC880_ASUS,
48         ALC880_ASUS_DIG,
49         ALC880_ASUS_W1V,
50         ALC880_ASUS_DIG2,
51         ALC880_UNIWILL_DIG,
52         ALC880_CLEVO,
53         ALC880_TCL_S700,
54         ALC880_LG,
55 #ifdef CONFIG_SND_DEBUG
56         ALC880_TEST,
57 #endif
58         ALC880_AUTO,
59         ALC880_MODEL_LAST /* last tag */
60 };
61
62 /* ALC260 models */
63 enum {
64         ALC260_BASIC,
65         ALC260_HP,
66         ALC260_HP_3013,
67         ALC260_FUJITSU_S702X,
68         ALC260_ACER,
69 #ifdef CONFIG_SND_DEBUG
70         ALC260_TEST,
71 #endif
72         ALC260_AUTO,
73         ALC260_MODEL_LAST /* last tag */
74 };
75
76 /* ALC262 models */
77 enum {
78         ALC262_BASIC,
79         ALC262_FUJITSU,
80         ALC262_AUTO,
81         ALC262_MODEL_LAST /* last tag */
82 };
83
84 /* ALC861 models */
85 enum {
86         ALC861_3ST,
87         ALC861_3ST_DIG,
88         ALC861_6ST_DIG,
89         ALC861_AUTO,
90         ALC861_MODEL_LAST,
91 };
92
93 /* ALC882 models */
94 enum {
95         ALC882_3ST_DIG,
96         ALC882_6ST_DIG,
97         ALC882_AUTO,
98         ALC882_MODEL_LAST,
99 };
100
101 /* for GPIO Poll */
102 #define GPIO_MASK       0x03
103
104 struct alc_spec {
105         /* codec parameterization */
106         struct snd_kcontrol_new *mixers[5];     /* mixer arrays */
107         unsigned int num_mixers;
108
109         const struct hda_verb *init_verbs[5];   /* initialization verbs
110                                                  * don't forget NULL termination!
111                                                  */
112         unsigned int num_init_verbs;
113
114         char *stream_name_analog;       /* analog PCM stream */
115         struct hda_pcm_stream *stream_analog_playback;
116         struct hda_pcm_stream *stream_analog_capture;
117
118         char *stream_name_digital;      /* digital PCM stream */ 
119         struct hda_pcm_stream *stream_digital_playback;
120         struct hda_pcm_stream *stream_digital_capture;
121
122         /* playback */
123         struct hda_multi_out multiout;  /* playback set-up
124                                          * max_channels, dacs must be set
125                                          * dig_out_nid and hp_nid are optional
126                                          */
127
128         /* capture */
129         unsigned int num_adc_nids;
130         hda_nid_t *adc_nids;
131         hda_nid_t dig_in_nid;           /* digital-in NID; optional */
132
133         /* capture source */
134         const struct hda_input_mux *input_mux;
135         unsigned int cur_mux[3];
136
137         /* channel model */
138         const struct hda_channel_mode *channel_mode;
139         int num_channel_mode;
140
141         /* PCM information */
142         struct hda_pcm pcm_rec[3];      /* used in alc_build_pcms() */
143
144         /* dynamic controls, init_verbs and input_mux */
145         struct auto_pin_cfg autocfg;
146         unsigned int num_kctl_alloc, num_kctl_used;
147         struct snd_kcontrol_new *kctl_alloc;
148         struct hda_input_mux private_imux;
149         hda_nid_t private_dac_nids[5];
150
151         /* hooks */
152         void (*init_hook)(struct hda_codec *codec);
153         void (*unsol_event)(struct hda_codec *codec, unsigned int res);
154
155         /* for pin sensing */
156         unsigned int sense_updated: 1;
157         unsigned int jack_present: 1;
158 };
159
160 /*
161  * configuration template - to be copied to the spec instance
162  */
163 struct alc_config_preset {
164         struct snd_kcontrol_new *mixers[5]; /* should be identical size with spec */
165         const struct hda_verb *init_verbs[5];
166         unsigned int num_dacs;
167         hda_nid_t *dac_nids;
168         hda_nid_t dig_out_nid;          /* optional */
169         hda_nid_t hp_nid;               /* optional */
170         unsigned int num_adc_nids;
171         hda_nid_t *adc_nids;
172         hda_nid_t dig_in_nid;
173         unsigned int num_channel_mode;
174         const struct hda_channel_mode *channel_mode;
175         const struct hda_input_mux *input_mux;
176         void (*unsol_event)(struct hda_codec *, unsigned int);
177         void (*init_hook)(struct hda_codec *);
178 };
179
180
181 /*
182  * input MUX handling
183  */
184 static int alc_mux_enum_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
185 {
186         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
187         struct alc_spec *spec = codec->spec;
188         return snd_hda_input_mux_info(spec->input_mux, uinfo);
189 }
190
191 static int alc_mux_enum_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
192 {
193         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
194         struct alc_spec *spec = codec->spec;
195         unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
196
197         ucontrol->value.enumerated.item[0] = spec->cur_mux[adc_idx];
198         return 0;
199 }
200
201 static int alc_mux_enum_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
202 {
203         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
204         struct alc_spec *spec = codec->spec;
205         unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
206         return snd_hda_input_mux_put(codec, spec->input_mux, ucontrol,
207                                      spec->adc_nids[adc_idx], &spec->cur_mux[adc_idx]);
208 }
209
210
211 /*
212  * channel mode setting
213  */
214 static int alc_ch_mode_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
215 {
216         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
217         struct alc_spec *spec = codec->spec;
218         return snd_hda_ch_mode_info(codec, uinfo, spec->channel_mode,
219                                     spec->num_channel_mode);
220 }
221
222 static int alc_ch_mode_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
223 {
224         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
225         struct alc_spec *spec = codec->spec;
226         return snd_hda_ch_mode_get(codec, ucontrol, spec->channel_mode,
227                                    spec->num_channel_mode, spec->multiout.max_channels);
228 }
229
230 static int alc_ch_mode_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
231 {
232         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
233         struct alc_spec *spec = codec->spec;
234         return snd_hda_ch_mode_put(codec, ucontrol, spec->channel_mode,
235                                    spec->num_channel_mode, &spec->multiout.max_channels);
236 }
237
238 /*
239  * Control the mode of pin widget settings via the mixer.  "pc" is used
240  * instead of "%" to avoid consequences of accidently treating the % as 
241  * being part of a format specifier.  Maximum allowed length of a value is
242  * 63 characters plus NULL terminator.
243  *
244  * Note: some retasking pin complexes seem to ignore requests for input
245  * states other than HiZ (eg: PIN_VREFxx) and revert to HiZ if any of these
246  * are requested.  Therefore order this list so that this behaviour will not
247  * cause problems when mixer clients move through the enum sequentially.
248  * NIDs 0x0f and 0x10 have been observed to have this behaviour.
249  */
250 static char *alc_pin_mode_names[] = {
251         "Mic 50pc bias", "Mic 80pc bias",
252         "Line in", "Line out", "Headphone out",
253 };
254 static unsigned char alc_pin_mode_values[] = {
255         PIN_VREF50, PIN_VREF80, PIN_IN, PIN_OUT, PIN_HP,
256 };
257 /* The control can present all 5 options, or it can limit the options based
258  * in the pin being assumed to be exclusively an input or an output pin.
259  */
260 #define ALC_PIN_DIR_IN    0x00
261 #define ALC_PIN_DIR_OUT   0x01
262 #define ALC_PIN_DIR_INOUT 0x02
263
264 /* Info about the pin modes supported by the three different pin directions. 
265  * For each direction the minimum and maximum values are given.
266  */
267 static signed char alc_pin_mode_dir_info[3][2] = {
268         { 0, 2 },    /* ALC_PIN_DIR_IN */
269         { 3, 4 },    /* ALC_PIN_DIR_OUT */
270         { 0, 4 },    /* ALC_PIN_DIR_INOUT */
271 };
272 #define alc_pin_mode_min(_dir) (alc_pin_mode_dir_info[_dir][0])
273 #define alc_pin_mode_max(_dir) (alc_pin_mode_dir_info[_dir][1])
274 #define alc_pin_mode_n_items(_dir) \
275         (alc_pin_mode_max(_dir)-alc_pin_mode_min(_dir)+1)
276
277 static int alc_pin_mode_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
278 {
279         unsigned int item_num = uinfo->value.enumerated.item;
280         unsigned char dir = (kcontrol->private_value >> 16) & 0xff;
281
282         uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
283         uinfo->count = 1;
284         uinfo->value.enumerated.items = alc_pin_mode_n_items(dir);
285
286         if (item_num<alc_pin_mode_min(dir) || item_num>alc_pin_mode_max(dir))
287                 item_num = alc_pin_mode_min(dir);
288         strcpy(uinfo->value.enumerated.name, alc_pin_mode_names[item_num]);
289         return 0;
290 }
291
292 static int alc_pin_mode_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
293 {
294         unsigned int i;
295         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
296         hda_nid_t nid = kcontrol->private_value & 0xffff;
297         unsigned char dir = (kcontrol->private_value >> 16) & 0xff;
298         long *valp = ucontrol->value.integer.value;
299         unsigned int pinctl = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_PIN_WIDGET_CONTROL,0x00);
300
301         /* Find enumerated value for current pinctl setting */
302         i = alc_pin_mode_min(dir);
303         while (alc_pin_mode_values[i]!=pinctl && i<=alc_pin_mode_max(dir))
304                 i++;
305         *valp = i<=alc_pin_mode_max(dir)?i:alc_pin_mode_min(dir);
306         return 0;
307 }
308
309 static int alc_pin_mode_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
310 {
311         signed int change;
312         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
313         hda_nid_t nid = kcontrol->private_value & 0xffff;
314         unsigned char dir = (kcontrol->private_value >> 16) & 0xff;
315         long val = *ucontrol->value.integer.value;
316         unsigned int pinctl = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_PIN_WIDGET_CONTROL,0x00);
317
318         if (val<alc_pin_mode_min(dir) || val>alc_pin_mode_max(dir)) 
319                 val = alc_pin_mode_min(dir);
320
321         change = pinctl != alc_pin_mode_values[val];
322         if (change) {
323                 /* Set pin mode to that requested */
324                 snd_hda_codec_write(codec,nid,0,AC_VERB_SET_PIN_WIDGET_CONTROL,
325                         alc_pin_mode_values[val]);
326
327                 /* Also enable the retasking pin's input/output as required 
328                  * for the requested pin mode.  Enum values of 2 or less are
329                  * input modes.
330                  *
331                  * Dynamically switching the input/output buffers probably
332                  * reduces noise slightly, particularly on input.  However,
333                  * havingboth input and output buffers enabled
334                  * simultaneously doesn't seem to be problematic.
335                  */
336                 if (val <= 2) {
337                         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_AMP_GAIN_MUTE,
338                                 AMP_OUT_MUTE);
339                         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_AMP_GAIN_MUTE,
340                                 AMP_IN_UNMUTE(0));
341                 } else {
342                         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_AMP_GAIN_MUTE,
343                                 AMP_IN_MUTE(0));
344                         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_AMP_GAIN_MUTE,
345                                 AMP_OUT_UNMUTE);
346                 }
347         }
348         return change;
349 }
350
351 #define ALC_PIN_MODE(xname, nid, dir) \
352         { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = 0,  \
353           .info = alc_pin_mode_info, \
354           .get = alc_pin_mode_get, \
355           .put = alc_pin_mode_put, \
356           .private_value = nid | (dir<<16) }
357
358 /* A switch control for ALC260 GPIO pins.  Multiple GPIOs can be ganged
359  * together using a mask with more than one bit set.  This control is
360  * currently used only by the ALC260 test model.  At this stage they are not
361  * needed for any "production" models.
362  */
363 #ifdef CONFIG_SND_DEBUG
364 static int alc_gpio_data_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
365 {
366         uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN;
367         uinfo->count = 1;
368         uinfo->value.integer.min = 0;
369         uinfo->value.integer.max = 1;
370         return 0;
371 }                                
372 static int alc_gpio_data_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
373 {
374         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
375         hda_nid_t nid = kcontrol->private_value & 0xffff;
376         unsigned char mask = (kcontrol->private_value >> 16) & 0xff;
377         long *valp = ucontrol->value.integer.value;
378         unsigned int val = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_GPIO_DATA,0x00);
379
380         *valp = (val & mask) != 0;
381         return 0;
382 }
383 static int alc_gpio_data_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
384 {
385         signed int change;
386         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
387         hda_nid_t nid = kcontrol->private_value & 0xffff;
388         unsigned char mask = (kcontrol->private_value >> 16) & 0xff;
389         long val = *ucontrol->value.integer.value;
390         unsigned int gpio_data = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_GPIO_DATA,0x00);
391
392         /* Set/unset the masked GPIO bit(s) as needed */
393         change = (val==0?0:mask) != (gpio_data & mask);
394         if (val==0)
395                 gpio_data &= ~mask;
396         else
397                 gpio_data |= mask;
398         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_GPIO_DATA,gpio_data);
399
400         return change;
401 }
402 #define ALC_GPIO_DATA_SWITCH(xname, nid, mask) \
403         { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = 0,  \
404           .info = alc_gpio_data_info, \
405           .get = alc_gpio_data_get, \
406           .put = alc_gpio_data_put, \
407           .private_value = nid | (mask<<16) }
408 #endif   /* CONFIG_SND_DEBUG */
409
410 /* A switch control to allow the enabling of the digital IO pins on the
411  * ALC260.  This is incredibly simplistic; the intention of this control is
412  * to provide something in the test model allowing digital outputs to be
413  * identified if present.  If models are found which can utilise these
414  * outputs a more complete mixer control can be devised for those models if
415  * necessary.
416  */
417 #ifdef CONFIG_SND_DEBUG
418 static int alc_spdif_ctrl_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
419 {
420         uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN;
421         uinfo->count = 1;
422         uinfo->value.integer.min = 0;
423         uinfo->value.integer.max = 1;
424         return 0;
425 }                                
426 static int alc_spdif_ctrl_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
427 {
428         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
429         hda_nid_t nid = kcontrol->private_value & 0xffff;
430         unsigned char mask = (kcontrol->private_value >> 16) & 0xff;
431         long *valp = ucontrol->value.integer.value;
432         unsigned int val = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_DIGI_CONVERT,0x00);
433
434         *valp = (val & mask) != 0;
435         return 0;
436 }
437 static int alc_spdif_ctrl_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
438 {
439         signed int change;
440         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
441         hda_nid_t nid = kcontrol->private_value & 0xffff;
442         unsigned char mask = (kcontrol->private_value >> 16) & 0xff;
443         long val = *ucontrol->value.integer.value;
444         unsigned int ctrl_data = snd_hda_codec_read(codec,nid,0,AC_VERB_GET_DIGI_CONVERT,0x00);
445
446         /* Set/unset the masked control bit(s) as needed */
447         change = (val==0?0:mask) != (ctrl_data & mask);
448         if (val==0)
449                 ctrl_data &= ~mask;
450         else
451                 ctrl_data |= mask;
452         snd_hda_codec_write(codec,nid,0,AC_VERB_SET_DIGI_CONVERT_1,ctrl_data);
453
454         return change;
455 }
456 #define ALC_SPDIF_CTRL_SWITCH(xname, nid, mask) \
457         { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = 0,  \
458           .info = alc_spdif_ctrl_info, \
459           .get = alc_spdif_ctrl_get, \
460           .put = alc_spdif_ctrl_put, \
461           .private_value = nid | (mask<<16) }
462 #endif   /* CONFIG_SND_DEBUG */
463
464 /*
465  * set up from the preset table
466  */
467 static void setup_preset(struct alc_spec *spec, const struct alc_config_preset *preset)
468 {
469         int i;
470
471         for (i = 0; i < ARRAY_SIZE(preset->mixers) && preset->mixers[i]; i++)
472                 spec->mixers[spec->num_mixers++] = preset->mixers[i];
473         for (i = 0; i < ARRAY_SIZE(preset->init_verbs) && preset->init_verbs[i]; i++)
474                 spec->init_verbs[spec->num_init_verbs++] = preset->init_verbs[i];
475         
476         spec->channel_mode = preset->channel_mode;
477         spec->num_channel_mode = preset->num_channel_mode;
478
479         spec->multiout.max_channels = spec->channel_mode[0].channels;
480
481         spec->multiout.num_dacs = preset->num_dacs;
482         spec->multiout.dac_nids = preset->dac_nids;
483         spec->multiout.dig_out_nid = preset->dig_out_nid;
484         spec->multiout.hp_nid = preset->hp_nid;
485         
486         spec->input_mux = preset->input_mux;
487
488         spec->num_adc_nids = preset->num_adc_nids;
489         spec->adc_nids = preset->adc_nids;
490         spec->dig_in_nid = preset->dig_in_nid;
491
492         spec->unsol_event = preset->unsol_event;
493         spec->init_hook = preset->init_hook;
494 }
495
496 /*
497  * ALC880 3-stack model
498  *
499  * DAC: Front = 0x02 (0x0c), Surr = 0x05 (0x0f), CLFE = 0x04 (0x0e)
500  * Pin assignment: Front = 0x14, Line-In/Surr = 0x1a, Mic/CLFE = 0x18, F-Mic = 0x1b
501  *                 HP = 0x19
502  */
503
504 static hda_nid_t alc880_dac_nids[4] = {
505         /* front, rear, clfe, rear_surr */
506         0x02, 0x05, 0x04, 0x03
507 };
508
509 static hda_nid_t alc880_adc_nids[3] = {
510         /* ADC0-2 */
511         0x07, 0x08, 0x09,
512 };
513
514 /* The datasheet says the node 0x07 is connected from inputs,
515  * but it shows zero connection in the real implementation on some devices.
516  * Note: this is a 915GAV bug, fixed on 915GLV
517  */
518 static hda_nid_t alc880_adc_nids_alt[2] = {
519         /* ADC1-2 */
520         0x08, 0x09,
521 };
522
523 #define ALC880_DIGOUT_NID       0x06
524 #define ALC880_DIGIN_NID        0x0a
525
526 static struct hda_input_mux alc880_capture_source = {
527         .num_items = 4,
528         .items = {
529                 { "Mic", 0x0 },
530                 { "Front Mic", 0x3 },
531                 { "Line", 0x2 },
532                 { "CD", 0x4 },
533         },
534 };
535
536 /* channel source setting (2/6 channel selection for 3-stack) */
537 /* 2ch mode */
538 static struct hda_verb alc880_threestack_ch2_init[] = {
539         /* set line-in to input, mute it */
540         { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
541         { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
542         /* set mic-in to input vref 80%, mute it */
543         { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
544         { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
545         { } /* end */
546 };
547
548 /* 6ch mode */
549 static struct hda_verb alc880_threestack_ch6_init[] = {
550         /* set line-in to output, unmute it */
551         { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
552         { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
553         /* set mic-in to output, unmute it */
554         { 0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
555         { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
556         { } /* end */
557 };
558
559 static struct hda_channel_mode alc880_threestack_modes[2] = {
560         { 2, alc880_threestack_ch2_init },
561         { 6, alc880_threestack_ch6_init },
562 };
563
564 static struct snd_kcontrol_new alc880_three_stack_mixer[] = {
565         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
566         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
567         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
568         HDA_BIND_MUTE("Surround Playback Switch", 0x0f, 2, HDA_INPUT),
569         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
570         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
571         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
572         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
573         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
574         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
575         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
576         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
577         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
578         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
579         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x3, HDA_INPUT),
580         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x3, HDA_INPUT),
581         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x0b, 0x05, HDA_INPUT),
582         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x05, HDA_INPUT),
583         HDA_CODEC_MUTE("Headphone Playback Switch", 0x19, 0x0, HDA_OUTPUT),
584         {
585                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
586                 .name = "Channel Mode",
587                 .info = alc_ch_mode_info,
588                 .get = alc_ch_mode_get,
589                 .put = alc_ch_mode_put,
590         },
591         { } /* end */
592 };
593
594 /* capture mixer elements */
595 static struct snd_kcontrol_new alc880_capture_mixer[] = {
596         HDA_CODEC_VOLUME("Capture Volume", 0x07, 0x0, HDA_INPUT),
597         HDA_CODEC_MUTE("Capture Switch", 0x07, 0x0, HDA_INPUT),
598         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x08, 0x0, HDA_INPUT),
599         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x08, 0x0, HDA_INPUT),
600         HDA_CODEC_VOLUME_IDX("Capture Volume", 2, 0x09, 0x0, HDA_INPUT),
601         HDA_CODEC_MUTE_IDX("Capture Switch", 2, 0x09, 0x0, HDA_INPUT),
602         {
603                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
604                 /* The multiple "Capture Source" controls confuse alsamixer
605                  * So call somewhat different..
606                  * FIXME: the controls appear in the "playback" view!
607                  */
608                 /* .name = "Capture Source", */
609                 .name = "Input Source",
610                 .count = 3,
611                 .info = alc_mux_enum_info,
612                 .get = alc_mux_enum_get,
613                 .put = alc_mux_enum_put,
614         },
615         { } /* end */
616 };
617
618 /* capture mixer elements (in case NID 0x07 not available) */
619 static struct snd_kcontrol_new alc880_capture_alt_mixer[] = {
620         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
621         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
622         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x09, 0x0, HDA_INPUT),
623         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x09, 0x0, HDA_INPUT),
624         {
625                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
626                 /* The multiple "Capture Source" controls confuse alsamixer
627                  * So call somewhat different..
628                  * FIXME: the controls appear in the "playback" view!
629                  */
630                 /* .name = "Capture Source", */
631                 .name = "Input Source",
632                 .count = 2,
633                 .info = alc_mux_enum_info,
634                 .get = alc_mux_enum_get,
635                 .put = alc_mux_enum_put,
636         },
637         { } /* end */
638 };
639
640
641
642 /*
643  * ALC880 5-stack model
644  *
645  * DAC: Front = 0x02 (0x0c), Surr = 0x05 (0x0f), CLFE = 0x04 (0x0d), Side = 0x02 (0xd)
646  * Pin assignment: Front = 0x14, Surr = 0x17, CLFE = 0x16
647  *                 Line-In/Side = 0x1a, Mic = 0x18, F-Mic = 0x1b, HP = 0x19
648  */
649
650 /* additional mixers to alc880_three_stack_mixer */
651 static struct snd_kcontrol_new alc880_five_stack_mixer[] = {
652         HDA_CODEC_VOLUME("Side Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
653         HDA_BIND_MUTE("Side Playback Switch", 0x0d, 2, HDA_INPUT),
654         { } /* end */
655 };
656
657 /* channel source setting (6/8 channel selection for 5-stack) */
658 /* 6ch mode */
659 static struct hda_verb alc880_fivestack_ch6_init[] = {
660         /* set line-in to input, mute it */
661         { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
662         { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
663         { } /* end */
664 };
665
666 /* 8ch mode */
667 static struct hda_verb alc880_fivestack_ch8_init[] = {
668         /* set line-in to output, unmute it */
669         { 0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
670         { 0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
671         { } /* end */
672 };
673
674 static struct hda_channel_mode alc880_fivestack_modes[2] = {
675         { 6, alc880_fivestack_ch6_init },
676         { 8, alc880_fivestack_ch8_init },
677 };
678
679
680 /*
681  * ALC880 6-stack model
682  *
683  * DAC: Front = 0x02 (0x0c), Surr = 0x03 (0x0d), CLFE = 0x04 (0x0e), Side = 0x05 (0x0f)
684  * Pin assignment: Front = 0x14, Surr = 0x15, CLFE = 0x16, Side = 0x17,
685  *   Mic = 0x18, F-Mic = 0x19, Line = 0x1a, HP = 0x1b
686  */
687
688 static hda_nid_t alc880_6st_dac_nids[4] = {
689         /* front, rear, clfe, rear_surr */
690         0x02, 0x03, 0x04, 0x05
691 };      
692
693 static struct hda_input_mux alc880_6stack_capture_source = {
694         .num_items = 4,
695         .items = {
696                 { "Mic", 0x0 },
697                 { "Front Mic", 0x1 },
698                 { "Line", 0x2 },
699                 { "CD", 0x4 },
700         },
701 };
702
703 /* fixed 8-channels */
704 static struct hda_channel_mode alc880_sixstack_modes[1] = {
705         { 8, NULL },
706 };
707
708 static struct snd_kcontrol_new alc880_six_stack_mixer[] = {
709         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
710         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
711         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
712         HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
713         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
714         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
715         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
716         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
717         HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
718         HDA_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT),
719         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
720         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
721         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
722         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
723         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
724         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
725         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x1, HDA_INPUT),
726         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x1, HDA_INPUT),
727         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x0b, 0x05, HDA_INPUT),
728         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x05, HDA_INPUT),
729         {
730                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
731                 .name = "Channel Mode",
732                 .info = alc_ch_mode_info,
733                 .get = alc_ch_mode_get,
734                 .put = alc_ch_mode_put,
735         },
736         { } /* end */
737 };
738
739
740 /*
741  * ALC880 W810 model
742  *
743  * W810 has rear IO for:
744  * Front (DAC 02)
745  * Surround (DAC 03)
746  * Center/LFE (DAC 04)
747  * Digital out (06)
748  *
749  * The system also has a pair of internal speakers, and a headphone jack.
750  * These are both connected to Line2 on the codec, hence to DAC 02.
751  * 
752  * There is a variable resistor to control the speaker or headphone
753  * volume. This is a hardware-only device without a software API.
754  *
755  * Plugging headphones in will disable the internal speakers. This is
756  * implemented in hardware, not via the driver using jack sense. In
757  * a similar fashion, plugging into the rear socket marked "front" will
758  * disable both the speakers and headphones.
759  *
760  * For input, there's a microphone jack, and an "audio in" jack.
761  * These may not do anything useful with this driver yet, because I
762  * haven't setup any initialization verbs for these yet...
763  */
764
765 static hda_nid_t alc880_w810_dac_nids[3] = {
766         /* front, rear/surround, clfe */
767         0x02, 0x03, 0x04
768 };
769
770 /* fixed 6 channels */
771 static struct hda_channel_mode alc880_w810_modes[1] = {
772         { 6, NULL }
773 };
774
775 /* Pin assignment: Front = 0x14, Surr = 0x15, CLFE = 0x16, HP = 0x1b */
776 static struct snd_kcontrol_new alc880_w810_base_mixer[] = {
777         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
778         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
779         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
780         HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
781         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
782         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
783         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
784         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
785         HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
786         { } /* end */
787 };
788
789
790 /*
791  * Z710V model
792  *
793  * DAC: Front = 0x02 (0x0c), HP = 0x03 (0x0d)
794  * Pin assignment: Front = 0x14, HP = 0x15, Mic = 0x18, Mic2 = 0x19(?), Line = 0x1a
795  */
796
797 static hda_nid_t alc880_z71v_dac_nids[1] = {
798         0x02
799 };
800 #define ALC880_Z71V_HP_DAC      0x03
801
802 /* fixed 2 channels */
803 static struct hda_channel_mode alc880_2_jack_modes[1] = {
804         { 2, NULL }
805 };
806
807 static struct snd_kcontrol_new alc880_z71v_mixer[] = {
808         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
809         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
810         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
811         HDA_BIND_MUTE("Headphone Playback Switch", 0x0d, 2, HDA_INPUT),
812         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
813         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
814         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
815         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
816         { } /* end */
817 };
818
819
820 /* FIXME! */
821 /*
822  * ALC880 F1734 model
823  *
824  * DAC: HP = 0x02 (0x0c), Front = 0x03 (0x0d)
825  * Pin assignment: HP = 0x14, Front = 0x15, Mic = 0x18
826  */
827
828 static hda_nid_t alc880_f1734_dac_nids[1] = {
829         0x03
830 };
831 #define ALC880_F1734_HP_DAC     0x02
832
833 static struct snd_kcontrol_new alc880_f1734_mixer[] = {
834         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
835         HDA_BIND_MUTE("Headphone Playback Switch", 0x0c, 2, HDA_INPUT),
836         HDA_CODEC_VOLUME("Internal Speaker Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
837         HDA_BIND_MUTE("Internal Speaker Playback Switch", 0x0d, 2, HDA_INPUT),
838         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
839         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
840         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
841         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
842         { } /* end */
843 };
844
845
846 /* FIXME! */
847 /*
848  * ALC880 ASUS model
849  *
850  * DAC: HP/Front = 0x02 (0x0c), Surr = 0x03 (0x0d), CLFE = 0x04 (0x0e)
851  * Pin assignment: HP/Front = 0x14, Surr = 0x15, CLFE = 0x16,
852  *  Mic = 0x18, Line = 0x1a
853  */
854
855 #define alc880_asus_dac_nids    alc880_w810_dac_nids    /* identical with w810 */
856 #define alc880_asus_modes       alc880_threestack_modes /* 2/6 channel mode */
857
858 static struct snd_kcontrol_new alc880_asus_mixer[] = {
859         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
860         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
861         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
862         HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
863         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
864         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
865         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
866         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
867         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
868         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
869         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
870         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
871         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
872         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
873         {
874                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
875                 .name = "Channel Mode",
876                 .info = alc_ch_mode_info,
877                 .get = alc_ch_mode_get,
878                 .put = alc_ch_mode_put,
879         },
880         { } /* end */
881 };
882
883 /* FIXME! */
884 /*
885  * ALC880 ASUS W1V model
886  *
887  * DAC: HP/Front = 0x02 (0x0c), Surr = 0x03 (0x0d), CLFE = 0x04 (0x0e)
888  * Pin assignment: HP/Front = 0x14, Surr = 0x15, CLFE = 0x16,
889  *  Mic = 0x18, Line = 0x1a, Line2 = 0x1b
890  */
891
892 /* additional mixers to alc880_asus_mixer */
893 static struct snd_kcontrol_new alc880_asus_w1v_mixer[] = {
894         HDA_CODEC_VOLUME("Line2 Playback Volume", 0x0b, 0x03, HDA_INPUT),
895         HDA_CODEC_MUTE("Line2 Playback Switch", 0x0b, 0x03, HDA_INPUT),
896         { } /* end */
897 };
898
899 /* additional mixers to alc880_asus_mixer */
900 static struct snd_kcontrol_new alc880_pcbeep_mixer[] = {
901         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x0b, 0x05, HDA_INPUT),
902         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x05, HDA_INPUT),
903         { } /* end */
904 };
905
906 /* TCL S700 */
907 static struct snd_kcontrol_new alc880_tcl_s700_mixer[] = {
908         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
909         HDA_CODEC_MUTE("Front Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
910         HDA_CODEC_MUTE("Headphone Playback Switch", 0x14, 0x0, HDA_OUTPUT),
911         HDA_CODEC_VOLUME("CD Playback Volume", 0x0B, 0x04, HDA_INPUT),
912         HDA_CODEC_MUTE("CD Playback Switch", 0x0B, 0x04, HDA_INPUT),
913         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0B, 0x0, HDA_INPUT),
914         HDA_CODEC_MUTE("Mic Playback Switch", 0x0B, 0x0, HDA_INPUT),
915         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
916         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
917         {
918                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
919                 /* The multiple "Capture Source" controls confuse alsamixer
920                  * So call somewhat different..
921                  * FIXME: the controls appear in the "playback" view!
922                  */
923                 /* .name = "Capture Source", */
924                 .name = "Input Source",
925                 .count = 1,
926                 .info = alc_mux_enum_info,
927                 .get = alc_mux_enum_get,
928                 .put = alc_mux_enum_put,
929         },
930         { } /* end */
931 };
932
933 /*
934  * build control elements
935  */
936 static int alc_build_controls(struct hda_codec *codec)
937 {
938         struct alc_spec *spec = codec->spec;
939         int err;
940         int i;
941
942         for (i = 0; i < spec->num_mixers; i++) {
943                 err = snd_hda_add_new_ctls(codec, spec->mixers[i]);
944                 if (err < 0)
945                         return err;
946         }
947
948         if (spec->multiout.dig_out_nid) {
949                 err = snd_hda_create_spdif_out_ctls(codec, spec->multiout.dig_out_nid);
950                 if (err < 0)
951                         return err;
952         }
953         if (spec->dig_in_nid) {
954                 err = snd_hda_create_spdif_in_ctls(codec, spec->dig_in_nid);
955                 if (err < 0)
956                         return err;
957         }
958         return 0;
959 }
960
961
962 /*
963  * initialize the codec volumes, etc
964  */
965
966 /*
967  * generic initialization of ADC, input mixers and output mixers
968  */
969 static struct hda_verb alc880_volume_init_verbs[] = {
970         /*
971          * Unmute ADC0-2 and set the default input to mic-in
972          */
973         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
974         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
975         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
976         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
977         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
978         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
979
980         /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
981          * mixer widget
982          * Note: PASD motherboards uses the Line In 2 as the input for front panel
983          * mic (mic 2)
984          */
985         /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
986         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
987         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
988         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
989         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
990         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
991
992         /*
993          * Set up output mixers (0x0c - 0x0f)
994          */
995         /* set vol=0 to output mixers */
996         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
997         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
998         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
999         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
1000         /* set up input amps for analog loopback */
1001         /* Amp Indices: DAC = 0, mixer = 1 */
1002         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1003         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
1004         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1005         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
1006         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1007         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
1008         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1009         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
1010
1011         { }
1012 };
1013
1014 /*
1015  * 3-stack pin configuration:
1016  * front = 0x14, mic/clfe = 0x18, HP = 0x19, line/surr = 0x1a, f-mic = 0x1b
1017  */
1018 static struct hda_verb alc880_pin_3stack_init_verbs[] = {
1019         /*
1020          * preset connection lists of input pins
1021          * 0 = front, 1 = rear_surr, 2 = CLFE, 3 = surround
1022          */
1023         {0x10, AC_VERB_SET_CONNECT_SEL, 0x02}, /* mic/clfe */
1024         {0x11, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */
1025         {0x12, AC_VERB_SET_CONNECT_SEL, 0x03}, /* line/surround */
1026
1027         /*
1028          * Set pin mode and muting
1029          */
1030         /* set front pin widgets 0x14 for output */
1031         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1032         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1033         /* Mic1 (rear panel) pin widget for input and vref at 80% */
1034         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1035         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1036         /* Mic2 (as headphone out) for HP output */
1037         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1038         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1039         /* Line In pin widget for input */
1040         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1041         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1042         /* Line2 (as front mic) pin widget for input and vref at 80% */
1043         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1044         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1045         /* CD pin widget for input */
1046         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1047
1048         { }
1049 };
1050
1051 /*
1052  * 5-stack pin configuration:
1053  * front = 0x14, surround = 0x17, clfe = 0x16, mic = 0x18, HP = 0x19,
1054  * line-in/side = 0x1a, f-mic = 0x1b
1055  */
1056 static struct hda_verb alc880_pin_5stack_init_verbs[] = {
1057         /*
1058          * preset connection lists of input pins
1059          * 0 = front, 1 = rear_surr, 2 = CLFE, 3 = surround
1060          */
1061         {0x11, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */
1062         {0x12, AC_VERB_SET_CONNECT_SEL, 0x01}, /* line/side */
1063
1064         /*
1065          * Set pin mode and muting
1066          */
1067         /* set pin widgets 0x14-0x17 for output */
1068         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1069         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1070         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1071         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1072         /* unmute pins for output (no gain on this amp) */
1073         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1074         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1075         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1076         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1077
1078         /* Mic1 (rear panel) pin widget for input and vref at 80% */
1079         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1080         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1081         /* Mic2 (as headphone out) for HP output */
1082         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1083         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1084         /* Line In pin widget for input */
1085         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1086         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1087         /* Line2 (as front mic) pin widget for input and vref at 80% */
1088         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1089         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1090         /* CD pin widget for input */
1091         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1092
1093         { }
1094 };
1095
1096 /*
1097  * W810 pin configuration:
1098  * front = 0x14, surround = 0x15, clfe = 0x16, HP = 0x1b
1099  */
1100 static struct hda_verb alc880_pin_w810_init_verbs[] = {
1101         /* hphone/speaker input selector: front DAC */
1102         {0x13, AC_VERB_SET_CONNECT_SEL, 0x0},
1103
1104         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1105         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1106         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1107         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1108         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1109         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1110
1111         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1112         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1113
1114         { }
1115 };
1116
1117 /*
1118  * Z71V pin configuration:
1119  * Speaker-out = 0x14, HP = 0x15, Mic = 0x18, Line-in = 0x1a, Mic2 = 0x1b (?)
1120  */
1121 static struct hda_verb alc880_pin_z71v_init_verbs[] = {
1122         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1123         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1124         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1125         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1126
1127         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1128         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1129         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1130         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1131
1132         { }
1133 };
1134
1135 /*
1136  * 6-stack pin configuration:
1137  * front = 0x14, surr = 0x15, clfe = 0x16, side = 0x17, mic = 0x18, f-mic = 0x19,
1138  * line = 0x1a, HP = 0x1b
1139  */
1140 static struct hda_verb alc880_pin_6stack_init_verbs[] = {
1141         {0x13, AC_VERB_SET_CONNECT_SEL, 0x00}, /* HP */
1142
1143         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1144         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1145         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1146         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1147         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1148         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1149         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1150         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1151
1152         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1153         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1154         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1155         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1156         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1157         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1158         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1159         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1160         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1161         
1162         { }
1163 };
1164
1165 /* FIXME! */
1166 /*
1167  * F1734 pin configuration:
1168  * HP = 0x14, speaker-out = 0x15, mic = 0x18
1169  */
1170 static struct hda_verb alc880_pin_f1734_init_verbs[] = {
1171         {0x10, AC_VERB_SET_CONNECT_SEL, 0x02},
1172         {0x11, AC_VERB_SET_CONNECT_SEL, 0x00},
1173         {0x12, AC_VERB_SET_CONNECT_SEL, 0x01},
1174         {0x13, AC_VERB_SET_CONNECT_SEL, 0x00},
1175
1176         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1177         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1178         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1179         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1180
1181         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1182         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1183         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1184         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1185         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1186         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1187         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1188         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1189         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1190
1191         { }
1192 };
1193
1194 /* FIXME! */
1195 /*
1196  * ASUS pin configuration:
1197  * HP/front = 0x14, surr = 0x15, clfe = 0x16, mic = 0x18, line = 0x1a
1198  */
1199 static struct hda_verb alc880_pin_asus_init_verbs[] = {
1200         {0x10, AC_VERB_SET_CONNECT_SEL, 0x02},
1201         {0x11, AC_VERB_SET_CONNECT_SEL, 0x00},
1202         {0x12, AC_VERB_SET_CONNECT_SEL, 0x01},
1203         {0x13, AC_VERB_SET_CONNECT_SEL, 0x00},
1204
1205         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1206         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1207         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1208         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1209         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1210         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1211         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1212         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1213
1214         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1215         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1216         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1217         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1218         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1219         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1220         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1221         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1222         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1223         
1224         { }
1225 };
1226
1227 /* Enable GPIO mask and set output */
1228 static struct hda_verb alc880_gpio1_init_verbs[] = {
1229         {0x01, AC_VERB_SET_GPIO_MASK, 0x01},
1230         {0x01, AC_VERB_SET_GPIO_DIRECTION, 0x01},
1231         {0x01, AC_VERB_SET_GPIO_DATA, 0x01},
1232
1233         { }
1234 };
1235
1236 /* Enable GPIO mask and set output */
1237 static struct hda_verb alc880_gpio2_init_verbs[] = {
1238         {0x01, AC_VERB_SET_GPIO_MASK, 0x02},
1239         {0x01, AC_VERB_SET_GPIO_DIRECTION, 0x02},
1240         {0x01, AC_VERB_SET_GPIO_DATA, 0x02},
1241
1242         { }
1243 };
1244
1245 /* Clevo m520g init */
1246 static struct hda_verb alc880_pin_clevo_init_verbs[] = {
1247         /* headphone output */
1248         {0x11, AC_VERB_SET_CONNECT_SEL, 0x01},
1249         /* line-out */
1250         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1251         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1252         /* Line-in */
1253         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1254         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1255         /* CD */
1256         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1257         {0x1c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1258         /* Mic1 (rear panel) */
1259         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1260         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1261         /* Mic2 (front panel) */
1262         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1263         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1264         /* headphone */
1265         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1266         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1267         /* change to EAPD mode */
1268         {0x20, AC_VERB_SET_COEF_INDEX, 0x07},
1269         {0x20, AC_VERB_SET_PROC_COEF,  0x3060},
1270
1271         { }
1272 };
1273
1274 static struct hda_verb alc880_pin_tcl_S700_init_verbs[] = {
1275         /* Headphone output */
1276         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1277         /* Front output*/
1278         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1279         {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00},
1280
1281         /* Line In pin widget for input */
1282         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1283         /* CD pin widget for input */
1284         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1285         /* Mic1 (rear panel) pin widget for input and vref at 80% */
1286         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1287
1288         /* change to EAPD mode */
1289         {0x20, AC_VERB_SET_COEF_INDEX, 0x07},
1290         {0x20, AC_VERB_SET_PROC_COEF,  0x3070},
1291
1292         { }
1293 };
1294
1295 /*
1296  * LG m1 express dual
1297  *
1298  * Pin assignment:
1299  *   Rear Line-In/Out (blue): 0x14
1300  *   Build-in Mic-In: 0x15
1301  *   Speaker-out: 0x17
1302  *   HP-Out (green): 0x1b
1303  *   Mic-In/Out (red): 0x19
1304  *   SPDIF-Out: 0x1e
1305  */
1306
1307 /* To make 5.1 output working (green=Front, blue=Surr, red=CLFE) */
1308 static hda_nid_t alc880_lg_dac_nids[3] = {
1309         0x05, 0x02, 0x03
1310 };
1311
1312 /* seems analog CD is not working */
1313 static struct hda_input_mux alc880_lg_capture_source = {
1314         .num_items = 3,
1315         .items = {
1316                 { "Mic", 0x1 },
1317                 { "Line", 0x5 },
1318                 { "Internal Mic", 0x6 },
1319         },
1320 };
1321
1322 /* 2,4,6 channel modes */
1323 static struct hda_verb alc880_lg_ch2_init[] = {
1324         /* set line-in and mic-in to input */
1325         { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
1326         { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
1327         { }
1328 };
1329
1330 static struct hda_verb alc880_lg_ch4_init[] = {
1331         /* set line-in to out and mic-in to input */
1332         { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP },
1333         { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
1334         { }
1335 };
1336
1337 static struct hda_verb alc880_lg_ch6_init[] = {
1338         /* set line-in and mic-in to output */
1339         { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP },
1340         { 0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP },
1341         { }
1342 };
1343
1344 static struct hda_channel_mode alc880_lg_ch_modes[3] = {
1345         { 2, alc880_lg_ch2_init },
1346         { 4, alc880_lg_ch4_init },
1347         { 6, alc880_lg_ch6_init },
1348 };
1349
1350 static struct snd_kcontrol_new alc880_lg_mixer[] = {
1351         /* FIXME: it's not really "master" but front channels */
1352         HDA_CODEC_VOLUME("Master Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
1353         HDA_BIND_MUTE("Master Playback Switch", 0x0f, 2, HDA_INPUT),
1354         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
1355         HDA_BIND_MUTE("Surround Playback Switch", 0x0c, 2, HDA_INPUT),
1356         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0d, 1, 0x0, HDA_OUTPUT),
1357         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0d, 2, 0x0, HDA_OUTPUT),
1358         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0d, 1, 2, HDA_INPUT),
1359         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0d, 2, 2, HDA_INPUT),
1360         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x1, HDA_INPUT),
1361         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x1, HDA_INPUT),
1362         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x06, HDA_INPUT),
1363         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x06, HDA_INPUT),
1364         HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x0b, 0x07, HDA_INPUT),
1365         HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x0b, 0x07, HDA_INPUT),
1366         {
1367                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1368                 .name = "Channel Mode",
1369                 .info = alc_ch_mode_info,
1370                 .get = alc_ch_mode_get,
1371                 .put = alc_ch_mode_put,
1372         },
1373         { } /* end */
1374 };
1375
1376 static struct hda_verb alc880_lg_init_verbs[] = {
1377         /* set capture source to mic-in */
1378         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1379         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1380         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1381         /* mute all amp mixer inputs */
1382         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(5)},
1383         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(6)},
1384         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(7)},
1385         /* line-in to input */
1386         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1387         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1388         /* built-in mic */
1389         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1390         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1391         /* speaker-out */
1392         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1393         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1394         /* mic-in to input */
1395         {0x11, AC_VERB_SET_CONNECT_SEL, 0x01},
1396         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1397         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1398         /* HP-out */
1399         {0x13, AC_VERB_SET_CONNECT_SEL, 0x03},
1400         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
1401         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1402         /* jack sense */
1403         {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | 0x1},
1404         { }
1405 };
1406
1407 /* toggle speaker-output according to the hp-jack state */
1408 static void alc880_lg_automute(struct hda_codec *codec)
1409 {
1410         unsigned int present;
1411
1412         present = snd_hda_codec_read(codec, 0x1b, 0,
1413                                      AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
1414         snd_hda_codec_amp_update(codec, 0x17, 0, HDA_OUTPUT, 0,
1415                                  0x80, present ? 0x80 : 0);
1416         snd_hda_codec_amp_update(codec, 0x17, 1, HDA_OUTPUT, 0,
1417                                  0x80, present ? 0x80 : 0);
1418 }
1419
1420 static void alc880_lg_unsol_event(struct hda_codec *codec, unsigned int res)
1421 {
1422         /* Looks like the unsol event is incompatible with the standard
1423          * definition.  4bit tag is placed at 28 bit!
1424          */
1425         if ((res >> 28) == 0x01)
1426                 alc880_lg_automute(codec);
1427 }
1428
1429 /*
1430  * Common callbacks
1431  */
1432
1433 static int alc_init(struct hda_codec *codec)
1434 {
1435         struct alc_spec *spec = codec->spec;
1436         unsigned int i;
1437
1438         for (i = 0; i < spec->num_init_verbs; i++)
1439                 snd_hda_sequence_write(codec, spec->init_verbs[i]);
1440
1441         if (spec->init_hook)
1442                 spec->init_hook(codec);
1443
1444         return 0;
1445 }
1446
1447 static void alc_unsol_event(struct hda_codec *codec, unsigned int res)
1448 {
1449         struct alc_spec *spec = codec->spec;
1450
1451         if (spec->unsol_event)
1452                 spec->unsol_event(codec, res);
1453 }
1454
1455 #ifdef CONFIG_PM
1456 /*
1457  * resume
1458  */
1459 static int alc_resume(struct hda_codec *codec)
1460 {
1461         struct alc_spec *spec = codec->spec;
1462         int i;
1463
1464         alc_init(codec);
1465         for (i = 0; i < spec->num_mixers; i++)
1466                 snd_hda_resume_ctls(codec, spec->mixers[i]);
1467         if (spec->multiout.dig_out_nid)
1468                 snd_hda_resume_spdif_out(codec);
1469         if (spec->dig_in_nid)
1470                 snd_hda_resume_spdif_in(codec);
1471
1472         return 0;
1473 }
1474 #endif
1475
1476 /*
1477  * Analog playback callbacks
1478  */
1479 static int alc880_playback_pcm_open(struct hda_pcm_stream *hinfo,
1480                                     struct hda_codec *codec,
1481                                     struct snd_pcm_substream *substream)
1482 {
1483         struct alc_spec *spec = codec->spec;
1484         return snd_hda_multi_out_analog_open(codec, &spec->multiout, substream);
1485 }
1486
1487 static int alc880_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
1488                                        struct hda_codec *codec,
1489                                        unsigned int stream_tag,
1490                                        unsigned int format,
1491                                        struct snd_pcm_substream *substream)
1492 {
1493         struct alc_spec *spec = codec->spec;
1494         return snd_hda_multi_out_analog_prepare(codec, &spec->multiout, stream_tag,
1495                                                 format, substream);
1496 }
1497
1498 static int alc880_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
1499                                        struct hda_codec *codec,
1500                                        struct snd_pcm_substream *substream)
1501 {
1502         struct alc_spec *spec = codec->spec;
1503         return snd_hda_multi_out_analog_cleanup(codec, &spec->multiout);
1504 }
1505
1506 /*
1507  * Digital out
1508  */
1509 static int alc880_dig_playback_pcm_open(struct hda_pcm_stream *hinfo,
1510                                         struct hda_codec *codec,
1511                                         struct snd_pcm_substream *substream)
1512 {
1513         struct alc_spec *spec = codec->spec;
1514         return snd_hda_multi_out_dig_open(codec, &spec->multiout);
1515 }
1516
1517 static int alc880_dig_playback_pcm_close(struct hda_pcm_stream *hinfo,
1518                                          struct hda_codec *codec,
1519                                          struct snd_pcm_substream *substream)
1520 {
1521         struct alc_spec *spec = codec->spec;
1522         return snd_hda_multi_out_dig_close(codec, &spec->multiout);
1523 }
1524
1525 /*
1526  * Analog capture
1527  */
1528 static int alc880_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
1529                                       struct hda_codec *codec,
1530                                       unsigned int stream_tag,
1531                                       unsigned int format,
1532                                       struct snd_pcm_substream *substream)
1533 {
1534         struct alc_spec *spec = codec->spec;
1535
1536         snd_hda_codec_setup_stream(codec, spec->adc_nids[substream->number],
1537                                    stream_tag, 0, format);
1538         return 0;
1539 }
1540
1541 static int alc880_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
1542                                       struct hda_codec *codec,
1543                                       struct snd_pcm_substream *substream)
1544 {
1545         struct alc_spec *spec = codec->spec;
1546
1547         snd_hda_codec_setup_stream(codec, spec->adc_nids[substream->number], 0, 0, 0);
1548         return 0;
1549 }
1550
1551
1552 /*
1553  */
1554 static struct hda_pcm_stream alc880_pcm_analog_playback = {
1555         .substreams = 1,
1556         .channels_min = 2,
1557         .channels_max = 8,
1558         /* NID is set in alc_build_pcms */
1559         .ops = {
1560                 .open = alc880_playback_pcm_open,
1561                 .prepare = alc880_playback_pcm_prepare,
1562                 .cleanup = alc880_playback_pcm_cleanup
1563         },
1564 };
1565
1566 static struct hda_pcm_stream alc880_pcm_analog_capture = {
1567         .substreams = 2,
1568         .channels_min = 2,
1569         .channels_max = 2,
1570         /* NID is set in alc_build_pcms */
1571         .ops = {
1572                 .prepare = alc880_capture_pcm_prepare,
1573                 .cleanup = alc880_capture_pcm_cleanup
1574         },
1575 };
1576
1577 static struct hda_pcm_stream alc880_pcm_digital_playback = {
1578         .substreams = 1,
1579         .channels_min = 2,
1580         .channels_max = 2,
1581         /* NID is set in alc_build_pcms */
1582         .ops = {
1583                 .open = alc880_dig_playback_pcm_open,
1584                 .close = alc880_dig_playback_pcm_close
1585         },
1586 };
1587
1588 static struct hda_pcm_stream alc880_pcm_digital_capture = {
1589         .substreams = 1,
1590         .channels_min = 2,
1591         .channels_max = 2,
1592         /* NID is set in alc_build_pcms */
1593 };
1594
1595 /* Used by alc_build_pcms to flag that a PCM has no playback stream */
1596 static struct hda_pcm_stream alc_pcm_null_playback = {
1597         .substreams = 0,
1598         .channels_min = 0,
1599         .channels_max = 0,
1600 };
1601
1602 static int alc_build_pcms(struct hda_codec *codec)
1603 {
1604         struct alc_spec *spec = codec->spec;
1605         struct hda_pcm *info = spec->pcm_rec;
1606         int i;
1607
1608         codec->num_pcms = 1;
1609         codec->pcm_info = info;
1610
1611         info->name = spec->stream_name_analog;
1612         if (spec->stream_analog_playback) {
1613                 snd_assert(spec->multiout.dac_nids, return -EINVAL);
1614                 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = *(spec->stream_analog_playback);
1615                 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dac_nids[0];
1616         }
1617         if (spec->stream_analog_capture) {
1618                 snd_assert(spec->adc_nids, return -EINVAL);
1619                 info->stream[SNDRV_PCM_STREAM_CAPTURE] = *(spec->stream_analog_capture);
1620                 info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->adc_nids[0];
1621         }
1622
1623         if (spec->channel_mode) {
1624                 info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max = 0;
1625                 for (i = 0; i < spec->num_channel_mode; i++) {
1626                         if (spec->channel_mode[i].channels > info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max) {
1627                                 info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max = spec->channel_mode[i].channels;
1628                         }
1629                 }
1630         }
1631
1632         /* If the use of more than one ADC is requested for the current
1633          * model, configure a second analog capture-only PCM.
1634          */
1635         if (spec->num_adc_nids > 1) {
1636                 codec->num_pcms++;
1637                 info++;
1638                 info->name = spec->stream_name_analog;
1639                 /* No playback stream for second PCM */
1640                 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = alc_pcm_null_playback;
1641                 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = 0;
1642                 if (spec->stream_analog_capture) {
1643                         snd_assert(spec->adc_nids, return -EINVAL);
1644                         info->stream[SNDRV_PCM_STREAM_CAPTURE] = *(spec->stream_analog_capture);
1645                         info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->adc_nids[1];
1646                 }
1647         }
1648
1649         if (spec->multiout.dig_out_nid || spec->dig_in_nid) {
1650                 codec->num_pcms++;
1651                 info++;
1652                 info->name = spec->stream_name_digital;
1653                 if (spec->multiout.dig_out_nid &&
1654                     spec->stream_digital_playback) {
1655                         info->stream[SNDRV_PCM_STREAM_PLAYBACK] = *(spec->stream_digital_playback);
1656                         info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dig_out_nid;
1657                 }
1658                 if (spec->dig_in_nid &&
1659                     spec->stream_digital_capture) {
1660                         info->stream[SNDRV_PCM_STREAM_CAPTURE] = *(spec->stream_digital_capture);
1661                         info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->dig_in_nid;
1662                 }
1663         }
1664
1665         return 0;
1666 }
1667
1668 static void alc_free(struct hda_codec *codec)
1669 {
1670         struct alc_spec *spec = codec->spec;
1671         unsigned int i;
1672
1673         if (! spec)
1674                 return;
1675
1676         if (spec->kctl_alloc) {
1677                 for (i = 0; i < spec->num_kctl_used; i++)
1678                         kfree(spec->kctl_alloc[i].name);
1679                 kfree(spec->kctl_alloc);
1680         }
1681         kfree(spec);
1682 }
1683
1684 /*
1685  */
1686 static struct hda_codec_ops alc_patch_ops = {
1687         .build_controls = alc_build_controls,
1688         .build_pcms = alc_build_pcms,
1689         .init = alc_init,
1690         .free = alc_free,
1691         .unsol_event = alc_unsol_event,
1692 #ifdef CONFIG_PM
1693         .resume = alc_resume,
1694 #endif
1695 };
1696
1697
1698 /*
1699  * Test configuration for debugging
1700  *
1701  * Almost all inputs/outputs are enabled.  I/O pins can be configured via
1702  * enum controls.
1703  */
1704 #ifdef CONFIG_SND_DEBUG
1705 static hda_nid_t alc880_test_dac_nids[4] = {
1706         0x02, 0x03, 0x04, 0x05
1707 };
1708
1709 static struct hda_input_mux alc880_test_capture_source = {
1710         .num_items = 7,
1711         .items = {
1712                 { "In-1", 0x0 },
1713                 { "In-2", 0x1 },
1714                 { "In-3", 0x2 },
1715                 { "In-4", 0x3 },
1716                 { "CD", 0x4 },
1717                 { "Front", 0x5 },
1718                 { "Surround", 0x6 },
1719         },
1720 };
1721
1722 static struct hda_channel_mode alc880_test_modes[4] = {
1723         { 2, NULL },
1724         { 4, NULL },
1725         { 6, NULL },
1726         { 8, NULL },
1727 };
1728
1729 static int alc_test_pin_ctl_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
1730 {
1731         static char *texts[] = {
1732                 "N/A", "Line Out", "HP Out",
1733                 "In Hi-Z", "In 50%", "In Grd", "In 80%", "In 100%"
1734         };
1735         uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1736         uinfo->count = 1;
1737         uinfo->value.enumerated.items = 8;
1738         if (uinfo->value.enumerated.item >= 8)
1739                 uinfo->value.enumerated.item = 7;
1740         strcpy(uinfo->value.enumerated.name, texts[uinfo->value.enumerated.item]);
1741         return 0;
1742 }
1743
1744 static int alc_test_pin_ctl_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1745 {
1746         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1747         hda_nid_t nid = (hda_nid_t)kcontrol->private_value;
1748         unsigned int pin_ctl, item = 0;
1749
1750         pin_ctl = snd_hda_codec_read(codec, nid, 0,
1751                                      AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
1752         if (pin_ctl & AC_PINCTL_OUT_EN) {
1753                 if (pin_ctl & AC_PINCTL_HP_EN)
1754                         item = 2;
1755                 else
1756                         item = 1;
1757         } else if (pin_ctl & AC_PINCTL_IN_EN) {
1758                 switch (pin_ctl & AC_PINCTL_VREFEN) {
1759                 case AC_PINCTL_VREF_HIZ: item = 3; break;
1760                 case AC_PINCTL_VREF_50:  item = 4; break;
1761                 case AC_PINCTL_VREF_GRD: item = 5; break;
1762                 case AC_PINCTL_VREF_80:  item = 6; break;
1763                 case AC_PINCTL_VREF_100: item = 7; break;
1764                 }
1765         }
1766         ucontrol->value.enumerated.item[0] = item;
1767         return 0;
1768 }
1769
1770 static int alc_test_pin_ctl_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1771 {
1772         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1773         hda_nid_t nid = (hda_nid_t)kcontrol->private_value;
1774         static unsigned int ctls[] = {
1775                 0, AC_PINCTL_OUT_EN, AC_PINCTL_OUT_EN | AC_PINCTL_HP_EN,
1776                 AC_PINCTL_IN_EN | AC_PINCTL_VREF_HIZ,
1777                 AC_PINCTL_IN_EN | AC_PINCTL_VREF_50,
1778                 AC_PINCTL_IN_EN | AC_PINCTL_VREF_GRD,
1779                 AC_PINCTL_IN_EN | AC_PINCTL_VREF_80,
1780                 AC_PINCTL_IN_EN | AC_PINCTL_VREF_100,
1781         };
1782         unsigned int old_ctl, new_ctl;
1783
1784         old_ctl = snd_hda_codec_read(codec, nid, 0,
1785                                      AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
1786         new_ctl = ctls[ucontrol->value.enumerated.item[0]];
1787         if (old_ctl != new_ctl) {
1788                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, new_ctl);
1789                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
1790                                     ucontrol->value.enumerated.item[0] >= 3 ? 0xb080 : 0xb000);
1791                 return 1;
1792         }
1793         return 0;
1794 }
1795
1796 static int alc_test_pin_src_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
1797 {
1798         static char *texts[] = {
1799                 "Front", "Surround", "CLFE", "Side"
1800         };
1801         uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1802         uinfo->count = 1;
1803         uinfo->value.enumerated.items = 4;
1804         if (uinfo->value.enumerated.item >= 4)
1805                 uinfo->value.enumerated.item = 3;
1806         strcpy(uinfo->value.enumerated.name, texts[uinfo->value.enumerated.item]);
1807         return 0;
1808 }
1809
1810 static int alc_test_pin_src_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1811 {
1812         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1813         hda_nid_t nid = (hda_nid_t)kcontrol->private_value;
1814         unsigned int sel;
1815
1816         sel = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONNECT_SEL, 0);
1817         ucontrol->value.enumerated.item[0] = sel & 3;
1818         return 0;
1819 }
1820
1821 static int alc_test_pin_src_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1822 {
1823         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1824         hda_nid_t nid = (hda_nid_t)kcontrol->private_value;
1825         unsigned int sel;
1826
1827         sel = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONNECT_SEL, 0) & 3;
1828         if (ucontrol->value.enumerated.item[0] != sel) {
1829                 sel = ucontrol->value.enumerated.item[0] & 3;
1830                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_CONNECT_SEL, sel);
1831                 return 1;
1832         }
1833         return 0;
1834 }
1835
1836 #define PIN_CTL_TEST(xname,nid) {                       \
1837                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,    \
1838                         .name = xname,                 \
1839                         .info = alc_test_pin_ctl_info, \
1840                         .get = alc_test_pin_ctl_get,   \
1841                         .put = alc_test_pin_ctl_put,   \
1842                         .private_value = nid           \
1843                         }
1844
1845 #define PIN_SRC_TEST(xname,nid) {                       \
1846                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,    \
1847                         .name = xname,                 \
1848                         .info = alc_test_pin_src_info, \
1849                         .get = alc_test_pin_src_get,   \
1850                         .put = alc_test_pin_src_put,   \
1851                         .private_value = nid           \
1852                         }
1853
1854 static struct snd_kcontrol_new alc880_test_mixer[] = {
1855         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
1856         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
1857         HDA_CODEC_VOLUME("CLFE Playback Volume", 0x0e, 0x0, HDA_OUTPUT),
1858         HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
1859         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
1860         HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
1861         HDA_BIND_MUTE("CLFE Playback Switch", 0x0e, 2, HDA_INPUT),
1862         HDA_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT),
1863         PIN_CTL_TEST("Front Pin Mode", 0x14),
1864         PIN_CTL_TEST("Surround Pin Mode", 0x15),
1865         PIN_CTL_TEST("CLFE Pin Mode", 0x16),
1866         PIN_CTL_TEST("Side Pin Mode", 0x17),
1867         PIN_CTL_TEST("In-1 Pin Mode", 0x18),
1868         PIN_CTL_TEST("In-2 Pin Mode", 0x19),
1869         PIN_CTL_TEST("In-3 Pin Mode", 0x1a),
1870         PIN_CTL_TEST("In-4 Pin Mode", 0x1b),
1871         PIN_SRC_TEST("In-1 Pin Source", 0x18),
1872         PIN_SRC_TEST("In-2 Pin Source", 0x19),
1873         PIN_SRC_TEST("In-3 Pin Source", 0x1a),
1874         PIN_SRC_TEST("In-4 Pin Source", 0x1b),
1875         HDA_CODEC_VOLUME("In-1 Playback Volume", 0x0b, 0x0, HDA_INPUT),
1876         HDA_CODEC_MUTE("In-1 Playback Switch", 0x0b, 0x0, HDA_INPUT),
1877         HDA_CODEC_VOLUME("In-2 Playback Volume", 0x0b, 0x1, HDA_INPUT),
1878         HDA_CODEC_MUTE("In-2 Playback Switch", 0x0b, 0x1, HDA_INPUT),
1879         HDA_CODEC_VOLUME("In-3 Playback Volume", 0x0b, 0x2, HDA_INPUT),
1880         HDA_CODEC_MUTE("In-3 Playback Switch", 0x0b, 0x2, HDA_INPUT),
1881         HDA_CODEC_VOLUME("In-4 Playback Volume", 0x0b, 0x3, HDA_INPUT),
1882         HDA_CODEC_MUTE("In-4 Playback Switch", 0x0b, 0x3, HDA_INPUT),
1883         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x4, HDA_INPUT),
1884         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x4, HDA_INPUT),
1885         {
1886                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1887                 .name = "Channel Mode",
1888                 .info = alc_ch_mode_info,
1889                 .get = alc_ch_mode_get,
1890                 .put = alc_ch_mode_put,
1891         },
1892         { } /* end */
1893 };
1894
1895 static struct hda_verb alc880_test_init_verbs[] = {
1896         /* Unmute inputs of 0x0c - 0x0f */
1897         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1898         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1899         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1900         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1901         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1902         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1903         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1904         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
1905         /* Vol output for 0x0c-0x0f */
1906         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
1907         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
1908         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
1909         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
1910         /* Set output pins 0x14-0x17 */
1911         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1912         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1913         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1914         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
1915         /* Unmute output pins 0x14-0x17 */
1916         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1917         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1918         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1919         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
1920         /* Set input pins 0x18-0x1c */
1921         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1922         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
1923         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1924         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1925         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
1926         /* Mute input pins 0x18-0x1b */
1927         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1928         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1929         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1930         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
1931         /* ADC set up */
1932         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1933         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
1934         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1935         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
1936         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1937         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
1938         /* Analog input/passthru */
1939         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
1940         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
1941         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
1942         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
1943         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
1944         { }
1945 };
1946 #endif
1947
1948 /*
1949  */
1950
1951 static struct hda_board_config alc880_cfg_tbl[] = {
1952         /* Back 3 jack, front 2 jack */
1953         { .modelname = "3stack", .config = ALC880_3ST },
1954         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe200, .config = ALC880_3ST },
1955         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe201, .config = ALC880_3ST },
1956         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe202, .config = ALC880_3ST },
1957         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe203, .config = ALC880_3ST },
1958         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe204, .config = ALC880_3ST },
1959         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe205, .config = ALC880_3ST },
1960         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe206, .config = ALC880_3ST },
1961         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe207, .config = ALC880_3ST },
1962         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe208, .config = ALC880_3ST },
1963         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe209, .config = ALC880_3ST },
1964         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20a, .config = ALC880_3ST },
1965         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20b, .config = ALC880_3ST },
1966         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20c, .config = ALC880_3ST },
1967         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20d, .config = ALC880_3ST },
1968         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20e, .config = ALC880_3ST },
1969         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe20f, .config = ALC880_3ST },
1970         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe210, .config = ALC880_3ST },
1971         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe211, .config = ALC880_3ST },
1972         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe214, .config = ALC880_3ST },
1973         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe302, .config = ALC880_3ST },
1974         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe303, .config = ALC880_3ST },
1975         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe304, .config = ALC880_3ST },
1976         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe306, .config = ALC880_3ST },
1977         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe307, .config = ALC880_3ST },
1978         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe404, .config = ALC880_3ST },
1979         { .pci_subvendor = 0x8086, .pci_subdevice = 0xa101, .config = ALC880_3ST },
1980         { .pci_subvendor = 0x107b, .pci_subdevice = 0x3031, .config = ALC880_3ST },
1981         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4036, .config = ALC880_3ST },
1982         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4037, .config = ALC880_3ST },
1983         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4038, .config = ALC880_3ST },
1984         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4040, .config = ALC880_3ST },
1985         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4041, .config = ALC880_3ST },
1986         /* TCL S700 */
1987         { .pci_subvendor = 0x19db, .pci_subdevice = 0x4188, .config = ALC880_TCL_S700 },
1988
1989         /* Back 3 jack, front 2 jack (Internal add Aux-In) */
1990         { .pci_subvendor = 0x1025, .pci_subdevice = 0xe310, .config = ALC880_3ST },
1991         { .pci_subvendor = 0x104d, .pci_subdevice = 0x81d6, .config = ALC880_3ST }, 
1992         { .pci_subvendor = 0x104d, .pci_subdevice = 0x81a0, .config = ALC880_3ST },
1993
1994         /* Back 3 jack plus 1 SPDIF out jack, front 2 jack */
1995         { .modelname = "3stack-digout", .config = ALC880_3ST_DIG },
1996         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe308, .config = ALC880_3ST_DIG },
1997         { .pci_subvendor = 0x1025, .pci_subdevice = 0x0070, .config = ALC880_3ST_DIG },
1998         /* Clevo m520G NB */
1999         { .pci_subvendor = 0x1558, .pci_subdevice = 0x0520, .config = ALC880_CLEVO },
2000
2001         /* Back 3 jack plus 1 SPDIF out jack, front 2 jack (Internal add Aux-In)*/
2002         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe305, .config = ALC880_3ST_DIG },
2003         { .pci_subvendor = 0x8086, .pci_subdevice = 0xd402, .config = ALC880_3ST_DIG },
2004         { .pci_subvendor = 0x1025, .pci_subdevice = 0xe309, .config = ALC880_3ST_DIG },
2005
2006         /* Back 5 jack, front 2 jack */
2007         { .modelname = "5stack", .config = ALC880_5ST },
2008         { .pci_subvendor = 0x107b, .pci_subdevice = 0x3033, .config = ALC880_5ST },
2009         { .pci_subvendor = 0x107b, .pci_subdevice = 0x4039, .config = ALC880_5ST },
2010         { .pci_subvendor = 0x107b, .pci_subdevice = 0x3032, .config = ALC880_5ST },
2011         { .pci_subvendor = 0x103c, .pci_subdevice = 0x2a09, .config = ALC880_5ST },
2012         { .pci_subvendor = 0x1043, .pci_subdevice = 0x814e, .config = ALC880_5ST },
2013
2014         /* Back 5 jack plus 1 SPDIF out jack, front 2 jack */
2015         { .modelname = "5stack-digout", .config = ALC880_5ST_DIG },
2016         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe224, .config = ALC880_5ST_DIG },
2017         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe400, .config = ALC880_5ST_DIG },
2018         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe401, .config = ALC880_5ST_DIG },
2019         { .pci_subvendor = 0x8086, .pci_subdevice = 0xe402, .config = ALC880_5ST_DIG },
2020         { .pci_subvendor = 0x8086, .pci_subdevice = 0xd400, .config = ALC880_5ST_DIG },
2021         { .pci_subvendor = 0x8086, .pci_subdevice = 0xd401, .config = ALC880_5ST_DIG },
2022         { .pci_subvendor = 0x8086, .pci_subdevice = 0xa100, .config = ALC880_5ST_DIG },
2023         { .pci_subvendor = 0x1565, .pci_subdevice = 0x8202, .config = ALC880_5ST_DIG },
2024         { .pci_subvendor = 0x1019, .pci_subdevice = 0xa880, .config = ALC880_5ST_DIG },
2025         { .pci_subvendor = 0xa0a0, .pci_subdevice = 0x0560,
2026           .config = ALC880_5ST_DIG }, /* Aopen i915GMm-HFS */
2027         /* { .pci_subvendor = 0x1019, .pci_subdevice = 0xa884, .config = ALC880_5ST_DIG }, */ /* conflict with 6stack */
2028         { .pci_subvendor = 0x1695, .pci_subdevice = 0x400d, .config = ALC880_5ST_DIG },
2029         /* note subvendor = 0 below */
2030         /* { .pci_subvendor = 0x0000, .pci_subdevice = 0x8086, .config = ALC880_5ST_DIG }, */
2031
2032         { .modelname = "w810", .config = ALC880_W810 },
2033         { .pci_subvendor = 0x161f, .pci_subdevice = 0x203d, .config = ALC880_W810 },
2034
2035         { .modelname = "z71v", .config = ALC880_Z71V },
2036         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1964, .config = ALC880_Z71V },
2037
2038         { .modelname = "6stack", .config = ALC880_6ST },
2039         { .pci_subvendor = 0x1043, .pci_subdevice = 0x8196, .config = ALC880_6ST }, /* ASUS P5GD1-HVM */
2040         { .pci_subvendor = 0x1043, .pci_subdevice = 0x81b4, .config = ALC880_6ST },
2041         { .pci_subvendor = 0x1019, .pci_subdevice = 0xa884, .config = ALC880_6ST }, /* Acer APFV */
2042         { .pci_subvendor = 0x1458, .pci_subdevice = 0xa102, .config = ALC880_6ST }, /* Gigabyte K8N51 */
2043
2044         { .modelname = "6stack-digout", .config = ALC880_6ST_DIG },
2045         { .pci_subvendor = 0x2668, .pci_subdevice = 0x8086, .config = ALC880_6ST_DIG },
2046         { .pci_subvendor = 0x8086, .pci_subdevice = 0x2668, .config = ALC880_6ST_DIG },
2047         { .pci_subvendor = 0x1462, .pci_subdevice = 0x1150, .config = ALC880_6ST_DIG },
2048         { .pci_subvendor = 0xe803, .pci_subdevice = 0x1019, .config = ALC880_6ST_DIG },
2049         { .pci_subvendor = 0x1039, .pci_subdevice = 0x1234, .config = ALC880_6ST_DIG },
2050         { .pci_subvendor = 0x1025, .pci_subdevice = 0x0077, .config = ALC880_6ST_DIG },
2051         { .pci_subvendor = 0x1025, .pci_subdevice = 0x0078, .config = ALC880_6ST_DIG },
2052         { .pci_subvendor = 0x1025, .pci_subdevice = 0x0087, .config = ALC880_6ST_DIG },
2053         { .pci_subvendor = 0x1297, .pci_subdevice = 0xc790, .config = ALC880_6ST_DIG }, /* Shuttle ST20G5 */
2054         { .pci_subvendor = 0x1509, .pci_subdevice = 0x925d, .config = ALC880_6ST_DIG }, /* FIC P4M-915GD1 */
2055
2056         { .modelname = "asus", .config = ALC880_ASUS },
2057         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1964, .config = ALC880_ASUS_DIG },
2058         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1973, .config = ALC880_ASUS_DIG },
2059         { .pci_subvendor = 0x1043, .pci_subdevice = 0x19b3, .config = ALC880_ASUS_DIG },
2060         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1113, .config = ALC880_ASUS_DIG },
2061         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1173, .config = ALC880_ASUS_DIG },
2062         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1993, .config = ALC880_ASUS },
2063         { .pci_subvendor = 0x1043, .pci_subdevice = 0x10c3, .config = ALC880_ASUS_DIG },
2064         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1133, .config = ALC880_ASUS },
2065         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1123, .config = ALC880_ASUS_DIG },
2066         { .pci_subvendor = 0x1043, .pci_subdevice = 0x1143, .config = ALC880_ASUS },
2067         { .pci_subvendor = 0x1043, .pci_subdevice = 0x10b3, .config = ALC880_ASUS_W1V },
2068         { .pci_subvendor = 0x1558, .pci_subdevice = 0x5401, .config = ALC880_ASUS_DIG2 },
2069
2070         { .modelname = "uniwill", .config = ALC880_UNIWILL_DIG },
2071         { .pci_subvendor = 0x1584, .pci_subdevice = 0x9050, .config = ALC880_UNIWILL_DIG },     
2072
2073         { .modelname = "F1734", .config = ALC880_F1734 },
2074         { .pci_subvendor = 0x1734, .pci_subdevice = 0x107c, .config = ALC880_F1734 },
2075         { .pci_subvendor = 0x1584, .pci_subdevice = 0x9054, .config = ALC880_F1734 },
2076
2077         { .modelname = "lg", .config = ALC880_LG },
2078         { .pci_subvendor = 0x1854, .pci_subdevice = 0x003b, .config = ALC880_LG },
2079
2080 #ifdef CONFIG_SND_DEBUG
2081         { .modelname = "test", .config = ALC880_TEST },
2082 #endif
2083         { .modelname = "auto", .config = ALC880_AUTO },
2084
2085         {}
2086 };
2087
2088 /*
2089  * ALC880 codec presets
2090  */
2091 static struct alc_config_preset alc880_presets[] = {
2092         [ALC880_3ST] = {
2093                 .mixers = { alc880_three_stack_mixer },
2094                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_3stack_init_verbs },
2095                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2096                 .dac_nids = alc880_dac_nids,
2097                 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
2098                 .channel_mode = alc880_threestack_modes,
2099                 .input_mux = &alc880_capture_source,
2100         },
2101         [ALC880_3ST_DIG] = {
2102                 .mixers = { alc880_three_stack_mixer },
2103                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_3stack_init_verbs },
2104                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2105                 .dac_nids = alc880_dac_nids,
2106                 .dig_out_nid = ALC880_DIGOUT_NID,
2107                 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
2108                 .channel_mode = alc880_threestack_modes,
2109                 .input_mux = &alc880_capture_source,
2110         },
2111         [ALC880_TCL_S700] = {
2112                 .mixers = { alc880_tcl_s700_mixer },
2113                 .init_verbs = { alc880_volume_init_verbs,
2114                                 alc880_pin_tcl_S700_init_verbs,
2115                                 alc880_gpio2_init_verbs },
2116                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2117                 .dac_nids = alc880_dac_nids,
2118                 .hp_nid = 0x03,
2119                 .num_channel_mode = ARRAY_SIZE(alc880_2_jack_modes),
2120                 .channel_mode = alc880_2_jack_modes,
2121                 .input_mux = &alc880_capture_source,
2122         },
2123         [ALC880_5ST] = {
2124                 .mixers = { alc880_three_stack_mixer, alc880_five_stack_mixer},
2125                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_5stack_init_verbs },
2126                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2127                 .dac_nids = alc880_dac_nids,
2128                 .num_channel_mode = ARRAY_SIZE(alc880_fivestack_modes),
2129                 .channel_mode = alc880_fivestack_modes,
2130                 .input_mux = &alc880_capture_source,
2131         },
2132         [ALC880_5ST_DIG] = {
2133                 .mixers = { alc880_three_stack_mixer, alc880_five_stack_mixer },
2134                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_5stack_init_verbs },
2135                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2136                 .dac_nids = alc880_dac_nids,
2137                 .dig_out_nid = ALC880_DIGOUT_NID,
2138                 .num_channel_mode = ARRAY_SIZE(alc880_fivestack_modes),
2139                 .channel_mode = alc880_fivestack_modes,
2140                 .input_mux = &alc880_capture_source,
2141         },
2142         [ALC880_6ST] = {
2143                 .mixers = { alc880_six_stack_mixer },
2144                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_6stack_init_verbs },
2145                 .num_dacs = ARRAY_SIZE(alc880_6st_dac_nids),
2146                 .dac_nids = alc880_6st_dac_nids,
2147                 .num_channel_mode = ARRAY_SIZE(alc880_sixstack_modes),
2148                 .channel_mode = alc880_sixstack_modes,
2149                 .input_mux = &alc880_6stack_capture_source,
2150         },
2151         [ALC880_6ST_DIG] = {
2152                 .mixers = { alc880_six_stack_mixer },
2153                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_6stack_init_verbs },
2154                 .num_dacs = ARRAY_SIZE(alc880_6st_dac_nids),
2155                 .dac_nids = alc880_6st_dac_nids,
2156                 .dig_out_nid = ALC880_DIGOUT_NID,
2157                 .num_channel_mode = ARRAY_SIZE(alc880_sixstack_modes),
2158                 .channel_mode = alc880_sixstack_modes,
2159                 .input_mux = &alc880_6stack_capture_source,
2160         },
2161         [ALC880_W810] = {
2162                 .mixers = { alc880_w810_base_mixer },
2163                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_w810_init_verbs,
2164                                 alc880_gpio2_init_verbs },
2165                 .num_dacs = ARRAY_SIZE(alc880_w810_dac_nids),
2166                 .dac_nids = alc880_w810_dac_nids,
2167                 .dig_out_nid = ALC880_DIGOUT_NID,
2168                 .num_channel_mode = ARRAY_SIZE(alc880_w810_modes),
2169                 .channel_mode = alc880_w810_modes,
2170                 .input_mux = &alc880_capture_source,
2171         },
2172         [ALC880_Z71V] = {
2173                 .mixers = { alc880_z71v_mixer },
2174                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_z71v_init_verbs },
2175                 .num_dacs = ARRAY_SIZE(alc880_z71v_dac_nids),
2176                 .dac_nids = alc880_z71v_dac_nids,
2177                 .dig_out_nid = ALC880_DIGOUT_NID,
2178                 .hp_nid = 0x03,
2179                 .num_channel_mode = ARRAY_SIZE(alc880_2_jack_modes),
2180                 .channel_mode = alc880_2_jack_modes,
2181                 .input_mux = &alc880_capture_source,
2182         },
2183         [ALC880_F1734] = {
2184                 .mixers = { alc880_f1734_mixer },
2185                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_f1734_init_verbs },
2186                 .num_dacs = ARRAY_SIZE(alc880_f1734_dac_nids),
2187                 .dac_nids = alc880_f1734_dac_nids,
2188                 .hp_nid = 0x02,
2189                 .num_channel_mode = ARRAY_SIZE(alc880_2_jack_modes),
2190                 .channel_mode = alc880_2_jack_modes,
2191                 .input_mux = &alc880_capture_source,
2192         },
2193         [ALC880_ASUS] = {
2194                 .mixers = { alc880_asus_mixer },
2195                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_asus_init_verbs,
2196                                 alc880_gpio1_init_verbs },
2197                 .num_dacs = ARRAY_SIZE(alc880_asus_dac_nids),
2198                 .dac_nids = alc880_asus_dac_nids,
2199                 .num_channel_mode = ARRAY_SIZE(alc880_asus_modes),
2200                 .channel_mode = alc880_asus_modes,
2201                 .input_mux = &alc880_capture_source,
2202         },
2203         [ALC880_ASUS_DIG] = {
2204                 .mixers = { alc880_asus_mixer },
2205                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_asus_init_verbs,
2206                                 alc880_gpio1_init_verbs },
2207                 .num_dacs = ARRAY_SIZE(alc880_asus_dac_nids),
2208                 .dac_nids = alc880_asus_dac_nids,
2209                 .dig_out_nid = ALC880_DIGOUT_NID,
2210                 .num_channel_mode = ARRAY_SIZE(alc880_asus_modes),
2211                 .channel_mode = alc880_asus_modes,
2212                 .input_mux = &alc880_capture_source,
2213         },
2214         [ALC880_ASUS_DIG2] = {
2215                 .mixers = { alc880_asus_mixer },
2216                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_asus_init_verbs,
2217                                 alc880_gpio2_init_verbs }, /* use GPIO2 */
2218                 .num_dacs = ARRAY_SIZE(alc880_asus_dac_nids),
2219                 .dac_nids = alc880_asus_dac_nids,
2220                 .dig_out_nid = ALC880_DIGOUT_NID,
2221                 .num_channel_mode = ARRAY_SIZE(alc880_asus_modes),
2222                 .channel_mode = alc880_asus_modes,
2223                 .input_mux = &alc880_capture_source,
2224         },
2225         [ALC880_ASUS_W1V] = {
2226                 .mixers = { alc880_asus_mixer, alc880_asus_w1v_mixer },
2227                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_asus_init_verbs,
2228                                 alc880_gpio1_init_verbs },
2229                 .num_dacs = ARRAY_SIZE(alc880_asus_dac_nids),
2230                 .dac_nids = alc880_asus_dac_nids,
2231                 .dig_out_nid = ALC880_DIGOUT_NID,
2232                 .num_channel_mode = ARRAY_SIZE(alc880_asus_modes),
2233                 .channel_mode = alc880_asus_modes,
2234                 .input_mux = &alc880_capture_source,
2235         },
2236         [ALC880_UNIWILL_DIG] = {
2237                 .mixers = { alc880_asus_mixer, alc880_pcbeep_mixer },
2238                 .init_verbs = { alc880_volume_init_verbs, alc880_pin_asus_init_verbs },
2239                 .num_dacs = ARRAY_SIZE(alc880_asus_dac_nids),
2240                 .dac_nids = alc880_asus_dac_nids,
2241                 .dig_out_nid = ALC880_DIGOUT_NID,
2242                 .num_channel_mode = ARRAY_SIZE(alc880_asus_modes),
2243                 .channel_mode = alc880_asus_modes,
2244                 .input_mux = &alc880_capture_source,
2245         },
2246         [ALC880_CLEVO] = {
2247                 .mixers = { alc880_three_stack_mixer },
2248                 .init_verbs = { alc880_volume_init_verbs,
2249                                 alc880_pin_clevo_init_verbs },
2250                 .num_dacs = ARRAY_SIZE(alc880_dac_nids),
2251                 .dac_nids = alc880_dac_nids,
2252                 .hp_nid = 0x03,
2253                 .num_channel_mode = ARRAY_SIZE(alc880_threestack_modes),
2254                 .channel_mode = alc880_threestack_modes,
2255                 .input_mux = &alc880_capture_source,
2256         },
2257         [ALC880_LG] = {
2258                 .mixers = { alc880_lg_mixer },
2259                 .init_verbs = { alc880_volume_init_verbs,
2260                                 alc880_lg_init_verbs },
2261                 .num_dacs = ARRAY_SIZE(alc880_lg_dac_nids),
2262                 .dac_nids = alc880_lg_dac_nids,
2263                 .dig_out_nid = ALC880_DIGOUT_NID,
2264                 .num_channel_mode = ARRAY_SIZE(alc880_lg_ch_modes),
2265                 .channel_mode = alc880_lg_ch_modes,
2266                 .input_mux = &alc880_lg_capture_source,
2267                 .unsol_event = alc880_lg_unsol_event,
2268                 .init_hook = alc880_lg_automute,
2269         },
2270 #ifdef CONFIG_SND_DEBUG
2271         [ALC880_TEST] = {
2272                 .mixers = { alc880_test_mixer },
2273                 .init_verbs = { alc880_test_init_verbs },
2274                 .num_dacs = ARRAY_SIZE(alc880_test_dac_nids),
2275                 .dac_nids = alc880_test_dac_nids,
2276                 .dig_out_nid = ALC880_DIGOUT_NID,
2277                 .num_channel_mode = ARRAY_SIZE(alc880_test_modes),
2278                 .channel_mode = alc880_test_modes,
2279                 .input_mux = &alc880_test_capture_source,
2280         },
2281 #endif
2282 };
2283
2284 /*
2285  * Automatic parse of I/O pins from the BIOS configuration
2286  */
2287
2288 #define NUM_CONTROL_ALLOC       32
2289 #define NUM_VERB_ALLOC          32
2290
2291 enum {
2292         ALC_CTL_WIDGET_VOL,
2293         ALC_CTL_WIDGET_MUTE,
2294         ALC_CTL_BIND_MUTE,
2295 };
2296 static struct snd_kcontrol_new alc880_control_templates[] = {
2297         HDA_CODEC_VOLUME(NULL, 0, 0, 0),
2298         HDA_CODEC_MUTE(NULL, 0, 0, 0),
2299         HDA_BIND_MUTE(NULL, 0, 0, 0),
2300 };
2301
2302 /* add dynamic controls */
2303 static int add_control(struct alc_spec *spec, int type, const char *name, unsigned long val)
2304 {
2305         struct snd_kcontrol_new *knew;
2306
2307         if (spec->num_kctl_used >= spec->num_kctl_alloc) {
2308                 int num = spec->num_kctl_alloc + NUM_CONTROL_ALLOC;
2309
2310                 knew = kcalloc(num + 1, sizeof(*knew), GFP_KERNEL); /* array + terminator */
2311                 if (! knew)
2312                         return -ENOMEM;
2313                 if (spec->kctl_alloc) {
2314                         memcpy(knew, spec->kctl_alloc, sizeof(*knew) * spec->num_kctl_alloc);
2315                         kfree(spec->kctl_alloc);
2316                 }
2317                 spec->kctl_alloc = knew;
2318                 spec->num_kctl_alloc = num;
2319         }
2320
2321         knew = &spec->kctl_alloc[spec->num_kctl_used];
2322         *knew = alc880_control_templates[type];
2323         knew->name = kstrdup(name, GFP_KERNEL);
2324         if (! knew->name)
2325                 return -ENOMEM;
2326         knew->private_value = val;
2327         spec->num_kctl_used++;
2328         return 0;
2329 }
2330
2331 #define alc880_is_fixed_pin(nid)        ((nid) >= 0x14 && (nid) <= 0x17)
2332 #define alc880_fixed_pin_idx(nid)       ((nid) - 0x14)
2333 #define alc880_is_multi_pin(nid)        ((nid) >= 0x18)
2334 #define alc880_multi_pin_idx(nid)       ((nid) - 0x18)
2335 #define alc880_is_input_pin(nid)        ((nid) >= 0x18)
2336 #define alc880_input_pin_idx(nid)       ((nid) - 0x18)
2337 #define alc880_idx_to_dac(nid)          ((nid) + 0x02)
2338 #define alc880_dac_to_idx(nid)          ((nid) - 0x02)
2339 #define alc880_idx_to_mixer(nid)        ((nid) + 0x0c)
2340 #define alc880_idx_to_selector(nid)     ((nid) + 0x10)
2341 #define ALC880_PIN_CD_NID               0x1c
2342
2343 /* fill in the dac_nids table from the parsed pin configuration */
2344 static int alc880_auto_fill_dac_nids(struct alc_spec *spec, const struct auto_pin_cfg *cfg)
2345 {
2346         hda_nid_t nid;
2347         int assigned[4];
2348         int i, j;
2349
2350         memset(assigned, 0, sizeof(assigned));
2351         spec->multiout.dac_nids = spec->private_dac_nids;
2352
2353         /* check the pins hardwired to audio widget */
2354         for (i = 0; i < cfg->line_outs; i++) {
2355                 nid = cfg->line_out_pins[i];
2356                 if (alc880_is_fixed_pin(nid)) {
2357                         int idx = alc880_fixed_pin_idx(nid);
2358                         spec->multiout.dac_nids[i] = alc880_idx_to_dac(idx);
2359                         assigned[idx] = 1;
2360                 }
2361         }
2362         /* left pins can be connect to any audio widget */
2363         for (i = 0; i < cfg->line_outs; i++) {
2364                 nid = cfg->line_out_pins[i];
2365                 if (alc880_is_fixed_pin(nid))
2366                         continue;
2367                 /* search for an empty channel */
2368                 for (j = 0; j < cfg->line_outs; j++) {
2369                         if (! assigned[j]) {
2370                                 spec->multiout.dac_nids[i] = alc880_idx_to_dac(j);
2371                                 assigned[j] = 1;
2372                                 break;
2373                         }
2374                 }
2375         }
2376         spec->multiout.num_dacs = cfg->line_outs;
2377         return 0;
2378 }
2379
2380 /* add playback controls from the parsed DAC table */
2381 static int alc880_auto_create_multi_out_ctls(struct alc_spec *spec,
2382                                              const struct auto_pin_cfg *cfg)
2383 {
2384         char name[32];
2385         static const char *chname[4] = { "Front", "Surround", NULL /*CLFE*/, "Side" };
2386         hda_nid_t nid;
2387         int i, err;
2388
2389         for (i = 0; i < cfg->line_outs; i++) {
2390                 if (! spec->multiout.dac_nids[i])
2391                         continue;
2392                 nid = alc880_idx_to_mixer(alc880_dac_to_idx(spec->multiout.dac_nids[i]));
2393                 if (i == 2) {
2394                         /* Center/LFE */
2395                         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Center Playback Volume",
2396                                                HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT))) < 0)
2397                                 return err;
2398                         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "LFE Playback Volume",
2399                                                HDA_COMPOSE_AMP_VAL(nid, 2, 0, HDA_OUTPUT))) < 0)
2400                                 return err;
2401                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, "Center Playback Switch",
2402                                                HDA_COMPOSE_AMP_VAL(nid, 1, 2, HDA_INPUT))) < 0)
2403                                 return err;
2404                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, "LFE Playback Switch",
2405                                                HDA_COMPOSE_AMP_VAL(nid, 2, 2, HDA_INPUT))) < 0)
2406                                 return err;
2407                 } else {
2408                         sprintf(name, "%s Playback Volume", chname[i]);
2409                         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, name,
2410                                                HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
2411                                 return err;
2412                         sprintf(name, "%s Playback Switch", chname[i]);
2413                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, name,
2414                                                HDA_COMPOSE_AMP_VAL(nid, 3, 2, HDA_INPUT))) < 0)
2415                                 return err;
2416                 }
2417         }
2418         return 0;
2419 }
2420
2421 /* add playback controls for speaker and HP outputs */
2422 static int alc880_auto_create_extra_out(struct alc_spec *spec, hda_nid_t pin,
2423                                         const char *pfx)
2424 {
2425         hda_nid_t nid;
2426         int err;
2427         char name[32];
2428
2429         if (! pin)
2430                 return 0;
2431
2432         if (alc880_is_fixed_pin(pin)) {
2433                 nid = alc880_idx_to_dac(alc880_fixed_pin_idx(pin));
2434                 if (! spec->multiout.dac_nids[0]) {
2435                         /* use this as the primary output */
2436                         spec->multiout.dac_nids[0] = nid;
2437                         if (! spec->multiout.num_dacs)
2438                                 spec->multiout.num_dacs = 1;
2439                 } else 
2440                         /* specify the DAC as the extra output */
2441                         spec->multiout.hp_nid = nid;
2442                 /* control HP volume/switch on the output mixer amp */
2443                 nid = alc880_idx_to_mixer(alc880_fixed_pin_idx(pin));
2444                 sprintf(name, "%s Playback Volume", pfx);
2445                 if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, name,
2446                                        HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
2447                         return err;
2448                 sprintf(name, "%s Playback Switch", pfx);
2449                 if ((err = add_control(spec, ALC_CTL_BIND_MUTE, name,
2450                                        HDA_COMPOSE_AMP_VAL(nid, 3, 2, HDA_INPUT))) < 0)
2451                         return err;
2452         } else if (alc880_is_multi_pin(pin)) {
2453                 /* set manual connection */
2454                 if (! spec->multiout.dac_nids[0]) {
2455                         /* use this as the primary output */
2456                         spec->multiout.dac_nids[0] = alc880_idx_to_dac(alc880_multi_pin_idx(pin));
2457                         if (! spec->multiout.num_dacs)
2458                                 spec->multiout.num_dacs = 1;
2459                 }
2460                 /* we have only a switch on HP-out PIN */
2461                 sprintf(name, "%s Playback Switch", pfx);
2462                 if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, name,
2463                                        HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT))) < 0)
2464                         return err;
2465         }
2466         return 0;
2467 }
2468
2469 /* create input playback/capture controls for the given pin */
2470 static int new_analog_input(struct alc_spec *spec, hda_nid_t pin, const char *ctlname,
2471                             int idx, hda_nid_t mix_nid)
2472 {
2473         char name[32];
2474         int err;
2475
2476         sprintf(name, "%s Playback Volume", ctlname);
2477         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, name,
2478                                HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT))) < 0)
2479                 return err;
2480         sprintf(name, "%s Playback Switch", ctlname);
2481         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, name,
2482                                HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT))) < 0)
2483                 return err;
2484         return 0;
2485 }
2486
2487 /* create playback/capture controls for input pins */
2488 static int alc880_auto_create_analog_input_ctls(struct alc_spec *spec,
2489                                                 const struct auto_pin_cfg *cfg)
2490 {
2491         struct hda_input_mux *imux = &spec->private_imux;
2492         int i, err, idx;
2493
2494         for (i = 0; i < AUTO_PIN_LAST; i++) {
2495                 if (alc880_is_input_pin(cfg->input_pins[i])) {
2496                         idx = alc880_input_pin_idx(cfg->input_pins[i]);
2497                         err = new_analog_input(spec, cfg->input_pins[i],
2498                                                auto_pin_cfg_labels[i],
2499                                                idx, 0x0b);
2500                         if (err < 0)
2501                                 return err;
2502                         imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
2503                         imux->items[imux->num_items].index = alc880_input_pin_idx(cfg->input_pins[i]);
2504                         imux->num_items++;
2505                 }
2506         }
2507         return 0;
2508 }
2509
2510 static void alc880_auto_set_output_and_unmute(struct hda_codec *codec,
2511                                               hda_nid_t nid, int pin_type,
2512                                               int dac_idx)
2513 {
2514         /* set as output */
2515         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
2516         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE);
2517         /* need the manual connection? */
2518         if (alc880_is_multi_pin(nid)) {
2519                 struct alc_spec *spec = codec->spec;
2520                 int idx = alc880_multi_pin_idx(nid);
2521                 snd_hda_codec_write(codec, alc880_idx_to_selector(idx), 0,
2522                                     AC_VERB_SET_CONNECT_SEL,
2523                                     alc880_dac_to_idx(spec->multiout.dac_nids[dac_idx]));
2524         }
2525 }
2526
2527 static void alc880_auto_init_multi_out(struct hda_codec *codec)
2528 {
2529         struct alc_spec *spec = codec->spec;
2530         int i;
2531
2532         for (i = 0; i < spec->autocfg.line_outs; i++) {
2533                 hda_nid_t nid = spec->autocfg.line_out_pins[i];
2534                 alc880_auto_set_output_and_unmute(codec, nid, PIN_OUT, i);
2535         }
2536 }
2537
2538 static void alc880_auto_init_extra_out(struct hda_codec *codec)
2539 {
2540         struct alc_spec *spec = codec->spec;
2541         hda_nid_t pin;
2542
2543         pin = spec->autocfg.speaker_pin;
2544         if (pin) /* connect to front */
2545                 alc880_auto_set_output_and_unmute(codec, pin, PIN_OUT, 0);
2546         pin = spec->autocfg.hp_pin;
2547         if (pin) /* connect to front */
2548                 alc880_auto_set_output_and_unmute(codec, pin, PIN_HP, 0);
2549 }
2550
2551 static void alc880_auto_init_analog_input(struct hda_codec *codec)
2552 {
2553         struct alc_spec *spec = codec->spec;
2554         int i;
2555
2556         for (i = 0; i < AUTO_PIN_LAST; i++) {
2557                 hda_nid_t nid = spec->autocfg.input_pins[i];
2558                 if (alc880_is_input_pin(nid)) {
2559                         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
2560                                             i <= AUTO_PIN_FRONT_MIC ? PIN_VREF80 : PIN_IN);
2561                         if (nid != ALC880_PIN_CD_NID)
2562                                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
2563                                                     AMP_OUT_MUTE);
2564                 }
2565         }
2566 }
2567
2568 /* parse the BIOS configuration and set up the alc_spec */
2569 /* return 1 if successful, 0 if the proper config is not found, or a negative error code */
2570 static int alc880_parse_auto_config(struct hda_codec *codec)
2571 {
2572         struct alc_spec *spec = codec->spec;
2573         int err;
2574         static hda_nid_t alc880_ignore[] = { 0x1d, 0 };
2575
2576         if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg,
2577                                                 alc880_ignore)) < 0)
2578                 return err;
2579         if (! spec->autocfg.line_outs && ! spec->autocfg.speaker_pin &&
2580             ! spec->autocfg.hp_pin)
2581                 return 0; /* can't find valid BIOS pin config */
2582
2583         if ((err = alc880_auto_fill_dac_nids(spec, &spec->autocfg)) < 0 ||
2584             (err = alc880_auto_create_multi_out_ctls(spec, &spec->autocfg)) < 0 ||
2585             (err = alc880_auto_create_extra_out(spec, spec->autocfg.speaker_pin,
2586                                                 "Speaker")) < 0 ||
2587             (err = alc880_auto_create_extra_out(spec, spec->autocfg.speaker_pin,
2588                                                 "Headphone")) < 0 ||
2589             (err = alc880_auto_create_analog_input_ctls(spec, &spec->autocfg)) < 0)
2590                 return err;
2591
2592         spec->multiout.max_channels = spec->multiout.num_dacs * 2;
2593
2594         if (spec->autocfg.dig_out_pin)
2595                 spec->multiout.dig_out_nid = ALC880_DIGOUT_NID;
2596         if (spec->autocfg.dig_in_pin)
2597                 spec->dig_in_nid = ALC880_DIGIN_NID;
2598
2599         if (spec->kctl_alloc)
2600                 spec->mixers[spec->num_mixers++] = spec->kctl_alloc;
2601
2602         spec->init_verbs[spec->num_init_verbs++] = alc880_volume_init_verbs;
2603
2604         spec->input_mux = &spec->private_imux;
2605
2606         return 1;
2607 }
2608
2609 /* additional initialization for auto-configuration model */
2610 static void alc880_auto_init(struct hda_codec *codec)
2611 {
2612         alc880_auto_init_multi_out(codec);
2613         alc880_auto_init_extra_out(codec);
2614         alc880_auto_init_analog_input(codec);
2615 }
2616
2617 /*
2618  * OK, here we have finally the patch for ALC880
2619  */
2620
2621 static int patch_alc880(struct hda_codec *codec)
2622 {
2623         struct alc_spec *spec;
2624         int board_config;
2625         int err;
2626
2627         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
2628         if (spec == NULL)
2629                 return -ENOMEM;
2630
2631         codec->spec = spec;
2632
2633         board_config = snd_hda_check_board_config(codec, alc880_cfg_tbl);
2634         if (board_config < 0 || board_config >= ALC880_MODEL_LAST) {
2635                 printk(KERN_INFO "hda_codec: Unknown model for ALC880, trying auto-probe from BIOS...\n");
2636                 board_config = ALC880_AUTO;
2637         }
2638
2639         if (board_config == ALC880_AUTO) {
2640                 /* automatic parse from the BIOS config */
2641                 err = alc880_parse_auto_config(codec);
2642                 if (err < 0) {
2643                         alc_free(codec);
2644                         return err;
2645                 } else if (! err) {
2646                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using 3-stack mode...\n");
2647                         board_config = ALC880_3ST;
2648                 }
2649         }
2650
2651         if (board_config != ALC880_AUTO)
2652                 setup_preset(spec, &alc880_presets[board_config]);
2653
2654         spec->stream_name_analog = "ALC880 Analog";
2655         spec->stream_analog_playback = &alc880_pcm_analog_playback;
2656         spec->stream_analog_capture = &alc880_pcm_analog_capture;
2657
2658         spec->stream_name_digital = "ALC880 Digital";
2659         spec->stream_digital_playback = &alc880_pcm_digital_playback;
2660         spec->stream_digital_capture = &alc880_pcm_digital_capture;
2661
2662         if (! spec->adc_nids && spec->input_mux) {
2663                 /* check whether NID 0x07 is valid */
2664                 unsigned int wcap = get_wcaps(codec, alc880_adc_nids[0]);
2665                 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT; /* get type */
2666                 if (wcap != AC_WID_AUD_IN) {
2667                         spec->adc_nids = alc880_adc_nids_alt;
2668                         spec->num_adc_nids = ARRAY_SIZE(alc880_adc_nids_alt);
2669                         spec->mixers[spec->num_mixers] = alc880_capture_alt_mixer;
2670                         spec->num_mixers++;
2671                 } else {
2672                         spec->adc_nids = alc880_adc_nids;
2673                         spec->num_adc_nids = ARRAY_SIZE(alc880_adc_nids);
2674                         spec->mixers[spec->num_mixers] = alc880_capture_mixer;
2675                         spec->num_mixers++;
2676                 }
2677         }
2678
2679         codec->patch_ops = alc_patch_ops;
2680         if (board_config == ALC880_AUTO)
2681                 spec->init_hook = alc880_auto_init;
2682
2683         return 0;
2684 }
2685
2686
2687 /*
2688  * ALC260 support
2689  */
2690
2691 static hda_nid_t alc260_dac_nids[1] = {
2692         /* front */
2693         0x02,
2694 };
2695
2696 static hda_nid_t alc260_adc_nids[1] = {
2697         /* ADC0 */
2698         0x04,
2699 };
2700
2701 static hda_nid_t alc260_adc_nids_alt[1] = {
2702         /* ADC1 */
2703         0x05,
2704 };
2705
2706 static hda_nid_t alc260_hp_adc_nids[2] = {
2707         /* ADC1, 0 */
2708         0x05, 0x04
2709 };
2710
2711 /* NIDs used when simultaneous access to both ADCs makes sense.  Note that
2712  * alc260_capture_mixer assumes ADC0 (nid 0x04) is the first ADC.
2713  */
2714 static hda_nid_t alc260_dual_adc_nids[2] = {
2715         /* ADC0, ADC1 */
2716         0x04, 0x05
2717 };
2718
2719 #define ALC260_DIGOUT_NID       0x03
2720 #define ALC260_DIGIN_NID        0x06
2721
2722 static struct hda_input_mux alc260_capture_source = {
2723         .num_items = 4,
2724         .items = {
2725                 { "Mic", 0x0 },
2726                 { "Front Mic", 0x1 },
2727                 { "Line", 0x2 },
2728                 { "CD", 0x4 },
2729         },
2730 };
2731
2732 /* On Fujitsu S702x laptops capture only makes sense from Mic/LineIn jack,
2733  * headphone jack and the internal CD lines.
2734  */
2735 static struct hda_input_mux alc260_fujitsu_capture_source = {
2736         .num_items = 3,
2737         .items = {
2738                 { "Mic/Line", 0x0 },
2739                 { "CD", 0x4 },
2740                 { "Headphone", 0x2 },
2741         },
2742 };
2743
2744 /* Acer TravelMate(/Extensa/Aspire) notebooks have similar configutation to
2745  * the Fujitsu S702x, but jacks are marked differently. We won't allow
2746  * retasking the Headphone jack, so it won't be available here.
2747  */
2748 static struct hda_input_mux alc260_acer_capture_source = {
2749         .num_items = 3,
2750         .items = {
2751                 { "Mic", 0x0 },
2752                 { "Line", 0x2 },
2753                 { "CD", 0x4 },
2754         },
2755 };
2756
2757 /*
2758  * This is just place-holder, so there's something for alc_build_pcms to look
2759  * at when it calculates the maximum number of channels. ALC260 has no mixer
2760  * element which allows changing the channel mode, so the verb list is
2761  * never used.
2762  */
2763 static struct hda_channel_mode alc260_modes[1] = {
2764         { 2, NULL },
2765 };
2766
2767
2768 /* Mixer combinations
2769  *
2770  * basic: base_output + input + pc_beep + capture
2771  * HP: base_output + input + capture_alt
2772  * HP_3013: hp_3013 + input + capture
2773  * fujitsu: fujitsu + capture
2774  * acer: acer + capture
2775  */
2776
2777 static struct snd_kcontrol_new alc260_base_output_mixer[] = {
2778         HDA_CODEC_VOLUME("Front Playback Volume", 0x08, 0x0, HDA_OUTPUT),
2779         HDA_BIND_MUTE("Front Playback Switch", 0x08, 2, HDA_INPUT),
2780         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x09, 0x0, HDA_OUTPUT),
2781         HDA_BIND_MUTE("Headphone Playback Switch", 0x09, 2, HDA_INPUT),
2782         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT),
2783         HDA_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_INPUT),
2784         { } /* end */
2785 };      
2786
2787 static struct snd_kcontrol_new alc260_input_mixer[] = {
2788         HDA_CODEC_VOLUME("CD Playback Volume", 0x07, 0x04, HDA_INPUT),
2789         HDA_CODEC_MUTE("CD Playback Switch", 0x07, 0x04, HDA_INPUT),
2790         HDA_CODEC_VOLUME("Line Playback Volume", 0x07, 0x02, HDA_INPUT),
2791         HDA_CODEC_MUTE("Line Playback Switch", 0x07, 0x02, HDA_INPUT),
2792         HDA_CODEC_VOLUME("Mic Playback Volume", 0x07, 0x0, HDA_INPUT),
2793         HDA_CODEC_MUTE("Mic Playback Switch", 0x07, 0x0, HDA_INPUT),
2794         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x07, 0x01, HDA_INPUT),
2795         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x07, 0x01, HDA_INPUT),
2796         { } /* end */
2797 };
2798
2799 static struct snd_kcontrol_new alc260_pc_beep_mixer[] = {
2800         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x07, 0x05, HDA_INPUT),
2801         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x07, 0x05, HDA_INPUT),
2802         { } /* end */
2803 };
2804
2805 static struct snd_kcontrol_new alc260_hp_3013_mixer[] = {
2806         HDA_CODEC_VOLUME("Front Playback Volume", 0x09, 0x0, HDA_OUTPUT),
2807         HDA_CODEC_MUTE("Front Playback Switch", 0x10, 0x0, HDA_OUTPUT),
2808         HDA_CODEC_VOLUME("Aux-In Playback Volume", 0x07, 0x06, HDA_INPUT),
2809         HDA_CODEC_MUTE("Aux-In Playback Switch", 0x07, 0x06, HDA_INPUT),
2810         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x08, 0x0, HDA_OUTPUT),
2811         HDA_CODEC_MUTE("Headphone Playback Switch", 0x15, 0x0, HDA_OUTPUT),
2812         HDA_CODEC_VOLUME_MONO("iSpeaker Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT),
2813         HDA_CODEC_MUTE_MONO("iSpeaker Playback Switch", 0x11, 1, 0x0, HDA_OUTPUT),
2814         { } /* end */
2815 };
2816
2817 static struct snd_kcontrol_new alc260_fujitsu_mixer[] = {
2818         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x08, 0x0, HDA_OUTPUT),
2819         HDA_BIND_MUTE("Headphone Playback Switch", 0x08, 2, HDA_INPUT),
2820         ALC_PIN_MODE("Headphone Jack Mode", 0x14, ALC_PIN_DIR_INOUT),
2821         HDA_CODEC_VOLUME("CD Playback Volume", 0x07, 0x04, HDA_INPUT),
2822         HDA_CODEC_MUTE("CD Playback Switch", 0x07, 0x04, HDA_INPUT),
2823         HDA_CODEC_VOLUME("Mic/Line Playback Volume", 0x07, 0x0, HDA_INPUT),
2824         HDA_CODEC_MUTE("Mic/Line Playback Switch", 0x07, 0x0, HDA_INPUT),
2825         ALC_PIN_MODE("Mic/Line Jack Mode", 0x12, ALC_PIN_DIR_IN),
2826         HDA_CODEC_VOLUME("Beep Playback Volume", 0x07, 0x05, HDA_INPUT),
2827         HDA_CODEC_MUTE("Beep Playback Switch", 0x07, 0x05, HDA_INPUT),
2828         HDA_CODEC_VOLUME("Internal Speaker Playback Volume", 0x09, 0x0, HDA_OUTPUT),
2829         HDA_BIND_MUTE("Internal Speaker Playback Switch", 0x09, 2, HDA_INPUT),
2830         { } /* end */
2831 };
2832
2833 static struct snd_kcontrol_new alc260_acer_mixer[] = {
2834         HDA_CODEC_VOLUME("Master Playback Volume", 0x08, 0x0, HDA_OUTPUT),
2835         HDA_BIND_MUTE("Master Playback Switch", 0x08, 2, HDA_INPUT),
2836         HDA_CODEC_VOLUME("CD Playback Volume", 0x07, 0x04, HDA_INPUT),
2837         HDA_CODEC_MUTE("CD Playback Switch", 0x07, 0x04, HDA_INPUT),
2838         HDA_CODEC_VOLUME("Mic Playback Volume", 0x07, 0x0, HDA_INPUT),
2839         HDA_CODEC_MUTE("Mic Playback Switch", 0x07, 0x0, HDA_INPUT),
2840         ALC_PIN_MODE("Mic Jack Mode", 0x12, ALC_PIN_DIR_IN),
2841         HDA_CODEC_VOLUME("Line Playback Volume", 0x07, 0x02, HDA_INPUT),
2842         HDA_CODEC_MUTE("Line Playback Switch", 0x07, 0x02, HDA_INPUT),
2843         ALC_PIN_MODE("Line Jack Mode", 0x14, ALC_PIN_DIR_INOUT),
2844         HDA_CODEC_VOLUME("Beep Playback Volume", 0x07, 0x05, HDA_INPUT),
2845         HDA_CODEC_MUTE("Beep Playback Switch", 0x07, 0x05, HDA_INPUT),
2846         { } /* end */
2847 };
2848
2849 /* capture mixer elements */
2850 static struct snd_kcontrol_new alc260_capture_mixer[] = {
2851         HDA_CODEC_VOLUME("Capture Volume", 0x04, 0x0, HDA_INPUT),
2852         HDA_CODEC_MUTE("Capture Switch", 0x04, 0x0, HDA_INPUT),
2853         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x05, 0x0, HDA_INPUT),
2854         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x05, 0x0, HDA_INPUT),
2855         {
2856                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2857                 /* The multiple "Capture Source" controls confuse alsamixer
2858                  * So call somewhat different..
2859                  * FIXME: the controls appear in the "playback" view!
2860                  */
2861                 /* .name = "Capture Source", */
2862                 .name = "Input Source",
2863                 .count = 2,
2864                 .info = alc_mux_enum_info,
2865                 .get = alc_mux_enum_get,
2866                 .put = alc_mux_enum_put,
2867         },
2868         { } /* end */
2869 };
2870
2871 static struct snd_kcontrol_new alc260_capture_alt_mixer[] = {
2872         HDA_CODEC_VOLUME("Capture Volume", 0x05, 0x0, HDA_INPUT),
2873         HDA_CODEC_MUTE("Capture Switch", 0x05, 0x0, HDA_INPUT),
2874         {
2875                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2876                 /* The multiple "Capture Source" controls confuse alsamixer
2877                  * So call somewhat different..
2878                  * FIXME: the controls appear in the "playback" view!
2879                  */
2880                 /* .name = "Capture Source", */
2881                 .name = "Input Source",
2882                 .count = 1,
2883                 .info = alc_mux_enum_info,
2884                 .get = alc_mux_enum_get,
2885                 .put = alc_mux_enum_put,
2886         },
2887         { } /* end */
2888 };
2889
2890 /*
2891  * initialization verbs
2892  */
2893 static struct hda_verb alc260_init_verbs[] = {
2894         /* Line In pin widget for input */
2895         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
2896         /* CD pin widget for input */
2897         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
2898         /* Mic1 (rear panel) pin widget for input and vref at 80% */
2899         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2900         /* Mic2 (front panel) pin widget for input and vref at 80% */
2901         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2902         /* LINE-2 is used for line-out in rear */
2903         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2904         /* select line-out */
2905         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x00},
2906         /* LINE-OUT pin */
2907         {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2908         /* enable HP */
2909         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
2910         /* enable Mono */
2911         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2912         /* mute capture amp left and right */
2913         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
2914         /* set connection select to line in (default select for this ADC) */
2915         {0x04, AC_VERB_SET_CONNECT_SEL, 0x02},
2916         /* mute capture amp left and right */
2917         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
2918         /* set connection select to line in (default select for this ADC) */
2919         {0x05, AC_VERB_SET_CONNECT_SEL, 0x02},
2920         /* set vol=0 Line-Out mixer amp left and right */
2921         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2922         /* unmute pin widget amp left and right (no gain on this amp) */
2923         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2924         /* set vol=0 HP mixer amp left and right */
2925         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2926         /* unmute pin widget amp left and right (no gain on this amp) */
2927         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2928         /* set vol=0 Mono mixer amp left and right */
2929         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2930         /* unmute pin widget amp left and right (no gain on this amp) */
2931         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2932         /* unmute LINE-2 out pin */
2933         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2934         /* Amp Indexes: CD = 0x04, Line In 1 = 0x02, Mic 1 = 0x00 & Line In 2 = 0x03 */
2935         /* mute CD */
2936         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
2937         /* mute Line In */
2938         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
2939         /* mute Mic */
2940         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
2941         /* Amp Indexes: DAC = 0x01 & mixer = 0x00 */
2942         /* mute Front out path */
2943         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2944         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2945         /* mute Headphone out path */
2946         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2947         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2948         /* mute Mono out path */
2949         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2950         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2951         { }
2952 };
2953
2954 static struct hda_verb alc260_hp_init_verbs[] = {
2955         /* Headphone and output */
2956         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0},
2957         /* mono output */
2958         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
2959         /* Mic1 (rear panel) pin widget for input and vref at 80% */
2960         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24},
2961         /* Mic2 (front panel) pin widget for input and vref at 80% */
2962         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24},
2963         /* Line In pin widget for input */
2964         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
2965         /* Line-2 pin widget for output */
2966         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
2967         /* CD pin widget for input */
2968         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
2969         /* unmute amp left and right */
2970         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, 0x7000},
2971         /* set connection select to line in (default select for this ADC) */
2972         {0x04, AC_VERB_SET_CONNECT_SEL, 0x02},
2973         /* unmute Line-Out mixer amp left and right (volume = 0) */
2974         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
2975         /* mute pin widget amp left and right (no gain on this amp) */
2976         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
2977         /* unmute HP mixer amp left and right (volume = 0) */
2978         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
2979         /* mute pin widget amp left and right (no gain on this amp) */
2980         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
2981         /* Amp Indexes: CD = 0x04, Line In 1 = 0x02, Mic 1 = 0x00 & Line In 2 = 0x03 */
2982         /* unmute CD */
2983         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x04 << 8))},
2984         /* unmute Line In */
2985         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x02 << 8))},
2986         /* unmute Mic */
2987         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
2988         /* Amp Indexes: DAC = 0x01 & mixer = 0x00 */
2989         /* Unmute Front out path */
2990         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
2991         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
2992         /* Unmute Headphone out path */
2993         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
2994         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
2995         /* Unmute Mono out path */
2996         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
2997         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
2998         { }
2999 };
3000
3001 static struct hda_verb alc260_hp_3013_init_verbs[] = {
3002         /* Line out and output */
3003         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
3004         /* mono output */
3005         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
3006         /* Mic1 (rear panel) pin widget for input and vref at 80% */
3007         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24},
3008         /* Mic2 (front panel) pin widget for input and vref at 80% */
3009         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24},
3010         /* Line In pin widget for input */
3011         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
3012         /* Headphone pin widget for output */
3013         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0},
3014         /* CD pin widget for input */
3015         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
3016         /* unmute amp left and right */
3017         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, 0x7000},
3018         /* set connection select to line in (default select for this ADC) */
3019         {0x04, AC_VERB_SET_CONNECT_SEL, 0x02},
3020         /* unmute Line-Out mixer amp left and right (volume = 0) */
3021         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
3022         /* mute pin widget amp left and right (no gain on this amp) */
3023         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
3024         /* unmute HP mixer amp left and right (volume = 0) */
3025         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
3026         /* mute pin widget amp left and right (no gain on this amp) */
3027         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
3028         /* Amp Indexes: CD = 0x04, Line In 1 = 0x02, Mic 1 = 0x00 & Line In 2 = 0x03 */
3029         /* unmute CD */
3030         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x04 << 8))},
3031         /* unmute Line In */
3032         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x02 << 8))},
3033         /* unmute Mic */
3034         {0x07,  AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
3035         /* Amp Indexes: DAC = 0x01 & mixer = 0x00 */
3036         /* Unmute Front out path */
3037         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
3038         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
3039         /* Unmute Headphone out path */
3040         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
3041         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
3042         /* Unmute Mono out path */
3043         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
3044         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8))},
3045         { }
3046 };
3047
3048 /* Initialisation sequence for ALC260 as configured in Fujitsu S702x
3049  * laptops.
3050  */
3051 static struct hda_verb alc260_fujitsu_init_verbs[] = {
3052         /* Disable all GPIOs */
3053         {0x01, AC_VERB_SET_GPIO_MASK, 0},
3054         /* Internal speaker is connected to headphone pin */
3055         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3056         /* Headphone/Line-out jack connects to Line1 pin; make it an output */
3057         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3058         /* Mic/Line-in jack is connected to mic1 pin, so make it an input */
3059         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3060         /* Ensure all other unused pins are disabled and muted. */
3061         {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3062         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3063         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3064         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3065         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3066         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3067         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3068         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3069
3070         /* Disable digital (SPDIF) pins */
3071         {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0},
3072         {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0},
3073
3074         /* Ensure Line1 pin widget takes its input from the OUT1 sum bus 
3075          * when acting as an output.
3076          */
3077         {0x0d, AC_VERB_SET_CONNECT_SEL, 0},
3078
3079         /* Start with output sum widgets muted and their output gains at min */
3080         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3081         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3082         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3083         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3084         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3085         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3086         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3087         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3088         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3089
3090         /* Unmute HP pin widget amp left and right (no equiv mixer ctrl) */
3091         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3092         /* Unmute Line1 pin widget output buffer since it starts as an output.
3093          * If the pin mode is changed by the user the pin mode control will
3094          * take care of enabling the pin's input/output buffers as needed.
3095          * Therefore there's no need to enable the input buffer at this
3096          * stage.
3097          */
3098         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3099         /* Unmute input buffer of pin widget used for Line-in (no equiv 
3100          * mixer ctrl)
3101          */
3102         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3103
3104         /* Mute capture amp left and right */
3105         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3106         /* Set ADC connection select to match default mixer setting - line 
3107          * in (on mic1 pin)
3108          */
3109         {0x04, AC_VERB_SET_CONNECT_SEL, 0x00},
3110
3111         /* Do the same for the second ADC: mute capture input amp and
3112          * set ADC connection to line in (on mic1 pin)
3113          */
3114         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3115         {0x05, AC_VERB_SET_CONNECT_SEL, 0x00},
3116
3117         /* Mute all inputs to mixer widget (even unconnected ones) */
3118         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, /* mic1 pin */
3119         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, /* mic2 pin */
3120         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, /* line1 pin */
3121         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, /* line2 pin */
3122         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, /* CD pin */
3123         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)}, /* Beep-gen pin */
3124         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)}, /* Line-out pin */
3125         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)}, /* HP-pin pin */
3126
3127         { }
3128 };
3129
3130 /* Initialisation sequence for ALC260 as configured in Acer TravelMate and
3131  * similar laptops (adapted from Fujitsu init verbs).
3132  */
3133 static struct hda_verb alc260_acer_init_verbs[] = {
3134         /* On TravelMate laptops, GPIO 0 enables the internal speaker and
3135          * the headphone jack.  Turn this on and rely on the standard mute
3136          * methods whenever the user wants to turn these outputs off.
3137          */
3138         {0x01, AC_VERB_SET_GPIO_MASK, 0x01},
3139         {0x01, AC_VERB_SET_GPIO_DIRECTION, 0x01},
3140         {0x01, AC_VERB_SET_GPIO_DATA, 0x01},
3141         /* Internal speaker/Headphone jack is connected to Line-out pin */
3142         {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3143         /* Internal microphone/Mic jack is connected to Mic1 pin */
3144         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF50},
3145         /* Line In jack is connected to Line1 pin */
3146         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3147         /* Ensure all other unused pins are disabled and muted. */
3148         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3149         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3150         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3151         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3152         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3153         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3154         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, 0},
3155         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3156         /* Disable digital (SPDIF) pins */
3157         {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0},
3158         {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0},
3159
3160         /* Ensure Mic1 and Line1 pin widgets take input from the OUT1 sum 
3161          * bus when acting as outputs.
3162          */
3163         {0x0b, AC_VERB_SET_CONNECT_SEL, 0},
3164         {0x0d, AC_VERB_SET_CONNECT_SEL, 0},
3165
3166         /* Start with output sum widgets muted and their output gains at min */
3167         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3168         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3169         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3170         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3171         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3172         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3173         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3174         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3175         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3176
3177         /* Unmute Line-out pin widget amp left and right (no equiv mixer ctrl) */
3178         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3179         /* Unmute Mic1 and Line1 pin widget input buffers since they start as
3180          * inputs. If the pin mode is changed by the user the pin mode control
3181          * will take care of enabling the pin's input/output buffers as needed.
3182          * Therefore there's no need to enable the input buffer at this
3183          * stage.
3184          */
3185         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3186         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3187
3188         /* Mute capture amp left and right */
3189         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3190         /* Set ADC connection select to match default mixer setting - mic
3191          * (on mic1 pin)
3192          */
3193         {0x04, AC_VERB_SET_CONNECT_SEL, 0x00},
3194
3195         /* Do similar with the second ADC: mute capture input amp and
3196          * set ADC connection to line (on line1 pin)
3197          */
3198         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3199         {0x05, AC_VERB_SET_CONNECT_SEL, 0x02},
3200
3201         /* Mute all inputs to mixer widget (even unconnected ones) */
3202         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, /* mic1 pin */
3203         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, /* mic2 pin */
3204         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, /* line1 pin */
3205         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, /* line2 pin */
3206         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, /* CD pin */
3207         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)}, /* Beep-gen pin */
3208         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)}, /* Line-out pin */
3209         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)}, /* HP-pin pin */
3210
3211         { }
3212 };
3213
3214 /* Test configuration for debugging, modelled after the ALC880 test
3215  * configuration.
3216  */
3217 #ifdef CONFIG_SND_DEBUG
3218 static hda_nid_t alc260_test_dac_nids[1] = {
3219         0x02,
3220 };
3221 static hda_nid_t alc260_test_adc_nids[2] = {
3222         0x04, 0x05,
3223 };
3224 /* This is a bit messy since the two input muxes in the ALC260 have slight
3225  * variations in their signal assignments.  The ideal way to deal with this
3226  * is to extend alc_spec.input_mux to allow a different input MUX for each
3227  * ADC.  For the purposes of the test model it's sufficient to just list
3228  * both options for affected signal indices.  The separate input mux
3229  * functionality only needs to be considered if a model comes along which
3230  * actually uses signals 0x5, 0x6 and 0x7 for something which makes sense to
3231  * record.
3232  */
3233 static struct hda_input_mux alc260_test_capture_source = {
3234         .num_items = 8,
3235         .items = {
3236                 { "MIC1 pin", 0x0 },
3237                 { "MIC2 pin", 0x1 },
3238                 { "LINE1 pin", 0x2 },
3239                 { "LINE2 pin", 0x3 },
3240                 { "CD pin", 0x4 },
3241                 { "LINE-OUT pin (cap1), Mixer (cap2)", 0x5 },
3242                 { "HP-OUT pin (cap1), LINE-OUT pin (cap2)", 0x6 },
3243                 { "HP-OUT pin (cap2 only)", 0x7 },
3244         },
3245 };
3246 static struct snd_kcontrol_new alc260_test_mixer[] = {
3247         /* Output driver widgets */
3248         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT),
3249         HDA_BIND_MUTE_MONO("Mono Playback Switch", 0x0a, 1, 2, HDA_INPUT),
3250         HDA_CODEC_VOLUME("LOUT2 Playback Volume", 0x09, 0x0, HDA_OUTPUT),
3251         HDA_BIND_MUTE("LOUT2 Playback Switch", 0x09, 2, HDA_INPUT),
3252         HDA_CODEC_VOLUME("LOUT1 Playback Volume", 0x08, 0x0, HDA_OUTPUT),
3253         HDA_BIND_MUTE("LOUT1 Playback Switch", 0x08, 2, HDA_INPUT),
3254
3255         /* Modes for retasking pin widgets */
3256         ALC_PIN_MODE("HP-OUT pin mode", 0x10, ALC_PIN_DIR_INOUT),
3257         ALC_PIN_MODE("LINE-OUT pin mode", 0x0f, ALC_PIN_DIR_INOUT),
3258         ALC_PIN_MODE("LINE2 pin mode", 0x15, ALC_PIN_DIR_INOUT),
3259         ALC_PIN_MODE("LINE1 pin mode", 0x14, ALC_PIN_DIR_INOUT),
3260         ALC_PIN_MODE("MIC2 pin mode", 0x13, ALC_PIN_DIR_INOUT),
3261         ALC_PIN_MODE("MIC1 pin mode", 0x12, ALC_PIN_DIR_INOUT),
3262
3263         /* Loopback mixer controls */
3264         HDA_CODEC_VOLUME("MIC1 Playback Volume", 0x07, 0x00, HDA_INPUT),
3265         HDA_CODEC_MUTE("MIC1 Playback Switch", 0x07, 0x00, HDA_INPUT),
3266         HDA_CODEC_VOLUME("MIC2 Playback Volume", 0x07, 0x01, HDA_INPUT),
3267         HDA_CODEC_MUTE("MIC2 Playback Switch", 0x07, 0x01, HDA_INPUT),
3268         HDA_CODEC_VOLUME("LINE1 Playback Volume", 0x07, 0x02, HDA_INPUT),
3269         HDA_CODEC_MUTE("LINE1 Playback Switch", 0x07, 0x02, HDA_INPUT),
3270         HDA_CODEC_VOLUME("LINE2 Playback Volume", 0x07, 0x03, HDA_INPUT),
3271         HDA_CODEC_MUTE("LINE2 Playback Switch", 0x07, 0x03, HDA_INPUT),
3272         HDA_CODEC_VOLUME("CD Playback Volume", 0x07, 0x04, HDA_INPUT),
3273         HDA_CODEC_MUTE("CD Playback Switch", 0x07, 0x04, HDA_INPUT),
3274         HDA_CODEC_VOLUME("Beep Playback Volume", 0x07, 0x05, HDA_INPUT),
3275         HDA_CODEC_MUTE("Beep Playback Switch", 0x07, 0x05, HDA_INPUT),
3276         HDA_CODEC_VOLUME("LINE-OUT loopback Playback Volume", 0x07, 0x06, HDA_INPUT),
3277         HDA_CODEC_MUTE("LINE-OUT loopback Playback Switch", 0x07, 0x06, HDA_INPUT),
3278         HDA_CODEC_VOLUME("HP-OUT loopback Playback Volume", 0x07, 0x7, HDA_INPUT),
3279         HDA_CODEC_MUTE("HP-OUT loopback Playback Switch", 0x07, 0x7, HDA_INPUT),
3280
3281         /* Controls for GPIO pins, assuming they are configured as outputs */
3282         ALC_GPIO_DATA_SWITCH("GPIO pin 0", 0x01, 0x01),
3283         ALC_GPIO_DATA_SWITCH("GPIO pin 1", 0x01, 0x02),
3284         ALC_GPIO_DATA_SWITCH("GPIO pin 2", 0x01, 0x04),
3285         ALC_GPIO_DATA_SWITCH("GPIO pin 3", 0x01, 0x08),
3286
3287         /* Switches to allow the digital IO pins to be enabled.  The datasheet
3288          * is ambigious as to which NID is which; testing on laptops which
3289          * make this output available should provide clarification. 
3290          */
3291         ALC_SPDIF_CTRL_SWITCH("SPDIF Playback Switch", 0x03, 0x01),
3292         ALC_SPDIF_CTRL_SWITCH("SPDIF Capture Switch", 0x06, 0x01),
3293
3294         { } /* end */
3295 };
3296 static struct hda_verb alc260_test_init_verbs[] = {
3297         /* Enable all GPIOs as outputs with an initial value of 0 */
3298         {0x01, AC_VERB_SET_GPIO_DIRECTION, 0x0f},
3299         {0x01, AC_VERB_SET_GPIO_DATA, 0x00},
3300         {0x01, AC_VERB_SET_GPIO_MASK, 0x0f},
3301
3302         /* Enable retasking pins as output, initially without power amp */
3303         {0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3304         {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3305         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3306         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3307         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3308         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3309
3310         /* Disable digital (SPDIF) pins initially, but users can enable
3311          * them via a mixer switch.  In the case of SPDIF-out, this initverb
3312          * payload also sets the generation to 0, output to be in "consumer"
3313          * PCM format, copyright asserted, no pre-emphasis and no validity
3314          * control.
3315          */
3316         {0x03, AC_VERB_SET_DIGI_CONVERT_1, 0},
3317         {0x06, AC_VERB_SET_DIGI_CONVERT_1, 0},
3318
3319         /* Ensure mic1, mic2, line1 and line2 pin widgets take input from the 
3320          * OUT1 sum bus when acting as an output.
3321          */
3322         {0x0b, AC_VERB_SET_CONNECT_SEL, 0},
3323         {0x0c, AC_VERB_SET_CONNECT_SEL, 0},
3324         {0x0d, AC_VERB_SET_CONNECT_SEL, 0},
3325         {0x0e, AC_VERB_SET_CONNECT_SEL, 0},
3326
3327         /* Start with output sum widgets muted and their output gains at min */
3328         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3329         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3330         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3331         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3332         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3333         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3334         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3335         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3336         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3337
3338         /* Unmute retasking pin widget output buffers since the default
3339          * state appears to be output.  As the pin mode is changed by the
3340          * user the pin mode control will take care of enabling the pin's
3341          * input/output buffers as needed.
3342          */
3343         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3344         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3345         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3346         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3347         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3348         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3349         /* Also unmute the mono-out pin widget */
3350         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3351
3352         /* Mute capture amp left and right */
3353         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3354         /* Set ADC connection select to match default mixer setting (mic1
3355          * pin)
3356          */
3357         {0x04, AC_VERB_SET_CONNECT_SEL, 0x00},
3358
3359         /* Do the same for the second ADC: mute capture input amp and
3360          * set ADC connection to mic1 pin
3361          */
3362         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3363         {0x05, AC_VERB_SET_CONNECT_SEL, 0x00},
3364
3365         /* Mute all inputs to mixer widget (even unconnected ones) */
3366         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, /* mic1 pin */
3367         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)}, /* mic2 pin */
3368         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)}, /* line1 pin */
3369         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)}, /* line2 pin */
3370         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)}, /* CD pin */
3371         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)}, /* Beep-gen pin */
3372         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)}, /* Line-out pin */
3373         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)}, /* HP-pin pin */
3374
3375         { }
3376 };
3377 #endif
3378
3379 static struct hda_pcm_stream alc260_pcm_analog_playback = {
3380         .substreams = 1,
3381         .channels_min = 2,
3382         .channels_max = 2,
3383 };
3384
3385 static struct hda_pcm_stream alc260_pcm_analog_capture = {
3386         .substreams = 1,
3387         .channels_min = 2,
3388         .channels_max = 2,
3389 };
3390
3391 #define alc260_pcm_digital_playback     alc880_pcm_digital_playback
3392 #define alc260_pcm_digital_capture      alc880_pcm_digital_capture
3393
3394 /*
3395  * for BIOS auto-configuration
3396  */
3397
3398 static int alc260_add_playback_controls(struct alc_spec *spec, hda_nid_t nid,
3399                                         const char *pfx)
3400 {
3401         hda_nid_t nid_vol;
3402         unsigned long vol_val, sw_val;
3403         char name[32];
3404         int err;
3405
3406         if (nid >= 0x0f && nid < 0x11) {
3407                 nid_vol = nid - 0x7;
3408                 vol_val = HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0, HDA_OUTPUT);
3409                 sw_val = HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT);
3410         } else if (nid == 0x11) {
3411                 nid_vol = nid - 0x7;
3412                 vol_val = HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0, HDA_OUTPUT);
3413                 sw_val = HDA_COMPOSE_AMP_VAL(nid, 2, 0, HDA_OUTPUT);
3414         } else if (nid >= 0x12 && nid <= 0x15) {
3415                 nid_vol = 0x08;
3416                 vol_val = HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0, HDA_OUTPUT);
3417                 sw_val = HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT);
3418         } else
3419                 return 0; /* N/A */
3420         
3421         snprintf(name, sizeof(name), "%s Playback Volume", pfx);
3422         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, name, vol_val)) < 0)
3423                 return err;
3424         snprintf(name, sizeof(name), "%s Playback Switch", pfx);
3425         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, name, sw_val)) < 0)
3426                 return err;
3427         return 1;
3428 }
3429
3430 /* add playback controls from the parsed DAC table */
3431 static int alc260_auto_create_multi_out_ctls(struct alc_spec *spec,
3432                                              const struct auto_pin_cfg *cfg)
3433 {
3434         hda_nid_t nid;
3435         int err;
3436
3437         spec->multiout.num_dacs = 1;
3438         spec->multiout.dac_nids = spec->private_dac_nids;
3439         spec->multiout.dac_nids[0] = 0x02;
3440
3441         nid = cfg->line_out_pins[0];
3442         if (nid) {
3443                 err = alc260_add_playback_controls(spec, nid, "Front");
3444                 if (err < 0)
3445                         return err;
3446         }
3447
3448         nid = cfg->speaker_pin;
3449         if (nid) {
3450                 err = alc260_add_playback_controls(spec, nid, "Speaker");
3451                 if (err < 0)
3452                         return err;
3453         }
3454
3455         nid = cfg->hp_pin;
3456         if (nid) {
3457                 err = alc260_add_playback_controls(spec, nid, "Headphone");
3458                 if (err < 0)
3459                         return err;
3460         }
3461         return 0;       
3462 }
3463
3464 /* create playback/capture controls for input pins */
3465 static int alc260_auto_create_analog_input_ctls(struct alc_spec *spec,
3466                                                 const struct auto_pin_cfg *cfg)
3467 {
3468         struct hda_input_mux *imux = &spec->private_imux;
3469         int i, err, idx;
3470
3471         for (i = 0; i < AUTO_PIN_LAST; i++) {
3472                 if (cfg->input_pins[i] >= 0x12) {
3473                         idx = cfg->input_pins[i] - 0x12;
3474                         err = new_analog_input(spec, cfg->input_pins[i],
3475                                                auto_pin_cfg_labels[i], idx, 0x07);
3476                         if (err < 0)
3477                                 return err;
3478                         imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
3479                         imux->items[imux->num_items].index = idx;
3480                         imux->num_items++;
3481                 }
3482                 if ((cfg->input_pins[i] >= 0x0f) && (cfg->input_pins[i] <= 0x10)){
3483                         idx = cfg->input_pins[i] - 0x09;
3484                         err = new_analog_input(spec, cfg->input_pins[i],
3485                                                auto_pin_cfg_labels[i], idx, 0x07);
3486                         if (err < 0)
3487                                 return err;
3488                         imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
3489                         imux->items[imux->num_items].index = idx;
3490                         imux->num_items++;
3491                 }
3492         }
3493         return 0;
3494 }
3495
3496 static void alc260_auto_set_output_and_unmute(struct hda_codec *codec,
3497                                               hda_nid_t nid, int pin_type,
3498                                               int sel_idx)
3499 {
3500         /* set as output */
3501         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
3502         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE);
3503         /* need the manual connection? */
3504         if (nid >= 0x12) {
3505                 int idx = nid - 0x12;
3506                 snd_hda_codec_write(codec, idx + 0x0b, 0,
3507                                     AC_VERB_SET_CONNECT_SEL, sel_idx);
3508                                     
3509         }
3510 }
3511
3512 static void alc260_auto_init_multi_out(struct hda_codec *codec)
3513 {
3514         struct alc_spec *spec = codec->spec;
3515         hda_nid_t nid;
3516
3517         nid = spec->autocfg.line_out_pins[0];   
3518         if (nid)
3519                 alc260_auto_set_output_and_unmute(codec, nid, PIN_OUT, 0);
3520         
3521         nid = spec->autocfg.speaker_pin;
3522         if (nid)
3523                 alc260_auto_set_output_and_unmute(codec, nid, PIN_OUT, 0);
3524
3525         nid = spec->autocfg.hp_pin;
3526         if (nid)
3527                 alc260_auto_set_output_and_unmute(codec, nid, PIN_OUT, 0);
3528 }       
3529
3530 #define ALC260_PIN_CD_NID               0x16
3531 static void alc260_auto_init_analog_input(struct hda_codec *codec)
3532 {
3533         struct alc_spec *spec = codec->spec;
3534         int i;
3535
3536         for (i = 0; i < AUTO_PIN_LAST; i++) {
3537                 hda_nid_t nid = spec->autocfg.input_pins[i];
3538                 if (nid >= 0x12) {
3539                         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
3540                                             i <= AUTO_PIN_FRONT_MIC ? PIN_VREF80 : PIN_IN);
3541                         if (nid != ALC260_PIN_CD_NID)
3542                                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
3543                                                     AMP_OUT_MUTE);
3544                 }
3545         }
3546 }
3547
3548 /*
3549  * generic initialization of ADC, input mixers and output mixers
3550  */
3551 static struct hda_verb alc260_volume_init_verbs[] = {
3552         /*
3553          * Unmute ADC0-1 and set the default input to mic-in
3554          */
3555         {0x04, AC_VERB_SET_CONNECT_SEL, 0x00},
3556         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3557         {0x05, AC_VERB_SET_CONNECT_SEL, 0x00},
3558         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3559         
3560         /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
3561          * mixer widget
3562          * Note: PASD motherboards uses the Line In 2 as the input for front panel
3563          * mic (mic 2)
3564          */
3565         /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
3566         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3567         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3568         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
3569         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
3570         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
3571
3572         /*
3573          * Set up output mixers (0x08 - 0x0a)
3574          */
3575         /* set vol=0 to output mixers */
3576         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3577         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3578         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3579         /* set up input amps for analog loopback */
3580         /* Amp Indices: DAC = 0, mixer = 1 */
3581         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3582         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3583         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3584         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3585         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3586         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3587         
3588         { }
3589 };
3590
3591 static int alc260_parse_auto_config(struct hda_codec *codec)
3592 {
3593         struct alc_spec *spec = codec->spec;
3594         unsigned int wcap;
3595         int err;
3596         static hda_nid_t alc260_ignore[] = { 0x17, 0 };
3597
3598         if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg,
3599                                                 alc260_ignore)) < 0)
3600                 return err;
3601         if ((err = alc260_auto_create_multi_out_ctls(spec, &spec->autocfg)) < 0)
3602                 return err;
3603         if (! spec->kctl_alloc)
3604                 return 0; /* can't find valid BIOS pin config */
3605         if ((err = alc260_auto_create_analog_input_ctls(spec, &spec->autocfg)) < 0)
3606                 return err;
3607
3608         spec->multiout.max_channels = 2;
3609
3610         if (spec->autocfg.dig_out_pin)
3611                 spec->multiout.dig_out_nid = ALC260_DIGOUT_NID;
3612         if (spec->kctl_alloc)
3613                 spec->mixers[spec->num_mixers++] = spec->kctl_alloc;
3614
3615         spec->init_verbs[spec->num_init_verbs++] = alc260_volume_init_verbs;
3616
3617         spec->input_mux = &spec->private_imux;
3618
3619         /* check whether NID 0x04 is valid */
3620         wcap = get_wcaps(codec, 0x04);
3621         wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT; /* get type */
3622         if (wcap != AC_WID_AUD_IN) {
3623                 spec->adc_nids = alc260_adc_nids_alt;
3624                 spec->num_adc_nids = ARRAY_SIZE(alc260_adc_nids_alt);
3625                 spec->mixers[spec->num_mixers] = alc260_capture_alt_mixer;
3626         } else {
3627                 spec->adc_nids = alc260_adc_nids;
3628                 spec->num_adc_nids = ARRAY_SIZE(alc260_adc_nids);
3629                 spec->mixers[spec->num_mixers] = alc260_capture_mixer;
3630         }
3631         spec->num_mixers++;
3632
3633         return 1;
3634 }
3635
3636 /* additional initialization for auto-configuration model */
3637 static void alc260_auto_init(struct hda_codec *codec)
3638 {
3639         alc260_auto_init_multi_out(codec);
3640         alc260_auto_init_analog_input(codec);
3641 }
3642
3643 /*
3644  * ALC260 configurations
3645  */
3646 static struct hda_board_config alc260_cfg_tbl[] = {
3647         { .modelname = "basic", .config = ALC260_BASIC },
3648         { .pci_subvendor = 0x104d, .pci_subdevice = 0x81bb,
3649           .config = ALC260_BASIC }, /* Sony VAIO */
3650         { .pci_subvendor = 0x152d, .pci_subdevice = 0x0729,
3651           .config = ALC260_BASIC }, /* CTL Travel Master U553W */
3652         { .modelname = "hp", .config = ALC260_HP },
3653         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3010, .config = ALC260_HP },
3654         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3011, .config = ALC260_HP },
3655         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3012, .config = ALC260_HP },
3656         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3013, .config = ALC260_HP_3013 },
3657         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3014, .config = ALC260_HP },
3658         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3015, .config = ALC260_HP },
3659         { .pci_subvendor = 0x103c, .pci_subdevice = 0x3016, .config = ALC260_HP },
3660         { .modelname = "fujitsu", .config = ALC260_FUJITSU_S702X },
3661         { .pci_subvendor = 0x10cf, .pci_subdevice = 0x1326, .config = ALC260_FUJITSU_S702X },
3662         { .modelname = "acer", .config = ALC260_ACER },
3663         { .pci_subvendor = 0x1025, .pci_subdevice = 0x008f, .config = ALC260_ACER },
3664 #ifdef CONFIG_SND_DEBUG
3665         { .modelname = "test", .config = ALC260_TEST },
3666 #endif
3667         { .modelname = "auto", .config = ALC260_AUTO },
3668         {}
3669 };
3670
3671 static struct alc_config_preset alc260_presets[] = {
3672         [ALC260_BASIC] = {
3673                 .mixers = { alc260_base_output_mixer,
3674                             alc260_input_mixer,
3675                             alc260_pc_beep_mixer,
3676                             alc260_capture_mixer },
3677                 .init_verbs = { alc260_init_verbs },
3678                 .num_dacs = ARRAY_SIZE(alc260_dac_nids),
3679                 .dac_nids = alc260_dac_nids,
3680                 .num_adc_nids = ARRAY_SIZE(alc260_adc_nids),
3681                 .adc_nids = alc260_adc_nids,
3682                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3683                 .channel_mode = alc260_modes,
3684                 .input_mux = &alc260_capture_source,
3685         },
3686         [ALC260_HP] = {
3687                 .mixers = { alc260_base_output_mixer,
3688                             alc260_input_mixer,
3689                             alc260_capture_alt_mixer },
3690                 .init_verbs = { alc260_hp_init_verbs },
3691                 .num_dacs = ARRAY_SIZE(alc260_dac_nids),
3692                 .dac_nids = alc260_dac_nids,
3693                 .num_adc_nids = ARRAY_SIZE(alc260_hp_adc_nids),
3694                 .adc_nids = alc260_hp_adc_nids,
3695                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3696                 .channel_mode = alc260_modes,
3697                 .input_mux = &alc260_capture_source,
3698         },
3699         [ALC260_HP_3013] = {
3700                 .mixers = { alc260_hp_3013_mixer,
3701                             alc260_input_mixer,
3702                             alc260_capture_alt_mixer },
3703                 .init_verbs = { alc260_hp_3013_init_verbs },
3704                 .num_dacs = ARRAY_SIZE(alc260_dac_nids),
3705                 .dac_nids = alc260_dac_nids,
3706                 .num_adc_nids = ARRAY_SIZE(alc260_hp_adc_nids),
3707                 .adc_nids = alc260_hp_adc_nids,
3708                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3709                 .channel_mode = alc260_modes,
3710                 .input_mux = &alc260_capture_source,
3711         },
3712         [ALC260_FUJITSU_S702X] = {
3713                 .mixers = { alc260_fujitsu_mixer,
3714                             alc260_capture_mixer },
3715                 .init_verbs = { alc260_fujitsu_init_verbs },
3716                 .num_dacs = ARRAY_SIZE(alc260_dac_nids),
3717                 .dac_nids = alc260_dac_nids,
3718                 .num_adc_nids = ARRAY_SIZE(alc260_dual_adc_nids),
3719                 .adc_nids = alc260_dual_adc_nids,
3720                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3721                 .channel_mode = alc260_modes,
3722                 .input_mux = &alc260_fujitsu_capture_source,
3723         },
3724         [ALC260_ACER] = {
3725                 .mixers = { alc260_acer_mixer,
3726                             alc260_capture_mixer },
3727                 .init_verbs = { alc260_acer_init_verbs },
3728                 .num_dacs = ARRAY_SIZE(alc260_dac_nids),
3729                 .dac_nids = alc260_dac_nids,
3730                 .num_adc_nids = ARRAY_SIZE(alc260_dual_adc_nids),
3731                 .adc_nids = alc260_dual_adc_nids,
3732                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3733                 .channel_mode = alc260_modes,
3734                 .input_mux = &alc260_acer_capture_source,
3735         },
3736 #ifdef CONFIG_SND_DEBUG
3737         [ALC260_TEST] = {
3738                 .mixers = { alc260_test_mixer,
3739                             alc260_capture_mixer },
3740                 .init_verbs = { alc260_test_init_verbs },
3741                 .num_dacs = ARRAY_SIZE(alc260_test_dac_nids),
3742                 .dac_nids = alc260_test_dac_nids,
3743                 .num_adc_nids = ARRAY_SIZE(alc260_test_adc_nids),
3744                 .adc_nids = alc260_test_adc_nids,
3745                 .num_channel_mode = ARRAY_SIZE(alc260_modes),
3746                 .channel_mode = alc260_modes,
3747                 .input_mux = &alc260_test_capture_source,
3748         },
3749 #endif
3750 };
3751
3752 static int patch_alc260(struct hda_codec *codec)
3753 {
3754         struct alc_spec *spec;
3755         int err, board_config;
3756
3757         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
3758         if (spec == NULL)
3759                 return -ENOMEM;
3760
3761         codec->spec = spec;
3762
3763         board_config = snd_hda_check_board_config(codec, alc260_cfg_tbl);
3764         if (board_config < 0 || board_config >= ALC260_MODEL_LAST) {
3765                 snd_printd(KERN_INFO "hda_codec: Unknown model for ALC260\n");
3766                 board_config = ALC260_AUTO;
3767         }
3768
3769         if (board_config == ALC260_AUTO) {
3770                 /* automatic parse from the BIOS config */
3771                 err = alc260_parse_auto_config(codec);
3772                 if (err < 0) {
3773                         alc_free(codec);
3774                         return err;
3775                 } else if (! err) {
3776                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using base mode...\n");
3777                         board_config = ALC260_BASIC;
3778                 }
3779         }
3780
3781         if (board_config != ALC260_AUTO)
3782                 setup_preset(spec, &alc260_presets[board_config]);
3783
3784         spec->stream_name_analog = "ALC260 Analog";
3785         spec->stream_analog_playback = &alc260_pcm_analog_playback;
3786         spec->stream_analog_capture = &alc260_pcm_analog_capture;
3787
3788         spec->stream_name_digital = "ALC260 Digital";
3789         spec->stream_digital_playback = &alc260_pcm_digital_playback;
3790         spec->stream_digital_capture = &alc260_pcm_digital_capture;
3791
3792         codec->patch_ops = alc_patch_ops;
3793         if (board_config == ALC260_AUTO)
3794                 spec->init_hook = alc260_auto_init;
3795
3796         return 0;
3797 }
3798
3799
3800 /*
3801  * ALC882 support
3802  *
3803  * ALC882 is almost identical with ALC880 but has cleaner and more flexible
3804  * configuration.  Each pin widget can choose any input DACs and a mixer.
3805  * Each ADC is connected from a mixer of all inputs.  This makes possible
3806  * 6-channel independent captures.
3807  *
3808  * In addition, an independent DAC for the multi-playback (not used in this
3809  * driver yet).
3810  */
3811 #define ALC882_DIGOUT_NID       0x06
3812 #define ALC882_DIGIN_NID        0x0a
3813
3814 static struct hda_channel_mode alc882_ch_modes[1] = {
3815         { 8, NULL }
3816 };
3817
3818 static hda_nid_t alc882_dac_nids[4] = {
3819         /* front, rear, clfe, rear_surr */
3820         0x02, 0x03, 0x04, 0x05
3821 };
3822
3823 /* identical with ALC880 */
3824 #define alc882_adc_nids         alc880_adc_nids
3825 #define alc882_adc_nids_alt     alc880_adc_nids_alt
3826
3827 /* input MUX */
3828 /* FIXME: should be a matrix-type input source selection */
3829
3830 static struct hda_input_mux alc882_capture_source = {
3831         .num_items = 4,
3832         .items = {
3833                 { "Mic", 0x0 },
3834                 { "Front Mic", 0x1 },
3835                 { "Line", 0x2 },
3836                 { "CD", 0x4 },
3837         },
3838 };
3839
3840 #define alc882_mux_enum_info alc_mux_enum_info
3841 #define alc882_mux_enum_get alc_mux_enum_get
3842
3843 static int alc882_mux_enum_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
3844 {
3845         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
3846         struct alc_spec *spec = codec->spec;
3847         const struct hda_input_mux *imux = spec->input_mux;
3848         unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
3849         static hda_nid_t capture_mixers[3] = { 0x24, 0x23, 0x22 };
3850         hda_nid_t nid = capture_mixers[adc_idx];
3851         unsigned int *cur_val = &spec->cur_mux[adc_idx];
3852         unsigned int i, idx;
3853
3854         idx = ucontrol->value.enumerated.item[0];
3855         if (idx >= imux->num_items)
3856                 idx = imux->num_items - 1;
3857         if (*cur_val == idx && ! codec->in_resume)
3858                 return 0;
3859         for (i = 0; i < imux->num_items; i++) {
3860                 unsigned int v = (i == idx) ? 0x7000 : 0x7080;
3861                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
3862                                     v | (imux->items[i].index << 8));
3863         }
3864         *cur_val = idx;
3865         return 1;
3866 }
3867
3868 /*
3869  * 6ch mode
3870  */
3871 static struct hda_verb alc882_sixstack_ch6_init[] = {
3872         { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
3873         { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3874         { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3875         { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3876         { } /* end */
3877 };
3878
3879 /*
3880  * 8ch mode
3881  */
3882 static struct hda_verb alc882_sixstack_ch8_init[] = {
3883         { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3884         { 0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3885         { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3886         { 0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
3887         { } /* end */
3888 };
3889
3890 static struct hda_channel_mode alc882_sixstack_modes[2] = {
3891         { 6, alc882_sixstack_ch6_init },
3892         { 8, alc882_sixstack_ch8_init },
3893 };
3894
3895 /* Pin assignment: Front=0x14, Rear=0x15, CLFE=0x16, Side=0x17
3896  *                 Mic=0x18, Front Mic=0x19, Line-In=0x1a, HP=0x1b
3897  */
3898 static struct snd_kcontrol_new alc882_base_mixer[] = {
3899         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
3900         HDA_BIND_MUTE("Front Playback Switch", 0x0c, 2, HDA_INPUT),
3901         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0d, 0x0, HDA_OUTPUT),
3902         HDA_BIND_MUTE("Surround Playback Switch", 0x0d, 2, HDA_INPUT),
3903         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0e, 1, 0x0, HDA_OUTPUT),
3904         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
3905         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x0e, 1, 2, HDA_INPUT),
3906         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x0e, 2, 2, HDA_INPUT),
3907         HDA_CODEC_VOLUME("Side Playback Volume", 0x0f, 0x0, HDA_OUTPUT),
3908         HDA_BIND_MUTE("Side Playback Switch", 0x0f, 2, HDA_INPUT),
3909         HDA_CODEC_MUTE("Headphone Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
3910         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
3911         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
3912         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
3913         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
3914         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
3915         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
3916         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x1, HDA_INPUT),
3917         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x1, HDA_INPUT),
3918         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x0b, 0x05, HDA_INPUT),
3919         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x0b, 0x05, HDA_INPUT),
3920         HDA_CODEC_VOLUME("Capture Volume", 0x07, 0x0, HDA_INPUT),
3921         HDA_CODEC_MUTE("Capture Switch", 0x07, 0x0, HDA_INPUT),
3922         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x08, 0x0, HDA_INPUT),
3923         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x08, 0x0, HDA_INPUT),
3924         HDA_CODEC_VOLUME_IDX("Capture Volume", 2, 0x09, 0x0, HDA_INPUT),
3925         HDA_CODEC_MUTE_IDX("Capture Switch", 2, 0x09, 0x0, HDA_INPUT),
3926         {
3927                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3928                 /* .name = "Capture Source", */
3929                 .name = "Input Source",
3930                 .count = 3,
3931                 .info = alc882_mux_enum_info,
3932                 .get = alc882_mux_enum_get,
3933                 .put = alc882_mux_enum_put,
3934         },
3935         { } /* end */
3936 };
3937
3938 static struct snd_kcontrol_new alc882_chmode_mixer[] = {
3939         {
3940                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3941                 .name = "Channel Mode",
3942                 .info = alc_ch_mode_info,
3943                 .get = alc_ch_mode_get,
3944                 .put = alc_ch_mode_put,
3945         },
3946         { } /* end */
3947 };
3948
3949 static struct hda_verb alc882_init_verbs[] = {
3950         /* Front mixer: unmute input/output amp left and right (volume = 0) */
3951         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3952         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3953         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3954         /* Rear mixer */
3955         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3956         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3957         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3958         /* CLFE mixer */
3959         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3960         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3961         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3962         /* Side mixer */
3963         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3964         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3965         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3966
3967         /* Front Pin: output 0 (0x0c) */
3968         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3969         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3970         {0x14, AC_VERB_SET_CONNECT_SEL, 0x00},
3971         /* Rear Pin: output 1 (0x0d) */
3972         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3973         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3974         {0x15, AC_VERB_SET_CONNECT_SEL, 0x01},
3975         /* CLFE Pin: output 2 (0x0e) */
3976         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3977         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3978         {0x16, AC_VERB_SET_CONNECT_SEL, 0x02},
3979         /* Side Pin: output 3 (0x0f) */
3980         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
3981         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3982         {0x17, AC_VERB_SET_CONNECT_SEL, 0x03},
3983         /* Mic (rear) pin: input vref at 80% */
3984         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3985         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3986         /* Front Mic pin: input vref at 80% */
3987         {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3988         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3989         /* Line In pin: input */
3990         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3991         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3992         /* Line-2 In: Headphone output (output 0 - 0x0c) */
3993         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3994         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3995         {0x1b, AC_VERB_SET_CONNECT_SEL, 0x00},
3996         /* CD pin widget for input */
3997         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3998
3999         /* FIXME: use matrix-type input source selection */
4000         /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
4001         /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
4002         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4003         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
4004         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
4005         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
4006         /* Input mixer2 */
4007         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4008         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
4009         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
4010         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
4011         /* Input mixer3 */
4012         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4013         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
4014         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
4015         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
4016         /* ADC1: mute amp left and right */
4017         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4018         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
4019         /* ADC2: mute amp left and right */
4020         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4021         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
4022         /* ADC3: mute amp left and right */
4023         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4024         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
4025
4026         { }
4027 };
4028
4029 /*
4030  * generic initialization of ADC, input mixers and output mixers
4031  */
4032 static struct hda_verb alc882_auto_init_verbs[] = {
4033         /*
4034          * Unmute ADC0-2 and set the default input to mic-in
4035          */
4036         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
4037         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4038         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
4039         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4040         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
4041         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4042
4043         /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
4044          * mixer widget
4045          * Note: PASD motherboards uses the Line In 2 as the input for front panel
4046          * mic (mic 2)
4047          */
4048         /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
4049         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4050         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4051         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
4052         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
4053         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
4054
4055         /*
4056          * Set up output mixers (0x0c - 0x0f)
4057          */
4058         /* set vol=0 to output mixers */
4059         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4060         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4061         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4062         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4063         /* set up input amps for analog loopback */
4064         /* Amp Indices: DAC = 0, mixer = 1 */
4065         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4066         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4067         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4068         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4069         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4070         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4071         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4072         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4073         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4074         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4075
4076         /* FIXME: use matrix-type input source selection */
4077         /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
4078         /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
4079         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4080         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4081         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4082         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4083         /* Input mixer2 */
4084         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4085         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4086         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4087         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4088         /* Input mixer3 */
4089         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4090         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4091         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4092         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4093
4094         { }
4095 };
4096
4097 /* capture mixer elements */
4098 static struct snd_kcontrol_new alc882_capture_alt_mixer[] = {
4099         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
4100         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
4101         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x09, 0x0, HDA_INPUT),
4102         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x09, 0x0, HDA_INPUT),
4103         {
4104                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4105                 /* The multiple "Capture Source" controls confuse alsamixer
4106                  * So call somewhat different..
4107                  * FIXME: the controls appear in the "playback" view!
4108                  */
4109                 /* .name = "Capture Source", */
4110                 .name = "Input Source",
4111                 .count = 2,
4112                 .info = alc882_mux_enum_info,
4113                 .get = alc882_mux_enum_get,
4114                 .put = alc882_mux_enum_put,
4115         },
4116         { } /* end */
4117 };
4118
4119 static struct snd_kcontrol_new alc882_capture_mixer[] = {
4120         HDA_CODEC_VOLUME("Capture Volume", 0x07, 0x0, HDA_INPUT),
4121         HDA_CODEC_MUTE("Capture Switch", 0x07, 0x0, HDA_INPUT),
4122         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x08, 0x0, HDA_INPUT),
4123         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x08, 0x0, HDA_INPUT),
4124         HDA_CODEC_VOLUME_IDX("Capture Volume", 2, 0x09, 0x0, HDA_INPUT),
4125         HDA_CODEC_MUTE_IDX("Capture Switch", 2, 0x09, 0x0, HDA_INPUT),
4126         {
4127                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4128                 /* The multiple "Capture Source" controls confuse alsamixer
4129                  * So call somewhat different..
4130                  * FIXME: the controls appear in the "playback" view!
4131                  */
4132                 /* .name = "Capture Source", */
4133                 .name = "Input Source",
4134                 .count = 3,
4135                 .info = alc882_mux_enum_info,
4136                 .get = alc882_mux_enum_get,
4137                 .put = alc882_mux_enum_put,
4138         },
4139         { } /* end */
4140 };
4141
4142 /* pcm configuration: identiacal with ALC880 */
4143 #define alc882_pcm_analog_playback      alc880_pcm_analog_playback
4144 #define alc882_pcm_analog_capture       alc880_pcm_analog_capture
4145 #define alc882_pcm_digital_playback     alc880_pcm_digital_playback
4146 #define alc882_pcm_digital_capture      alc880_pcm_digital_capture
4147
4148 /*
4149  * configuration and preset
4150  */
4151 static struct hda_board_config alc882_cfg_tbl[] = {
4152         { .modelname = "3stack-dig", .config = ALC882_3ST_DIG },
4153         { .modelname = "6stack-dig", .config = ALC882_6ST_DIG },
4154         { .pci_subvendor = 0x1462, .pci_subdevice = 0x6668, .config = ALC882_6ST_DIG }, /* MSI  */
4155         { .pci_subvendor = 0x105b, .pci_subdevice = 0x6668, .config = ALC882_6ST_DIG }, /* Foxconn */
4156         { .pci_subvendor = 0x1019, .pci_subdevice = 0x6668, .config = ALC882_6ST_DIG }, /* ECS */
4157         { .modelname = "auto", .config = ALC882_AUTO },
4158         {}
4159 };
4160
4161 static struct alc_config_preset alc882_presets[] = {
4162         [ALC882_3ST_DIG] = {
4163                 .mixers = { alc882_base_mixer },
4164                 .init_verbs = { alc882_init_verbs },
4165                 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
4166                 .dac_nids = alc882_dac_nids,
4167                 .dig_out_nid = ALC882_DIGOUT_NID,
4168                 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
4169                 .adc_nids = alc882_adc_nids,
4170                 .dig_in_nid = ALC882_DIGIN_NID,
4171                 .num_channel_mode = ARRAY_SIZE(alc882_ch_modes),
4172                 .channel_mode = alc882_ch_modes,
4173                 .input_mux = &alc882_capture_source,
4174         },
4175         [ALC882_6ST_DIG] = {
4176                 .mixers = { alc882_base_mixer, alc882_chmode_mixer },
4177                 .init_verbs = { alc882_init_verbs },
4178                 .num_dacs = ARRAY_SIZE(alc882_dac_nids),
4179                 .dac_nids = alc882_dac_nids,
4180                 .dig_out_nid = ALC882_DIGOUT_NID,
4181                 .num_adc_nids = ARRAY_SIZE(alc882_adc_nids),
4182                 .adc_nids = alc882_adc_nids,
4183                 .dig_in_nid = ALC882_DIGIN_NID,
4184                 .num_channel_mode = ARRAY_SIZE(alc882_sixstack_modes),
4185                 .channel_mode = alc882_sixstack_modes,
4186                 .input_mux = &alc882_capture_source,
4187         },
4188 };
4189
4190
4191 /*
4192  * BIOS auto configuration
4193  */
4194 static void alc882_auto_set_output_and_unmute(struct hda_codec *codec,
4195                                               hda_nid_t nid, int pin_type,
4196                                               int dac_idx)
4197 {
4198         /* set as output */
4199         struct alc_spec *spec = codec->spec;
4200         int idx; 
4201         
4202         if (spec->multiout.dac_nids[dac_idx] == 0x25)
4203                 idx = 4;
4204         else
4205                 idx = spec->multiout.dac_nids[dac_idx] - 2;
4206
4207         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
4208         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE);
4209         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_CONNECT_SEL, idx);
4210
4211 }
4212
4213 static void alc882_auto_init_multi_out(struct hda_codec *codec)
4214 {
4215         struct alc_spec *spec = codec->spec;
4216         int i;
4217
4218         for (i = 0; i <= HDA_SIDE; i++) {
4219                 hda_nid_t nid = spec->autocfg.line_out_pins[i]; 
4220                 if (nid)
4221                         alc882_auto_set_output_and_unmute(codec, nid, PIN_OUT, i);
4222         }
4223 }
4224
4225 static void alc882_auto_init_hp_out(struct hda_codec *codec)
4226 {
4227         struct alc_spec *spec = codec->spec;
4228         hda_nid_t pin;
4229
4230         pin = spec->autocfg.hp_pin;
4231         if (pin) /* connect to front */
4232                 alc882_auto_set_output_and_unmute(codec, pin, PIN_HP, 0); /* use dac 0 */
4233 }
4234
4235 #define alc882_is_input_pin(nid)        alc880_is_input_pin(nid)
4236 #define ALC882_PIN_CD_NID               ALC880_PIN_CD_NID
4237
4238 static void alc882_auto_init_analog_input(struct hda_codec *codec)
4239 {
4240         struct alc_spec *spec = codec->spec;
4241         int i;
4242
4243         for (i = 0; i < AUTO_PIN_LAST; i++) {
4244                 hda_nid_t nid = spec->autocfg.input_pins[i];
4245                 if (alc882_is_input_pin(nid)) {
4246                         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
4247                                             i <= AUTO_PIN_FRONT_MIC ? PIN_VREF80 : PIN_IN);
4248                         if (nid != ALC882_PIN_CD_NID)
4249                                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
4250                                                     AMP_OUT_MUTE);
4251                 }
4252         }
4253 }
4254
4255 /* almost identical with ALC880 parser... */
4256 static int alc882_parse_auto_config(struct hda_codec *codec)
4257 {
4258         struct alc_spec *spec = codec->spec;
4259         int err = alc880_parse_auto_config(codec);
4260
4261         if (err < 0)
4262                 return err;
4263         else if (err > 0)
4264                 /* hack - override the init verbs */
4265                 spec->init_verbs[0] = alc882_auto_init_verbs;
4266         return err;
4267 }
4268
4269 /* additional initialization for auto-configuration model */
4270 static void alc882_auto_init(struct hda_codec *codec)
4271 {
4272         alc882_auto_init_multi_out(codec);
4273         alc882_auto_init_hp_out(codec);
4274         alc882_auto_init_analog_input(codec);
4275 }
4276
4277 /*
4278  *  ALC882 Headphone poll in 3.5.1a or 3.5.2
4279  */
4280
4281 static int patch_alc882(struct hda_codec *codec)
4282 {
4283         struct alc_spec *spec;
4284         int err, board_config;
4285
4286         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4287         if (spec == NULL)
4288                 return -ENOMEM;
4289
4290         codec->spec = spec;
4291
4292         board_config = snd_hda_check_board_config(codec, alc882_cfg_tbl);
4293
4294         if (board_config < 0 || board_config >= ALC882_MODEL_LAST) {
4295                 printk(KERN_INFO "hda_codec: Unknown model for ALC882, trying auto-probe from BIOS...\n");
4296                 board_config = ALC882_AUTO;
4297         }
4298
4299         if (board_config == ALC882_AUTO) {
4300                 /* automatic parse from the BIOS config */
4301                 err = alc882_parse_auto_config(codec);
4302                 if (err < 0) {
4303                         alc_free(codec);
4304                         return err;
4305                 } else if (! err) {
4306                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using base mode...\n");
4307                         board_config = ALC882_3ST_DIG;
4308                 }
4309         }
4310
4311         if (board_config != ALC882_AUTO)
4312                 setup_preset(spec, &alc882_presets[board_config]);
4313
4314         spec->stream_name_analog = "ALC882 Analog";
4315         spec->stream_analog_playback = &alc882_pcm_analog_playback;
4316         spec->stream_analog_capture = &alc882_pcm_analog_capture;
4317
4318         spec->stream_name_digital = "ALC882 Digital";
4319         spec->stream_digital_playback = &alc882_pcm_digital_playback;
4320         spec->stream_digital_capture = &alc882_pcm_digital_capture;
4321
4322         if (! spec->adc_nids && spec->input_mux) {
4323                 /* check whether NID 0x07 is valid */
4324                 unsigned int wcap = get_wcaps(codec, 0x07);
4325                 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT; /* get type */
4326                 if (wcap != AC_WID_AUD_IN) {
4327                         spec->adc_nids = alc882_adc_nids_alt;
4328                         spec->num_adc_nids = ARRAY_SIZE(alc882_adc_nids_alt);
4329                         spec->mixers[spec->num_mixers] = alc882_capture_alt_mixer;
4330                         spec->num_mixers++;
4331                 } else {
4332                         spec->adc_nids = alc882_adc_nids;
4333                         spec->num_adc_nids = ARRAY_SIZE(alc882_adc_nids);
4334                         spec->mixers[spec->num_mixers] = alc882_capture_mixer;
4335                         spec->num_mixers++;
4336                 }
4337         }
4338
4339         codec->patch_ops = alc_patch_ops;
4340         if (board_config == ALC882_AUTO)
4341                 spec->init_hook = alc882_auto_init;
4342
4343         return 0;
4344 }
4345
4346 /*
4347  * ALC262 support
4348  */
4349
4350 #define ALC262_DIGOUT_NID       ALC880_DIGOUT_NID
4351 #define ALC262_DIGIN_NID        ALC880_DIGIN_NID
4352
4353 #define alc262_dac_nids         alc260_dac_nids
4354 #define alc262_adc_nids         alc882_adc_nids
4355 #define alc262_adc_nids_alt     alc882_adc_nids_alt
4356
4357 #define alc262_modes            alc260_modes
4358 #define alc262_capture_source   alc882_capture_source
4359
4360 static struct snd_kcontrol_new alc262_base_mixer[] = {
4361         HDA_CODEC_VOLUME("Front Playback Volume", 0x0c, 0x0, HDA_OUTPUT),
4362         HDA_CODEC_MUTE("Front Playback Switch", 0x14, 0x0, HDA_OUTPUT),
4363         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
4364         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
4365         HDA_CODEC_VOLUME("Line Playback Volume", 0x0b, 0x02, HDA_INPUT),
4366         HDA_CODEC_MUTE("Line Playback Switch", 0x0b, 0x02, HDA_INPUT),
4367         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
4368         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
4369         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x0b, 0x01, HDA_INPUT),
4370         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x0b, 0x01, HDA_INPUT),
4371         /* HDA_CODEC_VOLUME("PC Beep Playback Volume", 0x0b, 0x05, HDA_INPUT),
4372            HDA_CODEC_MUTE("PC Beelp Playback Switch", 0x0b, 0x05, HDA_INPUT), */
4373         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x0D, 0x0, HDA_OUTPUT),
4374         HDA_CODEC_MUTE("Headphone Playback Switch", 0x15, 0x0, HDA_OUTPUT),
4375         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x0e, 2, 0x0, HDA_OUTPUT),
4376         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x16, 2, 0x0, HDA_OUTPUT),
4377         { } /* end */
4378 };
4379
4380 #define alc262_capture_mixer            alc882_capture_mixer
4381 #define alc262_capture_alt_mixer        alc882_capture_alt_mixer
4382
4383 /*
4384  * generic initialization of ADC, input mixers and output mixers
4385  */
4386 static struct hda_verb alc262_init_verbs[] = {
4387         /*
4388          * Unmute ADC0-2 and set the default input to mic-in
4389          */
4390         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
4391         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4392         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
4393         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4394         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
4395         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4396
4397         /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
4398          * mixer widget
4399          * Note: PASD motherboards uses the Line In 2 as the input for front panel
4400          * mic (mic 2)
4401          */
4402         /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
4403         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4404         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4405         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
4406         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
4407         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
4408
4409         /*
4410          * Set up output mixers (0x0c - 0x0e)
4411          */
4412         /* set vol=0 to output mixers */
4413         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4414         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4415         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4416         /* set up input amps for analog loopback */
4417         /* Amp Indices: DAC = 0, mixer = 1 */
4418         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4419         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4420         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4421         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4422         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4423         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4424
4425         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
4426         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0},
4427         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
4428         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24},
4429         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
4430         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
4431
4432         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
4433         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
4434         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
4435         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
4436         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, 0x0000},
4437         
4438         {0x14, AC_VERB_SET_CONNECT_SEL, 0x00},
4439         {0x15, AC_VERB_SET_CONNECT_SEL, 0x01},
4440         
4441         /* FIXME: use matrix-type input source selection */
4442         /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
4443         /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
4444         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4445         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4446         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4447         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4448         /* Input mixer2 */
4449         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4450         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4451         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4452         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4453         /* Input mixer3 */
4454         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4455         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4456         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4457         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},      
4458
4459         { }
4460 };
4461
4462 /*
4463  * fujitsu model
4464  *  0x14 = headphone/spdif-out, 0x15 = internal speaker
4465  */
4466
4467 #define ALC_HP_EVENT    0x37
4468
4469 static struct hda_verb alc262_fujitsu_unsol_verbs[] = {
4470         {0x14, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | ALC_HP_EVENT},
4471         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
4472         {}
4473 };
4474
4475 static struct hda_input_mux alc262_fujitsu_capture_source = {
4476         .num_items = 2,
4477         .items = {
4478                 { "Mic", 0x0 },
4479                 { "CD", 0x4 },
4480         },
4481 };
4482
4483 /* mute/unmute internal speaker according to the hp jack and mute state */
4484 static void alc262_fujitsu_automute(struct hda_codec *codec, int force)
4485 {
4486         struct alc_spec *spec = codec->spec;
4487         unsigned int mute;
4488
4489         if (force || ! spec->sense_updated) {
4490                 unsigned int present;
4491                 /* need to execute and sync at first */
4492                 snd_hda_codec_read(codec, 0x14, 0, AC_VERB_SET_PIN_SENSE, 0);
4493                 present = snd_hda_codec_read(codec, 0x14, 0,
4494                                          AC_VERB_GET_PIN_SENSE, 0);
4495                 spec->jack_present = (present & 0x80000000) != 0;
4496                 spec->sense_updated = 1;
4497         }
4498         if (spec->jack_present) {
4499                 /* mute internal speaker */
4500                 snd_hda_codec_amp_update(codec, 0x15, 0, HDA_OUTPUT, 0,
4501                                          0x80, 0x80);
4502                 snd_hda_codec_amp_update(codec, 0x15, 1, HDA_OUTPUT, 0,
4503                                          0x80, 0x80);
4504         } else {
4505                 /* unmute internal speaker if necessary */
4506                 mute = snd_hda_codec_amp_read(codec, 0x14, 0, HDA_OUTPUT, 0);
4507                 snd_hda_codec_amp_update(codec, 0x15, 0, HDA_OUTPUT, 0,
4508                                          0x80, mute & 0x80);
4509                 mute = snd_hda_codec_amp_read(codec, 0x14, 1, HDA_OUTPUT, 0);
4510                 snd_hda_codec_amp_update(codec, 0x15, 1, HDA_OUTPUT, 0,
4511                                          0x80, mute & 0x80);
4512         }
4513 }
4514
4515 /* unsolicited event for HP jack sensing */
4516 static void alc262_fujitsu_unsol_event(struct hda_codec *codec,
4517                                        unsigned int res)
4518 {
4519         if ((res >> 26) != ALC_HP_EVENT)
4520                 return;
4521         alc262_fujitsu_automute(codec, 1);
4522 }
4523
4524 /* bind volumes of both NID 0x0c and 0x0d */
4525 static int alc262_fujitsu_master_vol_put(struct snd_kcontrol *kcontrol,
4526                                          struct snd_ctl_elem_value *ucontrol)
4527 {
4528         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
4529         long *valp = ucontrol->value.integer.value;
4530         int change;
4531
4532         change = snd_hda_codec_amp_update(codec, 0x0c, 0, HDA_OUTPUT, 0,
4533                                           0x7f, valp[0] & 0x7f);
4534         change |= snd_hda_codec_amp_update(codec, 0x0c, 1, HDA_OUTPUT, 0,
4535                                            0x7f, valp[1] & 0x7f);
4536         snd_hda_codec_amp_update(codec, 0x0d, 0, HDA_OUTPUT, 0,
4537                                  0x7f, valp[0] & 0x7f);
4538         snd_hda_codec_amp_update(codec, 0x0d, 1, HDA_OUTPUT, 0,
4539                                  0x7f, valp[1] & 0x7f);
4540         return change;
4541 }
4542
4543 /* bind hp and internal speaker mute (with plug check) */
4544 static int alc262_fujitsu_master_sw_put(struct snd_kcontrol *kcontrol,
4545                                          struct snd_ctl_elem_value *ucontrol)
4546 {
4547         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
4548         long *valp = ucontrol->value.integer.value;
4549         int change;
4550
4551         change = snd_hda_codec_amp_update(codec, 0x14, 0, HDA_OUTPUT, 0,
4552                                           0x80, valp[0] ? 0 : 0x80);
4553         change |= snd_hda_codec_amp_update(codec, 0x14, 1, HDA_OUTPUT, 0,
4554                                            0x80, valp[1] ? 0 : 0x80);
4555         if (change || codec->in_resume)
4556                 alc262_fujitsu_automute(codec, codec->in_resume);
4557         return change;
4558 }
4559
4560 static struct snd_kcontrol_new alc262_fujitsu_mixer[] = {
4561         {
4562                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4563                 .name = "Master Playback Volume",
4564                 .info = snd_hda_mixer_amp_volume_info,
4565                 .get = snd_hda_mixer_amp_volume_get,
4566                 .put = alc262_fujitsu_master_vol_put,
4567                 .private_value = HDA_COMPOSE_AMP_VAL(0x0c, 3, 0, HDA_OUTPUT),
4568         },
4569         {
4570                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4571                 .name = "Master Playback Switch",
4572                 .info = snd_hda_mixer_amp_switch_info,
4573                 .get = snd_hda_mixer_amp_switch_get,
4574                 .put = alc262_fujitsu_master_sw_put,
4575                 .private_value = HDA_COMPOSE_AMP_VAL(0x14, 3, 0, HDA_OUTPUT),
4576         },
4577         HDA_CODEC_VOLUME("CD Playback Volume", 0x0b, 0x04, HDA_INPUT),
4578         HDA_CODEC_MUTE("CD Playback Switch", 0x0b, 0x04, HDA_INPUT),
4579         HDA_CODEC_VOLUME("Mic Boost", 0x18, 0, HDA_INPUT),
4580         HDA_CODEC_VOLUME("Mic Playback Volume", 0x0b, 0x0, HDA_INPUT),
4581         HDA_CODEC_MUTE("Mic Playback Switch", 0x0b, 0x0, HDA_INPUT),
4582         { } /* end */
4583 };
4584
4585 /* add playback controls from the parsed DAC table */
4586 static int alc262_auto_create_multi_out_ctls(struct alc_spec *spec, const struct auto_pin_cfg *cfg)
4587 {
4588         hda_nid_t nid;
4589         int err;
4590
4591         spec->multiout.num_dacs = 1;    /* only use one dac */
4592         spec->multiout.dac_nids = spec->private_dac_nids;
4593         spec->multiout.dac_nids[0] = 2;
4594
4595         nid = cfg->line_out_pins[0];
4596         if (nid) {
4597                 if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Front Playback Volume",
4598                                        HDA_COMPOSE_AMP_VAL(0x0c, 3, 0, HDA_OUTPUT))) < 0)
4599                         return err;
4600                 if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Front Playback Switch",
4601                                        HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
4602                         return err;
4603         }
4604
4605         nid = cfg->speaker_pin;
4606         if (nid) {
4607                 if (nid == 0x16) {
4608                         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Speaker Playback Volume",
4609                                                HDA_COMPOSE_AMP_VAL(0x0e, 2, 0, HDA_OUTPUT))) < 0)
4610                                 return err;
4611                         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Speaker Playback Switch",
4612                                                HDA_COMPOSE_AMP_VAL(nid, 2, 0, HDA_OUTPUT))) < 0)
4613                                 return err;
4614                 } else {
4615                         if (! cfg->line_out_pins[0])
4616                                 if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Speaker Playback Volume",
4617                                                HDA_COMPOSE_AMP_VAL(0x0c, 3, 0, HDA_OUTPUT))) < 0)
4618                                         return err;
4619                         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Speaker Playback Switch",
4620                                                HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
4621                                 return err;
4622                 }
4623         }
4624         nid = cfg->hp_pin;
4625         if (nid) {
4626                 /* spec->multiout.hp_nid = 2; */
4627                 if (nid == 0x16) {
4628                         if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Headphone Playback Volume",
4629                                                HDA_COMPOSE_AMP_VAL(0x0e, 2, 0, HDA_OUTPUT))) < 0)
4630                                 return err;
4631                         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Headphone Playback Switch",
4632                                                HDA_COMPOSE_AMP_VAL(nid, 2, 0, HDA_OUTPUT))) < 0)
4633                                 return err;
4634                 } else {
4635                         if (! cfg->line_out_pins[0])
4636                                 if ((err = add_control(spec, ALC_CTL_WIDGET_VOL, "Headphone Playback Volume",
4637                                                HDA_COMPOSE_AMP_VAL(0x0c, 3, 0, HDA_OUTPUT))) < 0)
4638                                         return err;
4639                         if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Headphone Playback Switch",
4640                                                HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
4641                                 return err;
4642                 }
4643         }
4644         return 0;       
4645 }
4646
4647 /* identical with ALC880 */
4648 #define alc262_auto_create_analog_input_ctls alc880_auto_create_analog_input_ctls
4649
4650 /*
4651  * generic initialization of ADC, input mixers and output mixers
4652  */
4653 static struct hda_verb alc262_volume_init_verbs[] = {
4654         /*
4655          * Unmute ADC0-2 and set the default input to mic-in
4656          */
4657         {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
4658         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4659         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
4660         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4661         {0x09, AC_VERB_SET_CONNECT_SEL, 0x00},
4662         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4663
4664         /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
4665          * mixer widget
4666          * Note: PASD motherboards uses the Line In 2 as the input for front panel
4667          * mic (mic 2)
4668          */
4669         /* Amp Indices: Mic1 = 0, Mic2 = 1, Line1 = 2, Line2 = 3, CD = 4 */
4670         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4671         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4672         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
4673         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
4674         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
4675
4676         /*
4677          * Set up output mixers (0x0c - 0x0f)
4678          */
4679         /* set vol=0 to output mixers */
4680         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4681         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4682         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4683         
4684         /* set up input amps for analog loopback */
4685         /* Amp Indices: DAC = 0, mixer = 1 */
4686         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4687         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4688         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4689         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4690         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4691         {0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4692
4693         /* FIXME: use matrix-type input source selection */
4694         /* Mixer elements: 0x18, 19, 1a, 1b, 1c, 1d, 14, 15, 16, 17, 0b */
4695         /* Input mixer1: unmute Mic, F-Mic, Line, CD inputs */
4696         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4697         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4698         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4699         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4700         /* Input mixer2 */
4701         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4702         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4703         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4704         {0x23, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4705         /* Input mixer3 */
4706         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x00 << 8))},
4707         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x03 << 8))},
4708         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8))},
4709         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x04 << 8))},
4710
4711         { }
4712 };
4713
4714 /* pcm configuration: identiacal with ALC880 */
4715 #define alc262_pcm_analog_playback      alc880_pcm_analog_playback
4716 #define alc262_pcm_analog_capture       alc880_pcm_analog_capture
4717 #define alc262_pcm_digital_playback     alc880_pcm_digital_playback
4718 #define alc262_pcm_digital_capture      alc880_pcm_digital_capture
4719
4720 /*
4721  * BIOS auto configuration
4722  */
4723 static int alc262_parse_auto_config(struct hda_codec *codec)
4724 {
4725         struct alc_spec *spec = codec->spec;
4726         int err;
4727         static hda_nid_t alc262_ignore[] = { 0x1d, 0 };
4728
4729         if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg,
4730                                                 alc262_ignore)) < 0)
4731                 return err;
4732         if (! spec->autocfg.line_outs && ! spec->autocfg.speaker_pin &&
4733             ! spec->autocfg.hp_pin)
4734                 return 0; /* can't find valid BIOS pin config */
4735         if ((err = alc262_auto_create_multi_out_ctls(spec, &spec->autocfg)) < 0 ||
4736             (err = alc262_auto_create_analog_input_ctls(spec, &spec->autocfg)) < 0)
4737                 return err;
4738
4739         spec->multiout.max_channels = spec->multiout.num_dacs * 2;
4740
4741         if (spec->autocfg.dig_out_pin)
4742                 spec->multiout.dig_out_nid = ALC262_DIGOUT_NID;
4743         if (spec->autocfg.dig_in_pin)
4744                 spec->dig_in_nid = ALC262_DIGIN_NID;
4745
4746         if (spec->kctl_alloc)
4747                 spec->mixers[spec->num_mixers++] = spec->kctl_alloc;
4748
4749         spec->init_verbs[spec->num_init_verbs++] = alc262_volume_init_verbs;
4750         spec->input_mux = &spec->private_imux;
4751
4752         return 1;
4753 }
4754
4755 #define alc262_auto_init_multi_out      alc882_auto_init_multi_out
4756 #define alc262_auto_init_hp_out         alc882_auto_init_hp_out
4757 #define alc262_auto_init_analog_input   alc882_auto_init_analog_input
4758
4759
4760 /* init callback for auto-configuration model -- overriding the default init */
4761 static void alc262_auto_init(struct hda_codec *codec)
4762 {
4763         alc262_auto_init_multi_out(codec);
4764         alc262_auto_init_hp_out(codec);
4765         alc262_auto_init_analog_input(codec);
4766 }
4767
4768 /*
4769  * configuration and preset
4770  */
4771 static struct hda_board_config alc262_cfg_tbl[] = {
4772         { .modelname = "basic", .config = ALC262_BASIC },
4773         { .modelname = "fujitsu", .config = ALC262_FUJITSU },
4774         { .pci_subvendor = 0x10cf, .pci_subdevice = 0x1397, .config = ALC262_FUJITSU },
4775         { .modelname = "auto", .config = ALC262_AUTO },
4776         {}
4777 };
4778
4779 static struct alc_config_preset alc262_presets[] = {
4780         [ALC262_BASIC] = {
4781                 .mixers = { alc262_base_mixer },
4782                 .init_verbs = { alc262_init_verbs },
4783                 .num_dacs = ARRAY_SIZE(alc262_dac_nids),
4784                 .dac_nids = alc262_dac_nids,
4785                 .hp_nid = 0x03,
4786                 .num_channel_mode = ARRAY_SIZE(alc262_modes),
4787                 .channel_mode = alc262_modes,
4788                 .input_mux = &alc262_capture_source,
4789         },
4790         [ALC262_FUJITSU] = {
4791                 .mixers = { alc262_fujitsu_mixer },
4792                 .init_verbs = { alc262_init_verbs, alc262_fujitsu_unsol_verbs },
4793                 .num_dacs = ARRAY_SIZE(alc262_dac_nids),
4794                 .dac_nids = alc262_dac_nids,
4795                 .hp_nid = 0x03,
4796                 .dig_out_nid = ALC262_DIGOUT_NID,
4797                 .num_channel_mode = ARRAY_SIZE(alc262_modes),
4798                 .channel_mode = alc262_modes,
4799                 .input_mux = &alc262_fujitsu_capture_source,
4800                 .unsol_event = alc262_fujitsu_unsol_event,
4801         },
4802 };
4803
4804 static int patch_alc262(struct hda_codec *codec)
4805 {
4806         struct alc_spec *spec;
4807         int board_config;
4808         int err;
4809
4810         spec = kcalloc(1, sizeof(*spec), GFP_KERNEL);
4811         if (spec == NULL)
4812                 return -ENOMEM;
4813
4814         codec->spec = spec;
4815 #if 0
4816         /* pshou 07/11/05  set a zero PCM sample to DAC when FIFO is under-run */
4817         {
4818         int tmp;
4819         snd_hda_codec_write(codec, 0x1a, 0, AC_VERB_SET_COEF_INDEX, 7);
4820         tmp = snd_hda_codec_read(codec, 0x20, 0, AC_VERB_GET_PROC_COEF, 0);
4821         snd_hda_codec_write(codec, 0x1a, 0, AC_VERB_SET_COEF_INDEX, 7);
4822         snd_hda_codec_write(codec, 0x1a, 0, AC_VERB_SET_PROC_COEF, tmp | 0x80);
4823         }
4824 #endif
4825
4826         board_config = snd_hda_check_board_config(codec, alc262_cfg_tbl);
4827         if (board_config < 0 || board_config >= ALC262_MODEL_LAST) {
4828                 printk(KERN_INFO "hda_codec: Unknown model for ALC262, trying auto-probe from BIOS...\n");
4829                 board_config = ALC262_AUTO;
4830         }
4831
4832         if (board_config == ALC262_AUTO) {
4833                 /* automatic parse from the BIOS config */
4834                 err = alc262_parse_auto_config(codec);
4835                 if (err < 0) {
4836                         alc_free(codec);
4837                         return err;
4838                 } else if (! err) {
4839                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using base mode...\n");
4840                         board_config = ALC262_BASIC;
4841                 }
4842         }
4843
4844         if (board_config != ALC262_AUTO)
4845                 setup_preset(spec, &alc262_presets[board_config]);
4846
4847         spec->stream_name_analog = "ALC262 Analog";
4848         spec->stream_analog_playback = &alc262_pcm_analog_playback;
4849         spec->stream_analog_capture = &alc262_pcm_analog_capture;
4850                 
4851         spec->stream_name_digital = "ALC262 Digital";
4852         spec->stream_digital_playback = &alc262_pcm_digital_playback;
4853         spec->stream_digital_capture = &alc262_pcm_digital_capture;
4854
4855         if (! spec->adc_nids && spec->input_mux) {
4856                 /* check whether NID 0x07 is valid */
4857                 unsigned int wcap = get_wcaps(codec, 0x07);
4858
4859                 wcap = (wcap & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT; /* get type */
4860                 if (wcap != AC_WID_AUD_IN) {
4861                         spec->adc_nids = alc262_adc_nids_alt;
4862                         spec->num_adc_nids = ARRAY_SIZE(alc262_adc_nids_alt);
4863                         spec->mixers[spec->num_mixers] = alc262_capture_alt_mixer;
4864                         spec->num_mixers++;
4865                 } else {
4866                         spec->adc_nids = alc262_adc_nids;
4867                         spec->num_adc_nids = ARRAY_SIZE(alc262_adc_nids);
4868                         spec->mixers[spec->num_mixers] = alc262_capture_mixer;
4869                         spec->num_mixers++;
4870                 }
4871         }
4872
4873         codec->patch_ops = alc_patch_ops;
4874         if (board_config == ALC262_AUTO)
4875                 spec->init_hook = alc262_auto_init;
4876                 
4877         return 0;
4878 }
4879
4880
4881 /*
4882  *  ALC861 channel source setting (2/6 channel selection for 3-stack)
4883  */
4884
4885 /*
4886  * set the path ways for 2 channel output
4887  * need to set the codec line out and mic 1 pin widgets to inputs
4888  */
4889 static struct hda_verb alc861_threestack_ch2_init[] = {
4890         /* set pin widget 1Ah (line in) for input */
4891         { 0x0c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
4892         /* set pin widget 18h (mic1/2) for input, for mic also enable the vref */
4893         { 0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
4894
4895         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb00c },
4896         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x01 << 8)) }, //mic
4897         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, (0x7000 | (0x02 << 8)) }, //line in
4898         { } /* end */
4899 };
4900 /*
4901  * 6ch mode
4902  * need to set the codec line out and mic 1 pin widgets to outputs
4903  */
4904 static struct hda_verb alc861_threestack_ch6_init[] = {
4905         /* set pin widget 1Ah (line in) for output (Back Surround)*/
4906         { 0x0c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
4907         /* set pin widget 18h (mic1) for output (CLFE)*/
4908         { 0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
4909
4910         { 0x0c, AC_VERB_SET_CONNECT_SEL, 0x00 },
4911         { 0x0d, AC_VERB_SET_CONNECT_SEL, 0x00 },
4912
4913         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080 },
4914         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x01 << 8)) }, //mic
4915         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, (0x7080 | (0x02 << 8)) }, //line in
4916         { } /* end */
4917 };
4918
4919 static struct hda_channel_mode alc861_threestack_modes[2] = {
4920         { 2, alc861_threestack_ch2_init },
4921         { 6, alc861_threestack_ch6_init },
4922 };
4923
4924 /* patch-ALC861 */
4925
4926 static struct snd_kcontrol_new alc861_base_mixer[] = {
4927         /* output mixer control */
4928         HDA_CODEC_MUTE("Front Playback Switch", 0x03, 0x0, HDA_OUTPUT),
4929         HDA_CODEC_MUTE("Surround Playback Switch", 0x06, 0x0, HDA_OUTPUT),
4930         HDA_CODEC_MUTE_MONO("Center Playback Switch", 0x05, 1, 0x0, HDA_OUTPUT),
4931         HDA_CODEC_MUTE_MONO("LFE Playback Switch", 0x05, 2, 0x0, HDA_OUTPUT),
4932         HDA_CODEC_MUTE("Side Playback Switch", 0x04, 0x0, HDA_OUTPUT),
4933
4934         /*Input mixer control */
4935         /* HDA_CODEC_VOLUME("Input Playback Volume", 0x15, 0x0, HDA_OUTPUT),
4936            HDA_CODEC_MUTE("Input Playback Switch", 0x15, 0x0, HDA_OUTPUT), */
4937         HDA_CODEC_VOLUME("CD Playback Volume", 0x15, 0x0, HDA_INPUT),
4938         HDA_CODEC_MUTE("CD Playback Switch", 0x15, 0x0, HDA_INPUT),
4939         HDA_CODEC_VOLUME("Line Playback Volume", 0x15, 0x02, HDA_INPUT),
4940         HDA_CODEC_MUTE("Line Playback Switch", 0x15, 0x02, HDA_INPUT),
4941         HDA_CODEC_VOLUME("Mic Playback Volume", 0x15, 0x01, HDA_INPUT),
4942         HDA_CODEC_MUTE("Mic Playback Switch", 0x15, 0x01, HDA_INPUT),
4943         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x10, 0x01, HDA_OUTPUT),
4944         HDA_CODEC_MUTE("Headphone Playback Switch", 0x1a, 0x03, HDA_INPUT),
4945  
4946         /* Capture mixer control */
4947         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
4948         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
4949         {
4950                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4951                 .name = "Capture Source",
4952                 .count = 1,
4953                 .info = alc_mux_enum_info,
4954                 .get = alc_mux_enum_get,
4955                 .put = alc_mux_enum_put,
4956         },
4957         { } /* end */
4958 };
4959
4960 static struct snd_kcontrol_new alc861_3ST_mixer[] = {
4961         /* output mixer control */
4962         HDA_CODEC_MUTE("Front Playback Switch", 0x03, 0x0, HDA_OUTPUT),
4963         HDA_CODEC_MUTE("Surround Playback Switch", 0x06, 0x0, HDA_OUTPUT),
4964         HDA_CODEC_MUTE_MONO("Center Playback Switch", 0x05, 1, 0x0, HDA_OUTPUT),
4965         HDA_CODEC_MUTE_MONO("LFE Playback Switch", 0x05, 2, 0x0, HDA_OUTPUT),
4966         /*HDA_CODEC_MUTE("Side Playback Switch", 0x04, 0x0, HDA_OUTPUT), */
4967
4968         /* Input mixer control */
4969         /* HDA_CODEC_VOLUME("Input Playback Volume", 0x15, 0x0, HDA_OUTPUT),
4970            HDA_CODEC_MUTE("Input Playback Switch", 0x15, 0x0, HDA_OUTPUT), */
4971         HDA_CODEC_VOLUME("CD Playback Volume", 0x15, 0x0, HDA_INPUT),
4972         HDA_CODEC_MUTE("CD Playback Switch", 0x15, 0x0, HDA_INPUT),
4973         HDA_CODEC_VOLUME("Line Playback Volume", 0x15, 0x02, HDA_INPUT),
4974         HDA_CODEC_MUTE("Line Playback Switch", 0x15, 0x02, HDA_INPUT),
4975         HDA_CODEC_VOLUME("Mic Playback Volume", 0x15, 0x01, HDA_INPUT),
4976         HDA_CODEC_MUTE("Mic Playback Switch", 0x15, 0x01, HDA_INPUT),
4977         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x10, 0x01, HDA_OUTPUT),
4978         HDA_CODEC_MUTE("Headphone Playback Switch", 0x1a, 0x03, HDA_INPUT),
4979  
4980         /* Capture mixer control */
4981         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
4982         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
4983         {
4984                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4985                 .name = "Capture Source",
4986                 .count = 1,
4987                 .info = alc_mux_enum_info,
4988                 .get = alc_mux_enum_get,
4989                 .put = alc_mux_enum_put,
4990         },
4991         {
4992                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4993                 .name = "Channel Mode",
4994                 .info = alc_ch_mode_info,
4995                 .get = alc_ch_mode_get,
4996                 .put = alc_ch_mode_put,
4997                 .private_value = ARRAY_SIZE(alc861_threestack_modes),
4998         },
4999         { } /* end */
5000 };                      
5001         
5002 /*
5003  * generic initialization of ADC, input mixers and output mixers
5004  */
5005 static struct hda_verb alc861_base_init_verbs[] = {
5006         /*
5007          * Unmute ADC0 and set the default input to mic-in
5008          */
5009         /* port-A for surround (rear panel) */
5010         { 0x0e, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
5011         { 0x0e, AC_VERB_SET_CONNECT_SEL, 0x00 },
5012         /* port-B for mic-in (rear panel) with vref */
5013         { 0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
5014         /* port-C for line-in (rear panel) */
5015         { 0x0c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
5016         /* port-D for Front */
5017         { 0x0b, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
5018         { 0x0b, AC_VERB_SET_CONNECT_SEL, 0x00 },
5019         /* port-E for HP out (front panel) */
5020         { 0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0 },
5021         /* route front PCM to HP */
5022         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x01 },
5023         /* port-F for mic-in (front panel) with vref */
5024         { 0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
5025         /* port-G for CLFE (rear panel) */
5026         { 0x1f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
5027         { 0x1f, AC_VERB_SET_CONNECT_SEL, 0x00 },
5028         /* port-H for side (rear panel) */
5029         { 0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
5030         { 0x20, AC_VERB_SET_CONNECT_SEL, 0x00 },
5031         /* CD-in */
5032         { 0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
5033         /* route front mic to ADC1*/
5034         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
5035         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5036         
5037         /* Unmute DAC0~3 & spdif out*/
5038         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5039         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5040         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5041         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5042         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5043         
5044         /* Unmute Mixer 14 (mic) 1c (Line in)*/
5045         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5046         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5047         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5048         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5049         
5050         /* Unmute Stereo Mixer 15 */
5051         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5052         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5053         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
5054         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb00c          }, //Output 0~12 step
5055
5056         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5057         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5058         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5059         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5060         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5061         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5062         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5063         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5064         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)}, // hp used DAC 3 (Front)
5065         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
5066
5067         { }
5068 };
5069
5070 static struct hda_verb alc861_threestack_init_verbs[] = {
5071         /*
5072          * Unmute ADC0 and set the default input to mic-in
5073          */
5074         /* port-A for surround (rear panel) */
5075         { 0x0e, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
5076         /* port-B for mic-in (rear panel) with vref */
5077         { 0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
5078         /* port-C for line-in (rear panel) */
5079         { 0x0c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
5080         /* port-D for Front */
5081         { 0x0b, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
5082         { 0x0b, AC_VERB_SET_CONNECT_SEL, 0x00 },
5083         /* port-E for HP out (front panel) */
5084         { 0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0 },
5085         /* route front PCM to HP */
5086         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x01 },
5087         /* port-F for mic-in (front panel) with vref */
5088         { 0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
5089         /* port-G for CLFE (rear panel) */
5090         { 0x1f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
5091         /* port-H for side (rear panel) */
5092         { 0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00 },
5093         /* CD-in */
5094         { 0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
5095         /* route front mic to ADC1*/
5096         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
5097         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5098         /* Unmute DAC0~3 & spdif out*/
5099         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5100         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5101         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5102         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5103         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5104         
5105         /* Unmute Mixer 14 (mic) 1c (Line in)*/
5106         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5107         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5108         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5109         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5110         
5111         /* Unmute Stereo Mixer 15 */
5112         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5113         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5114         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
5115         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb00c          }, //Output 0~12 step
5116
5117         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5118         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5119         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5120         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5121         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5122         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5123         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5124         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5125         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)}, // hp used DAC 3 (Front)
5126         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
5127         { }
5128 };
5129 /*
5130  * generic initialization of ADC, input mixers and output mixers
5131  */
5132 static struct hda_verb alc861_auto_init_verbs[] = {
5133         /*
5134          * Unmute ADC0 and set the default input to mic-in
5135          */
5136 //      {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},
5137         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5138         
5139         /* Unmute DAC0~3 & spdif out*/
5140         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
5141         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
5142         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
5143         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
5144         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
5145         
5146         /* Unmute Mixer 14 (mic) 1c (Line in)*/
5147         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5148         {0x014, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5149         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5150         {0x01c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5151         
5152         /* Unmute Stereo Mixer 15 */
5153         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5154         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5155         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
5156         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb00c},
5157
5158         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5159         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5160         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5161         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5162         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5163         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5164         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
5165         {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
5166
5167         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
5168         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
5169         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},    
5170         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},            
5171         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
5172         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
5173         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},    
5174         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},    
5175
5176         {0x08, AC_VERB_SET_CONNECT_SEL, 0x00},  // set Mic 1
5177
5178         { }
5179 };
5180
5181 /* pcm configuration: identiacal with ALC880 */
5182 #define alc861_pcm_analog_playback      alc880_pcm_analog_playback
5183 #define alc861_pcm_analog_capture       alc880_pcm_analog_capture
5184 #define alc861_pcm_digital_playback     alc880_pcm_digital_playback
5185 #define alc861_pcm_digital_capture      alc880_pcm_digital_capture
5186
5187
5188 #define ALC861_DIGOUT_NID       0x07
5189
5190 static struct hda_channel_mode alc861_8ch_modes[1] = {
5191         { 8, NULL }
5192 };
5193
5194 static hda_nid_t alc861_dac_nids[4] = {
5195         /* front, surround, clfe, side */
5196         0x03, 0x06, 0x05, 0x04
5197 };
5198
5199 static hda_nid_t alc861_adc_nids[1] = {
5200         /* ADC0-2 */
5201         0x08,
5202 };
5203
5204 static struct hda_input_mux alc861_capture_source = {
5205         .num_items = 5,
5206         .items = {
5207                 { "Mic", 0x0 },
5208                 { "Front Mic", 0x3 },
5209                 { "Line", 0x1 },
5210                 { "CD", 0x4 },
5211                 { "Mixer", 0x5 },
5212         },
5213 };
5214
5215 /* fill in the dac_nids table from the parsed pin configuration */
5216 static int alc861_auto_fill_dac_nids(struct alc_spec *spec, const struct auto_pin_cfg *cfg)
5217 {
5218         int i;
5219         hda_nid_t nid;
5220
5221         spec->multiout.dac_nids = spec->private_dac_nids;
5222         for (i = 0; i < cfg->line_outs; i++) {
5223                 nid = cfg->line_out_pins[i];
5224                 if (nid) {
5225                         if (i >= ARRAY_SIZE(alc861_dac_nids))
5226                                 continue;
5227                         spec->multiout.dac_nids[i] = alc861_dac_nids[i];
5228                 }
5229         }
5230         spec->multiout.num_dacs = cfg->line_outs;
5231         return 0;
5232 }
5233
5234 /* add playback controls from the parsed DAC table */
5235 static int alc861_auto_create_multi_out_ctls(struct alc_spec *spec,
5236                                              const struct auto_pin_cfg *cfg)
5237 {
5238         char name[32];
5239         static const char *chname[4] = { "Front", "Surround", NULL /*CLFE*/, "Side" };
5240         hda_nid_t nid;
5241         int i, idx, err;
5242
5243         for (i = 0; i < cfg->line_outs; i++) {
5244                 nid = spec->multiout.dac_nids[i];
5245                 if (! nid)
5246                         continue;
5247                 if (nid == 0x05) {
5248                         /* Center/LFE */
5249                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, "Center Playback Switch",
5250                                                HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT))) < 0)
5251                                 return err;
5252                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, "LFE Playback Switch",
5253                                                HDA_COMPOSE_AMP_VAL(nid, 2, 0, HDA_OUTPUT))) < 0)
5254                                 return err;
5255                 } else {
5256                         for (idx = 0; idx < ARRAY_SIZE(alc861_dac_nids) - 1; idx++)
5257                                 if (nid == alc861_dac_nids[idx])
5258                                         break;
5259                         sprintf(name, "%s Playback Switch", chname[idx]);
5260                         if ((err = add_control(spec, ALC_CTL_BIND_MUTE, name,
5261                                                HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
5262                                 return err;
5263                 }
5264         }
5265         return 0;
5266 }
5267
5268 static int alc861_auto_create_hp_ctls(struct alc_spec *spec, hda_nid_t pin)
5269 {
5270         int err;
5271         hda_nid_t nid;
5272
5273         if (! pin)
5274                 return 0;
5275
5276         if ((pin >= 0x0b && pin <= 0x10) || pin == 0x1f || pin == 0x20) {
5277                 nid = 0x03;
5278                 if ((err = add_control(spec, ALC_CTL_WIDGET_MUTE, "Headphone Playback Switch",
5279                                        HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT))) < 0)
5280                         return err;
5281                 spec->multiout.hp_nid = nid;
5282         }
5283         return 0;
5284 }
5285
5286 /* create playback/capture controls for input pins */
5287 static int alc861_auto_create_analog_input_ctls(struct alc_spec *spec, const struct auto_pin_cfg *cfg)
5288 {
5289         struct hda_input_mux *imux = &spec->private_imux;
5290         int i, err, idx, idx1;
5291
5292         for (i = 0; i < AUTO_PIN_LAST; i++) {
5293                 switch(cfg->input_pins[i]) {
5294                 case 0x0c:
5295                         idx1 = 1;
5296                         idx = 2;        // Line In
5297                         break;
5298                 case 0x0f:
5299                         idx1 = 2;
5300                         idx = 2;        // Line In
5301                         break;
5302                 case 0x0d:
5303                         idx1 = 0;
5304                         idx = 1;        // Mic In 
5305                         break;
5306                 case 0x10:      
5307                         idx1 = 3;
5308                         idx = 1;        // Mic In 
5309                         break;
5310                 case 0x11:
5311                         idx1 = 4;
5312                         idx = 0;        // CD
5313                         break;
5314                 default:
5315                         continue;
5316                 }
5317
5318                 err = new_analog_input(spec, cfg->input_pins[i],
5319                                        auto_pin_cfg_labels[i], idx, 0x15);
5320                 if (err < 0)
5321                         return err;
5322
5323                 imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
5324                 imux->items[imux->num_items].index = idx1;
5325                 imux->num_items++;      
5326         }
5327         return 0;
5328 }
5329
5330 static struct snd_kcontrol_new alc861_capture_mixer[] = {
5331         HDA_CODEC_VOLUME("Capture Volume", 0x08, 0x0, HDA_INPUT),
5332         HDA_CODEC_MUTE("Capture Switch", 0x08, 0x0, HDA_INPUT),
5333
5334         {
5335                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
5336                 /* The multiple "Capture Source" controls confuse alsamixer
5337                  * So call somewhat different..
5338                  *FIXME: the controls appear in the "playback" view!
5339                  */
5340                 /* .name = "Capture Source", */
5341                 .name = "Input Source",
5342                 .count = 1,
5343                 .info = alc_mux_enum_info,
5344                 .get = alc_mux_enum_get,
5345                 .put = alc_mux_enum_put,
5346         },
5347         { } /* end */
5348 };
5349
5350 static void alc861_auto_set_output_and_unmute(struct hda_codec *codec, hda_nid_t nid,
5351                                               int pin_type, int dac_idx)
5352 {
5353         /* set as output */
5354
5355         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
5356         snd_hda_codec_write(codec, dac_idx, 0, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE);
5357
5358 }
5359
5360 static void alc861_auto_init_multi_out(struct hda_codec *codec)
5361 {
5362         struct alc_spec *spec = codec->spec;
5363         int i;
5364
5365         for (i = 0; i < spec->autocfg.line_outs; i++) {
5366                 hda_nid_t nid = spec->autocfg.line_out_pins[i];
5367                 if (nid)
5368                         alc861_auto_set_output_and_unmute(codec, nid, PIN_OUT, spec->multiout.dac_nids[i]);
5369         }
5370 }
5371
5372 static void alc861_auto_init_hp_out(struct hda_codec *codec)
5373 {
5374         struct alc_spec *spec = codec->spec;
5375         hda_nid_t pin;
5376
5377         pin = spec->autocfg.hp_pin;
5378         if (pin) /* connect to front */
5379                 alc861_auto_set_output_and_unmute(codec, pin, PIN_HP, spec->multiout.dac_nids[0]);
5380 }
5381
5382 static void alc861_auto_init_analog_input(struct hda_codec *codec)
5383 {
5384         struct alc_spec *spec = codec->spec;
5385         int i;
5386
5387         for (i = 0; i < AUTO_PIN_LAST; i++) {
5388                 hda_nid_t nid = spec->autocfg.input_pins[i];
5389                 if ((nid>=0x0c) && (nid <=0x11)) {
5390                         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
5391                                             i <= AUTO_PIN_FRONT_MIC ? PIN_VREF80 : PIN_IN);
5392                 }
5393         }
5394 }
5395
5396 /* parse the BIOS configuration and set up the alc_spec */
5397 /* return 1 if successful, 0 if the proper config is not found, or a negative error code */
5398 static int alc861_parse_auto_config(struct hda_codec *codec)
5399 {
5400         struct alc_spec *spec = codec->spec;
5401         int err;
5402         static hda_nid_t alc861_ignore[] = { 0x1d, 0 };
5403
5404         if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg,
5405                                                 alc861_ignore)) < 0)
5406                 return err;
5407         if (! spec->autocfg.line_outs && ! spec->autocfg.speaker_pin &&
5408             ! spec->autocfg.hp_pin)
5409                 return 0; /* can't find valid BIOS pin config */
5410
5411         if ((err = alc861_auto_fill_dac_nids(spec, &spec->autocfg)) < 0 ||
5412             (err = alc861_auto_create_multi_out_ctls(spec, &spec->autocfg)) < 0 ||
5413             (err = alc861_auto_create_hp_ctls(spec, spec->autocfg.hp_pin)) < 0 ||
5414             (err = alc861_auto_create_analog_input_ctls(spec, &spec->autocfg)) < 0)
5415                 return err;
5416
5417         spec->multiout.max_channels = spec->multiout.num_dacs * 2;
5418
5419         if (spec->autocfg.dig_out_pin)
5420                 spec->multiout.dig_out_nid = ALC861_DIGOUT_NID;
5421
5422         if (spec->kctl_alloc)
5423                 spec->mixers[spec->num_mixers++] = spec->kctl_alloc;
5424
5425         spec->init_verbs[spec->num_init_verbs++] = alc861_auto_init_verbs;
5426
5427         spec->input_mux = &spec->private_imux;
5428
5429         spec->adc_nids = alc861_adc_nids;
5430         spec->num_adc_nids = ARRAY_SIZE(alc861_adc_nids);
5431         spec->mixers[spec->num_mixers] = alc861_capture_mixer;
5432         spec->num_mixers++;
5433
5434         return 1;
5435 }
5436
5437 /* additional initialization for auto-configuration model */
5438 static void alc861_auto_init(struct hda_codec *codec)
5439 {
5440         alc861_auto_init_multi_out(codec);
5441         alc861_auto_init_hp_out(codec);
5442         alc861_auto_init_analog_input(codec);
5443 }
5444
5445
5446 /*
5447  * configuration and preset
5448  */
5449 static struct hda_board_config alc861_cfg_tbl[] = {
5450         { .modelname = "3stack", .config = ALC861_3ST },
5451         { .pci_subvendor = 0x8086, .pci_subdevice = 0xd600, .config = ALC861_3ST },
5452         { .modelname = "3stack-dig", .config = ALC861_3ST_DIG },
5453         { .modelname = "6stack-dig", .config = ALC861_6ST_DIG },
5454         { .modelname = "auto", .config = ALC861_AUTO },
5455         {}
5456 };
5457
5458 static struct alc_config_preset alc861_presets[] = {
5459         [ALC861_3ST] = {
5460                 .mixers = { alc861_3ST_mixer },
5461                 .init_verbs = { alc861_threestack_init_verbs },
5462                 .num_dacs = ARRAY_SIZE(alc861_dac_nids),
5463                 .dac_nids = alc861_dac_nids,
5464                 .num_channel_mode = ARRAY_SIZE(alc861_threestack_modes),
5465                 .channel_mode = alc861_threestack_modes,
5466                 .num_adc_nids = ARRAY_SIZE(alc861_adc_nids),
5467                 .adc_nids = alc861_adc_nids,
5468                 .input_mux = &alc861_capture_source,
5469         },
5470         [ALC861_3ST_DIG] = {
5471                 .mixers = { alc861_base_mixer },
5472                 .init_verbs = { alc861_threestack_init_verbs },
5473                 .num_dacs = ARRAY_SIZE(alc861_dac_nids),
5474                 .dac_nids = alc861_dac_nids,
5475                 .dig_out_nid = ALC861_DIGOUT_NID,
5476                 .num_channel_mode = ARRAY_SIZE(alc861_threestack_modes),
5477                 .channel_mode = alc861_threestack_modes,
5478                 .num_adc_nids = ARRAY_SIZE(alc861_adc_nids),
5479                 .adc_nids = alc861_adc_nids,
5480                 .input_mux = &alc861_capture_source,
5481         },
5482         [ALC861_6ST_DIG] = {
5483                 .mixers = { alc861_base_mixer },
5484                 .init_verbs = { alc861_base_init_verbs },
5485                 .num_dacs = ARRAY_SIZE(alc861_dac_nids),
5486                 .dac_nids = alc861_dac_nids,
5487                 .dig_out_nid = ALC861_DIGOUT_NID,
5488                 .num_channel_mode = ARRAY_SIZE(alc861_8ch_modes),
5489                 .channel_mode = alc861_8ch_modes,
5490                 .num_adc_nids = ARRAY_SIZE(alc861_adc_nids),
5491                 .adc_nids = alc861_adc_nids,
5492                 .input_mux = &alc861_capture_source,
5493         },
5494 };      
5495
5496
5497 static int patch_alc861(struct hda_codec *codec)
5498 {
5499         struct alc_spec *spec;
5500         int board_config;
5501         int err;
5502
5503         spec = kcalloc(1, sizeof(*spec), GFP_KERNEL);
5504         if (spec == NULL)
5505                 return -ENOMEM;
5506
5507         codec->spec = spec;     
5508
5509         board_config = snd_hda_check_board_config(codec, alc861_cfg_tbl);
5510         if (board_config < 0 || board_config >= ALC861_MODEL_LAST) {
5511                 printk(KERN_INFO "hda_codec: Unknown model for ALC861, trying auto-probe from BIOS...\n");
5512                 board_config = ALC861_AUTO;
5513         }
5514
5515         if (board_config == ALC861_AUTO) {
5516                 /* automatic parse from the BIOS config */
5517                 err = alc861_parse_auto_config(codec);
5518                 if (err < 0) {
5519                         alc_free(codec);
5520                         return err;
5521                 } else if (! err) {
5522                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using base mode...\n");
5523                    board_config = ALC861_3ST_DIG;
5524                 }
5525         }
5526
5527         if (board_config != ALC861_AUTO)
5528                 setup_preset(spec, &alc861_presets[board_config]);
5529
5530         spec->stream_name_analog = "ALC861 Analog";
5531         spec->stream_analog_playback = &alc861_pcm_analog_playback;
5532         spec->stream_analog_capture = &alc861_pcm_analog_capture;
5533
5534         spec->stream_name_digital = "ALC861 Digital";
5535         spec->stream_digital_playback = &alc861_pcm_digital_playback;
5536         spec->stream_digital_capture = &alc861_pcm_digital_capture;
5537
5538         codec->patch_ops = alc_patch_ops;
5539         if (board_config == ALC861_AUTO)
5540                 spec->init_hook = alc861_auto_init;
5541                 
5542         return 0;
5543 }
5544
5545 /*
5546  * patch entries
5547  */
5548 struct hda_codec_preset snd_hda_preset_realtek[] = {
5549         { .id = 0x10ec0260, .name = "ALC260", .patch = patch_alc260 },
5550         { .id = 0x10ec0262, .name = "ALC262", .patch = patch_alc262 },
5551         { .id = 0x10ec0880, .name = "ALC880", .patch = patch_alc880 },
5552         { .id = 0x10ec0882, .name = "ALC882", .patch = patch_alc882 },
5553         { .id = 0x10ec0883, .name = "ALC883", .patch = patch_alc882 },
5554         { .id = 0x10ec0885, .name = "ALC885", .patch = patch_alc882 },
5555         { .id = 0x10ec0861, .name = "ALC861", .patch = patch_alc861 },
5556         {} /* terminator */
5557 };