]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/blob - sound/pci/hda/patch_analog.c
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/sam/kbuild...
[linux-2.6-omap-h63xx.git] / sound / pci / hda / patch_analog.c
1 /*
2  * HD audio interface patch for AD1882, AD1884, AD1981HD, AD1983, AD1984,
3  *   AD1986A, AD1988
4  *
5  * Copyright (c) 2005-2007 Takashi Iwai <tiwai@suse.de>
6  *
7  *  This driver is free software; you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License as published by
9  *  the Free Software Foundation; either version 2 of the License, or
10  *  (at your option) any later version.
11  *
12  *  This driver is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *  GNU General Public License for more details.
16  *
17  *  You should have received a copy of the GNU General Public License
18  *  along with this program; if not, write to the Free Software
19  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
20  */
21
22 #include <linux/init.h>
23 #include <linux/delay.h>
24 #include <linux/slab.h>
25 #include <linux/pci.h>
26
27 #include <sound/core.h>
28 #include "hda_codec.h"
29 #include "hda_local.h"
30 #include "hda_patch.h"
31
32 struct ad198x_spec {
33         struct snd_kcontrol_new *mixers[5];
34         int num_mixers;
35
36         const struct hda_verb *init_verbs[5];   /* initialization verbs
37                                                  * don't forget NULL termination!
38                                                  */
39         unsigned int num_init_verbs;
40
41         /* playback */
42         struct hda_multi_out multiout;  /* playback set-up
43                                          * max_channels, dacs must be set
44                                          * dig_out_nid and hp_nid are optional
45                                          */
46         unsigned int cur_eapd;
47         unsigned int need_dac_fix;
48
49         /* capture */
50         unsigned int num_adc_nids;
51         hda_nid_t *adc_nids;
52         hda_nid_t dig_in_nid;           /* digital-in NID; optional */
53
54         /* capture source */
55         const struct hda_input_mux *input_mux;
56         hda_nid_t *capsrc_nids;
57         unsigned int cur_mux[3];
58
59         /* channel model */
60         const struct hda_channel_mode *channel_mode;
61         int num_channel_mode;
62
63         /* PCM information */
64         struct hda_pcm pcm_rec[3];      /* used in alc_build_pcms() */
65
66         unsigned int spdif_route;
67
68         /* dynamic controls, init_verbs and input_mux */
69         struct auto_pin_cfg autocfg;
70         unsigned int num_kctl_alloc, num_kctl_used;
71         struct snd_kcontrol_new *kctl_alloc;
72         struct hda_input_mux private_imux;
73         hda_nid_t private_dac_nids[AUTO_CFG_MAX_OUTS];
74
75         unsigned int jack_present :1;
76
77 #ifdef CONFIG_SND_HDA_POWER_SAVE
78         struct hda_loopback_check loopback;
79 #endif
80         /* for virtual master */
81         hda_nid_t vmaster_nid;
82         const char **slave_vols;
83         const char **slave_sws;
84 };
85
86 /*
87  * input MUX handling (common part)
88  */
89 static int ad198x_mux_enum_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
90 {
91         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
92         struct ad198x_spec *spec = codec->spec;
93
94         return snd_hda_input_mux_info(spec->input_mux, uinfo);
95 }
96
97 static int ad198x_mux_enum_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
98 {
99         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
100         struct ad198x_spec *spec = codec->spec;
101         unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
102
103         ucontrol->value.enumerated.item[0] = spec->cur_mux[adc_idx];
104         return 0;
105 }
106
107 static int ad198x_mux_enum_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
108 {
109         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
110         struct ad198x_spec *spec = codec->spec;
111         unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
112
113         return snd_hda_input_mux_put(codec, spec->input_mux, ucontrol,
114                                      spec->capsrc_nids[adc_idx],
115                                      &spec->cur_mux[adc_idx]);
116 }
117
118 /*
119  * initialization (common callbacks)
120  */
121 static int ad198x_init(struct hda_codec *codec)
122 {
123         struct ad198x_spec *spec = codec->spec;
124         int i;
125
126         for (i = 0; i < spec->num_init_verbs; i++)
127                 snd_hda_sequence_write(codec, spec->init_verbs[i]);
128         return 0;
129 }
130
131 static const char *ad_slave_vols[] = {
132         "Front Playback Volume",
133         "Surround Playback Volume",
134         "Center Playback Volume",
135         "LFE Playback Volume",
136         "Side Playback Volume",
137         "Headphone Playback Volume",
138         "Mono Playback Volume",
139         "Speaker Playback Volume",
140         "IEC958 Playback Volume",
141         NULL
142 };
143
144 static const char *ad_slave_sws[] = {
145         "Front Playback Switch",
146         "Surround Playback Switch",
147         "Center Playback Switch",
148         "LFE Playback Switch",
149         "Side Playback Switch",
150         "Headphone Playback Switch",
151         "Mono Playback Switch",
152         "Speaker Playback Switch",
153         "IEC958 Playback Switch",
154         NULL
155 };
156
157 static int ad198x_build_controls(struct hda_codec *codec)
158 {
159         struct ad198x_spec *spec = codec->spec;
160         unsigned int i;
161         int err;
162
163         for (i = 0; i < spec->num_mixers; i++) {
164                 err = snd_hda_add_new_ctls(codec, spec->mixers[i]);
165                 if (err < 0)
166                         return err;
167         }
168         if (spec->multiout.dig_out_nid) {
169                 err = snd_hda_create_spdif_out_ctls(codec, spec->multiout.dig_out_nid);
170                 if (err < 0)
171                         return err;
172                 err = snd_hda_create_spdif_share_sw(codec,
173                                                     &spec->multiout);
174                 if (err < 0)
175                         return err;
176                 spec->multiout.share_spdif = 1;
177         } 
178         if (spec->dig_in_nid) {
179                 err = snd_hda_create_spdif_in_ctls(codec, spec->dig_in_nid);
180                 if (err < 0)
181                         return err;
182         }
183
184         /* if we have no master control, let's create it */
185         if (!snd_hda_find_mixer_ctl(codec, "Master Playback Volume")) {
186                 unsigned int vmaster_tlv[4];
187                 snd_hda_set_vmaster_tlv(codec, spec->vmaster_nid,
188                                         HDA_OUTPUT, vmaster_tlv);
189                 err = snd_hda_add_vmaster(codec, "Master Playback Volume",
190                                           vmaster_tlv,
191                                           (spec->slave_vols ?
192                                            spec->slave_vols : ad_slave_vols));
193                 if (err < 0)
194                         return err;
195         }
196         if (!snd_hda_find_mixer_ctl(codec, "Master Playback Switch")) {
197                 err = snd_hda_add_vmaster(codec, "Master Playback Switch",
198                                           NULL,
199                                           (spec->slave_sws ?
200                                            spec->slave_sws : ad_slave_sws));
201                 if (err < 0)
202                         return err;
203         }
204
205         return 0;
206 }
207
208 #ifdef CONFIG_SND_HDA_POWER_SAVE
209 static int ad198x_check_power_status(struct hda_codec *codec, hda_nid_t nid)
210 {
211         struct ad198x_spec *spec = codec->spec;
212         return snd_hda_check_amp_list_power(codec, &spec->loopback, nid);
213 }
214 #endif
215
216 /*
217  * Analog playback callbacks
218  */
219 static int ad198x_playback_pcm_open(struct hda_pcm_stream *hinfo,
220                                     struct hda_codec *codec,
221                                     struct snd_pcm_substream *substream)
222 {
223         struct ad198x_spec *spec = codec->spec;
224         return snd_hda_multi_out_analog_open(codec, &spec->multiout, substream,
225                                              hinfo);
226 }
227
228 static int ad198x_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
229                                        struct hda_codec *codec,
230                                        unsigned int stream_tag,
231                                        unsigned int format,
232                                        struct snd_pcm_substream *substream)
233 {
234         struct ad198x_spec *spec = codec->spec;
235         return snd_hda_multi_out_analog_prepare(codec, &spec->multiout, stream_tag,
236                                                 format, substream);
237 }
238
239 static int ad198x_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
240                                        struct hda_codec *codec,
241                                        struct snd_pcm_substream *substream)
242 {
243         struct ad198x_spec *spec = codec->spec;
244         return snd_hda_multi_out_analog_cleanup(codec, &spec->multiout);
245 }
246
247 /*
248  * Digital out
249  */
250 static int ad198x_dig_playback_pcm_open(struct hda_pcm_stream *hinfo,
251                                         struct hda_codec *codec,
252                                         struct snd_pcm_substream *substream)
253 {
254         struct ad198x_spec *spec = codec->spec;
255         return snd_hda_multi_out_dig_open(codec, &spec->multiout);
256 }
257
258 static int ad198x_dig_playback_pcm_close(struct hda_pcm_stream *hinfo,
259                                          struct hda_codec *codec,
260                                          struct snd_pcm_substream *substream)
261 {
262         struct ad198x_spec *spec = codec->spec;
263         return snd_hda_multi_out_dig_close(codec, &spec->multiout);
264 }
265
266 static int ad198x_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
267                                            struct hda_codec *codec,
268                                            unsigned int stream_tag,
269                                            unsigned int format,
270                                            struct snd_pcm_substream *substream)
271 {
272         struct ad198x_spec *spec = codec->spec;
273         return snd_hda_multi_out_dig_prepare(codec, &spec->multiout, stream_tag,
274                                              format, substream);
275 }
276
277 /*
278  * Analog capture
279  */
280 static int ad198x_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
281                                       struct hda_codec *codec,
282                                       unsigned int stream_tag,
283                                       unsigned int format,
284                                       struct snd_pcm_substream *substream)
285 {
286         struct ad198x_spec *spec = codec->spec;
287         snd_hda_codec_setup_stream(codec, spec->adc_nids[substream->number],
288                                    stream_tag, 0, format);
289         return 0;
290 }
291
292 static int ad198x_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
293                                       struct hda_codec *codec,
294                                       struct snd_pcm_substream *substream)
295 {
296         struct ad198x_spec *spec = codec->spec;
297         snd_hda_codec_cleanup_stream(codec, spec->adc_nids[substream->number]);
298         return 0;
299 }
300
301
302 /*
303  */
304 static struct hda_pcm_stream ad198x_pcm_analog_playback = {
305         .substreams = 1,
306         .channels_min = 2,
307         .channels_max = 6, /* changed later */
308         .nid = 0, /* fill later */
309         .ops = {
310                 .open = ad198x_playback_pcm_open,
311                 .prepare = ad198x_playback_pcm_prepare,
312                 .cleanup = ad198x_playback_pcm_cleanup
313         },
314 };
315
316 static struct hda_pcm_stream ad198x_pcm_analog_capture = {
317         .substreams = 1,
318         .channels_min = 2,
319         .channels_max = 2,
320         .nid = 0, /* fill later */
321         .ops = {
322                 .prepare = ad198x_capture_pcm_prepare,
323                 .cleanup = ad198x_capture_pcm_cleanup
324         },
325 };
326
327 static struct hda_pcm_stream ad198x_pcm_digital_playback = {
328         .substreams = 1,
329         .channels_min = 2,
330         .channels_max = 2,
331         .nid = 0, /* fill later */
332         .ops = {
333                 .open = ad198x_dig_playback_pcm_open,
334                 .close = ad198x_dig_playback_pcm_close,
335                 .prepare = ad198x_dig_playback_pcm_prepare
336         },
337 };
338
339 static struct hda_pcm_stream ad198x_pcm_digital_capture = {
340         .substreams = 1,
341         .channels_min = 2,
342         .channels_max = 2,
343         /* NID is set in alc_build_pcms */
344 };
345
346 static int ad198x_build_pcms(struct hda_codec *codec)
347 {
348         struct ad198x_spec *spec = codec->spec;
349         struct hda_pcm *info = spec->pcm_rec;
350
351         codec->num_pcms = 1;
352         codec->pcm_info = info;
353
354         info->name = "AD198x Analog";
355         info->stream[SNDRV_PCM_STREAM_PLAYBACK] = ad198x_pcm_analog_playback;
356         info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max = spec->multiout.max_channels;
357         info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dac_nids[0];
358         info->stream[SNDRV_PCM_STREAM_CAPTURE] = ad198x_pcm_analog_capture;
359         info->stream[SNDRV_PCM_STREAM_CAPTURE].substreams = spec->num_adc_nids;
360         info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->adc_nids[0];
361
362         if (spec->multiout.dig_out_nid) {
363                 info++;
364                 codec->num_pcms++;
365                 info->name = "AD198x Digital";
366                 info->pcm_type = HDA_PCM_TYPE_SPDIF;
367                 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = ad198x_pcm_digital_playback;
368                 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dig_out_nid;
369                 if (spec->dig_in_nid) {
370                         info->stream[SNDRV_PCM_STREAM_CAPTURE] = ad198x_pcm_digital_capture;
371                         info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->dig_in_nid;
372                 }
373         }
374
375         return 0;
376 }
377
378 static void ad198x_free(struct hda_codec *codec)
379 {
380         struct ad198x_spec *spec = codec->spec;
381         unsigned int i;
382
383         if (spec->kctl_alloc) {
384                 for (i = 0; i < spec->num_kctl_used; i++)
385                         kfree(spec->kctl_alloc[i].name);
386                 kfree(spec->kctl_alloc);
387         }
388         kfree(codec->spec);
389 }
390
391 static struct hda_codec_ops ad198x_patch_ops = {
392         .build_controls = ad198x_build_controls,
393         .build_pcms = ad198x_build_pcms,
394         .init = ad198x_init,
395         .free = ad198x_free,
396 #ifdef CONFIG_SND_HDA_POWER_SAVE
397         .check_power_status = ad198x_check_power_status,
398 #endif
399 };
400
401
402 /*
403  * EAPD control
404  * the private value = nid | (invert << 8)
405  */
406 #define ad198x_eapd_info        snd_ctl_boolean_mono_info
407
408 static int ad198x_eapd_get(struct snd_kcontrol *kcontrol,
409                            struct snd_ctl_elem_value *ucontrol)
410 {
411         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
412         struct ad198x_spec *spec = codec->spec;
413         int invert = (kcontrol->private_value >> 8) & 1;
414         if (invert)
415                 ucontrol->value.integer.value[0] = ! spec->cur_eapd;
416         else
417                 ucontrol->value.integer.value[0] = spec->cur_eapd;
418         return 0;
419 }
420
421 static int ad198x_eapd_put(struct snd_kcontrol *kcontrol,
422                            struct snd_ctl_elem_value *ucontrol)
423 {
424         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
425         struct ad198x_spec *spec = codec->spec;
426         int invert = (kcontrol->private_value >> 8) & 1;
427         hda_nid_t nid = kcontrol->private_value & 0xff;
428         unsigned int eapd;
429         eapd = !!ucontrol->value.integer.value[0];
430         if (invert)
431                 eapd = !eapd;
432         if (eapd == spec->cur_eapd)
433                 return 0;
434         spec->cur_eapd = eapd;
435         snd_hda_codec_write_cache(codec, nid,
436                                   0, AC_VERB_SET_EAPD_BTLENABLE,
437                                   eapd ? 0x02 : 0x00);
438         return 1;
439 }
440
441 static int ad198x_ch_mode_info(struct snd_kcontrol *kcontrol,
442                                struct snd_ctl_elem_info *uinfo);
443 static int ad198x_ch_mode_get(struct snd_kcontrol *kcontrol,
444                               struct snd_ctl_elem_value *ucontrol);
445 static int ad198x_ch_mode_put(struct snd_kcontrol *kcontrol,
446                               struct snd_ctl_elem_value *ucontrol);
447
448
449 /*
450  * AD1986A specific
451  */
452
453 #define AD1986A_SPDIF_OUT       0x02
454 #define AD1986A_FRONT_DAC       0x03
455 #define AD1986A_SURR_DAC        0x04
456 #define AD1986A_CLFE_DAC        0x05
457 #define AD1986A_ADC             0x06
458
459 static hda_nid_t ad1986a_dac_nids[3] = {
460         AD1986A_FRONT_DAC, AD1986A_SURR_DAC, AD1986A_CLFE_DAC
461 };
462 static hda_nid_t ad1986a_adc_nids[1] = { AD1986A_ADC };
463 static hda_nid_t ad1986a_capsrc_nids[1] = { 0x12 };
464
465 static struct hda_input_mux ad1986a_capture_source = {
466         .num_items = 7,
467         .items = {
468                 { "Mic", 0x0 },
469                 { "CD", 0x1 },
470                 { "Aux", 0x3 },
471                 { "Line", 0x4 },
472                 { "Mix", 0x5 },
473                 { "Mono", 0x6 },
474                 { "Phone", 0x7 },
475         },
476 };
477
478
479 static struct hda_bind_ctls ad1986a_bind_pcm_vol = {
480         .ops = &snd_hda_bind_vol,
481         .values = {
482                 HDA_COMPOSE_AMP_VAL(AD1986A_FRONT_DAC, 3, 0, HDA_OUTPUT),
483                 HDA_COMPOSE_AMP_VAL(AD1986A_SURR_DAC, 3, 0, HDA_OUTPUT),
484                 HDA_COMPOSE_AMP_VAL(AD1986A_CLFE_DAC, 3, 0, HDA_OUTPUT),
485                 0
486         },
487 };
488
489 static struct hda_bind_ctls ad1986a_bind_pcm_sw = {
490         .ops = &snd_hda_bind_sw,
491         .values = {
492                 HDA_COMPOSE_AMP_VAL(AD1986A_FRONT_DAC, 3, 0, HDA_OUTPUT),
493                 HDA_COMPOSE_AMP_VAL(AD1986A_SURR_DAC, 3, 0, HDA_OUTPUT),
494                 HDA_COMPOSE_AMP_VAL(AD1986A_CLFE_DAC, 3, 0, HDA_OUTPUT),
495                 0
496         },
497 };
498
499 /*
500  * mixers
501  */
502 static struct snd_kcontrol_new ad1986a_mixers[] = {
503         /*
504          * bind volumes/mutes of 3 DACs as a single PCM control for simplicity
505          */
506         HDA_BIND_VOL("PCM Playback Volume", &ad1986a_bind_pcm_vol),
507         HDA_BIND_SW("PCM Playback Switch", &ad1986a_bind_pcm_sw),
508         HDA_CODEC_VOLUME("Front Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
509         HDA_CODEC_MUTE("Front Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
510         HDA_CODEC_VOLUME("Surround Playback Volume", 0x1c, 0x0, HDA_OUTPUT),
511         HDA_CODEC_MUTE("Surround Playback Switch", 0x1c, 0x0, HDA_OUTPUT),
512         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x1d, 1, 0x0, HDA_OUTPUT),
513         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x1d, 2, 0x0, HDA_OUTPUT),
514         HDA_CODEC_MUTE_MONO("Center Playback Switch", 0x1d, 1, 0x0, HDA_OUTPUT),
515         HDA_CODEC_MUTE_MONO("LFE Playback Switch", 0x1d, 2, 0x0, HDA_OUTPUT),
516         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x1a, 0x0, HDA_OUTPUT),
517         HDA_CODEC_MUTE("Headphone Playback Switch", 0x1a, 0x0, HDA_OUTPUT),
518         HDA_CODEC_VOLUME("CD Playback Volume", 0x15, 0x0, HDA_OUTPUT),
519         HDA_CODEC_MUTE("CD Playback Switch", 0x15, 0x0, HDA_OUTPUT),
520         HDA_CODEC_VOLUME("Line Playback Volume", 0x17, 0x0, HDA_OUTPUT),
521         HDA_CODEC_MUTE("Line Playback Switch", 0x17, 0x0, HDA_OUTPUT),
522         HDA_CODEC_VOLUME("Aux Playback Volume", 0x16, 0x0, HDA_OUTPUT),
523         HDA_CODEC_MUTE("Aux Playback Switch", 0x16, 0x0, HDA_OUTPUT),
524         HDA_CODEC_VOLUME("Mic Playback Volume", 0x13, 0x0, HDA_OUTPUT),
525         HDA_CODEC_MUTE("Mic Playback Switch", 0x13, 0x0, HDA_OUTPUT),
526         HDA_CODEC_VOLUME("Mic Boost", 0x0f, 0x0, HDA_OUTPUT),
527         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x18, 0x0, HDA_OUTPUT),
528         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x18, 0x0, HDA_OUTPUT),
529         HDA_CODEC_VOLUME("Mono Playback Volume", 0x1e, 0x0, HDA_OUTPUT),
530         HDA_CODEC_MUTE("Mono Playback Switch", 0x1e, 0x0, HDA_OUTPUT),
531         HDA_CODEC_VOLUME("Capture Volume", 0x12, 0x0, HDA_OUTPUT),
532         HDA_CODEC_MUTE("Capture Switch", 0x12, 0x0, HDA_OUTPUT),
533         {
534                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
535                 .name = "Capture Source",
536                 .info = ad198x_mux_enum_info,
537                 .get = ad198x_mux_enum_get,
538                 .put = ad198x_mux_enum_put,
539         },
540         HDA_CODEC_MUTE("Stereo Downmix Switch", 0x09, 0x0, HDA_OUTPUT),
541         { } /* end */
542 };
543
544 /* additional mixers for 3stack mode */
545 static struct snd_kcontrol_new ad1986a_3st_mixers[] = {
546         {
547                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
548                 .name = "Channel Mode",
549                 .info = ad198x_ch_mode_info,
550                 .get = ad198x_ch_mode_get,
551                 .put = ad198x_ch_mode_put,
552         },
553         { } /* end */
554 };
555
556 /* laptop model - 2ch only */
557 static hda_nid_t ad1986a_laptop_dac_nids[1] = { AD1986A_FRONT_DAC };
558
559 /* master controls both pins 0x1a and 0x1b */
560 static struct hda_bind_ctls ad1986a_laptop_master_vol = {
561         .ops = &snd_hda_bind_vol,
562         .values = {
563                 HDA_COMPOSE_AMP_VAL(0x1a, 3, 0, HDA_OUTPUT),
564                 HDA_COMPOSE_AMP_VAL(0x1b, 3, 0, HDA_OUTPUT),
565                 0,
566         },
567 };
568
569 static struct hda_bind_ctls ad1986a_laptop_master_sw = {
570         .ops = &snd_hda_bind_sw,
571         .values = {
572                 HDA_COMPOSE_AMP_VAL(0x1a, 3, 0, HDA_OUTPUT),
573                 HDA_COMPOSE_AMP_VAL(0x1b, 3, 0, HDA_OUTPUT),
574                 0,
575         },
576 };
577
578 static struct snd_kcontrol_new ad1986a_laptop_mixers[] = {
579         HDA_CODEC_VOLUME("PCM Playback Volume", 0x03, 0x0, HDA_OUTPUT),
580         HDA_CODEC_MUTE("PCM Playback Switch", 0x03, 0x0, HDA_OUTPUT),
581         HDA_BIND_VOL("Master Playback Volume", &ad1986a_laptop_master_vol),
582         HDA_BIND_SW("Master Playback Switch", &ad1986a_laptop_master_sw),
583         HDA_CODEC_VOLUME("CD Playback Volume", 0x15, 0x0, HDA_OUTPUT),
584         HDA_CODEC_MUTE("CD Playback Switch", 0x15, 0x0, HDA_OUTPUT),
585         HDA_CODEC_VOLUME("Line Playback Volume", 0x17, 0x0, HDA_OUTPUT),
586         HDA_CODEC_MUTE("Line Playback Switch", 0x17, 0x0, HDA_OUTPUT),
587         HDA_CODEC_VOLUME("Aux Playback Volume", 0x16, 0x0, HDA_OUTPUT),
588         HDA_CODEC_MUTE("Aux Playback Switch", 0x16, 0x0, HDA_OUTPUT),
589         HDA_CODEC_VOLUME("Mic Playback Volume", 0x13, 0x0, HDA_OUTPUT),
590         HDA_CODEC_MUTE("Mic Playback Switch", 0x13, 0x0, HDA_OUTPUT),
591         HDA_CODEC_VOLUME("Mic Boost", 0x0f, 0x0, HDA_OUTPUT),
592         /* HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x18, 0x0, HDA_OUTPUT),
593            HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x18, 0x0, HDA_OUTPUT),
594            HDA_CODEC_VOLUME("Mono Playback Volume", 0x1e, 0x0, HDA_OUTPUT),
595            HDA_CODEC_MUTE("Mono Playback Switch", 0x1e, 0x0, HDA_OUTPUT), */
596         HDA_CODEC_VOLUME("Capture Volume", 0x12, 0x0, HDA_OUTPUT),
597         HDA_CODEC_MUTE("Capture Switch", 0x12, 0x0, HDA_OUTPUT),
598         {
599                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
600                 .name = "Capture Source",
601                 .info = ad198x_mux_enum_info,
602                 .get = ad198x_mux_enum_get,
603                 .put = ad198x_mux_enum_put,
604         },
605         { } /* end */
606 };
607
608 /* laptop-eapd model - 2ch only */
609
610 static struct hda_input_mux ad1986a_laptop_eapd_capture_source = {
611         .num_items = 3,
612         .items = {
613                 { "Mic", 0x0 },
614                 { "Internal Mic", 0x4 },
615                 { "Mix", 0x5 },
616         },
617 };
618
619 static struct hda_input_mux ad1986a_automic_capture_source = {
620         .num_items = 2,
621         .items = {
622                 { "Mic", 0x0 },
623                 { "Mix", 0x5 },
624         },
625 };
626
627 static struct snd_kcontrol_new ad1986a_laptop_eapd_mixers[] = {
628         HDA_BIND_VOL("Master Playback Volume", &ad1986a_laptop_master_vol),
629         HDA_BIND_SW("Master Playback Switch", &ad1986a_laptop_master_sw),
630         HDA_CODEC_VOLUME("PCM Playback Volume", 0x03, 0x0, HDA_OUTPUT),
631         HDA_CODEC_MUTE("PCM Playback Switch", 0x03, 0x0, HDA_OUTPUT),
632         HDA_CODEC_VOLUME("Mic Playback Volume", 0x13, 0x0, HDA_OUTPUT),
633         HDA_CODEC_MUTE("Mic Playback Switch", 0x13, 0x0, HDA_OUTPUT),
634         HDA_CODEC_VOLUME("Mic Boost", 0x0f, 0x0, HDA_OUTPUT),
635         HDA_CODEC_VOLUME("Capture Volume", 0x12, 0x0, HDA_OUTPUT),
636         HDA_CODEC_MUTE("Capture Switch", 0x12, 0x0, HDA_OUTPUT),
637         {
638                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
639                 .name = "Capture Source",
640                 .info = ad198x_mux_enum_info,
641                 .get = ad198x_mux_enum_get,
642                 .put = ad198x_mux_enum_put,
643         },
644         {
645                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
646                 .name = "External Amplifier",
647                 .info = ad198x_eapd_info,
648                 .get = ad198x_eapd_get,
649                 .put = ad198x_eapd_put,
650                 .private_value = 0x1b | (1 << 8), /* port-D, inversed */
651         },
652         { } /* end */
653 };
654
655 /* re-connect the mic boost input according to the jack sensing */
656 static void ad1986a_automic(struct hda_codec *codec)
657 {
658         unsigned int present;
659         present = snd_hda_codec_read(codec, 0x1f, 0, AC_VERB_GET_PIN_SENSE, 0);
660         /* 0 = 0x1f, 2 = 0x1d, 4 = mixed */
661         snd_hda_codec_write(codec, 0x0f, 0, AC_VERB_SET_CONNECT_SEL,
662                             (present & AC_PINSENSE_PRESENCE) ? 0 : 2);
663 }
664
665 #define AD1986A_MIC_EVENT               0x36
666
667 static void ad1986a_automic_unsol_event(struct hda_codec *codec,
668                                             unsigned int res)
669 {
670         if ((res >> 26) != AD1986A_MIC_EVENT)
671                 return;
672         ad1986a_automic(codec);
673 }
674
675 static int ad1986a_automic_init(struct hda_codec *codec)
676 {
677         ad198x_init(codec);
678         ad1986a_automic(codec);
679         return 0;
680 }
681
682 /* laptop-automute - 2ch only */
683
684 static void ad1986a_update_hp(struct hda_codec *codec)
685 {
686         struct ad198x_spec *spec = codec->spec;
687         unsigned int mute;
688
689         if (spec->jack_present)
690                 mute = HDA_AMP_MUTE; /* mute internal speaker */
691         else
692                 /* unmute internal speaker if necessary */
693                 mute = snd_hda_codec_amp_read(codec, 0x1a, 0, HDA_OUTPUT, 0);
694         snd_hda_codec_amp_stereo(codec, 0x1b, HDA_OUTPUT, 0,
695                                  HDA_AMP_MUTE, mute);
696 }
697
698 static void ad1986a_hp_automute(struct hda_codec *codec)
699 {
700         struct ad198x_spec *spec = codec->spec;
701         unsigned int present;
702
703         present = snd_hda_codec_read(codec, 0x1a, 0, AC_VERB_GET_PIN_SENSE, 0);
704         /* Lenovo N100 seems to report the reversed bit for HP jack-sensing */
705         spec->jack_present = !(present & 0x80000000);
706         ad1986a_update_hp(codec);
707 }
708
709 #define AD1986A_HP_EVENT                0x37
710
711 static void ad1986a_hp_unsol_event(struct hda_codec *codec, unsigned int res)
712 {
713         if ((res >> 26) != AD1986A_HP_EVENT)
714                 return;
715         ad1986a_hp_automute(codec);
716 }
717
718 static int ad1986a_hp_init(struct hda_codec *codec)
719 {
720         ad198x_init(codec);
721         ad1986a_hp_automute(codec);
722         return 0;
723 }
724
725 /* bind hp and internal speaker mute (with plug check) */
726 static int ad1986a_hp_master_sw_put(struct snd_kcontrol *kcontrol,
727                                     struct snd_ctl_elem_value *ucontrol)
728 {
729         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
730         long *valp = ucontrol->value.integer.value;
731         int change;
732
733         change = snd_hda_codec_amp_update(codec, 0x1a, 0, HDA_OUTPUT, 0,
734                                           HDA_AMP_MUTE,
735                                           valp[0] ? 0 : HDA_AMP_MUTE);
736         change |= snd_hda_codec_amp_update(codec, 0x1a, 1, HDA_OUTPUT, 0,
737                                            HDA_AMP_MUTE,
738                                            valp[1] ? 0 : HDA_AMP_MUTE);
739         if (change)
740                 ad1986a_update_hp(codec);
741         return change;
742 }
743
744 static struct snd_kcontrol_new ad1986a_laptop_automute_mixers[] = {
745         HDA_BIND_VOL("Master Playback Volume", &ad1986a_laptop_master_vol),
746         {
747                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
748                 .name = "Master Playback Switch",
749                 .info = snd_hda_mixer_amp_switch_info,
750                 .get = snd_hda_mixer_amp_switch_get,
751                 .put = ad1986a_hp_master_sw_put,
752                 .private_value = HDA_COMPOSE_AMP_VAL(0x1a, 3, 0, HDA_OUTPUT),
753         },
754         HDA_CODEC_VOLUME("PCM Playback Volume", 0x03, 0x0, HDA_OUTPUT),
755         HDA_CODEC_MUTE("PCM Playback Switch", 0x03, 0x0, HDA_OUTPUT),
756         HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x17, 0x0, HDA_OUTPUT),
757         HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x17, 0x0, HDA_OUTPUT),
758         HDA_CODEC_VOLUME("Mic Playback Volume", 0x13, 0x0, HDA_OUTPUT),
759         HDA_CODEC_MUTE("Mic Playback Switch", 0x13, 0x0, HDA_OUTPUT),
760         HDA_CODEC_VOLUME("Mic Boost", 0x0f, 0x0, HDA_OUTPUT),
761         HDA_CODEC_VOLUME("Beep Playback Volume", 0x18, 0x0, HDA_OUTPUT),
762         HDA_CODEC_MUTE("Beep Playback Switch", 0x18, 0x0, HDA_OUTPUT),
763         HDA_CODEC_VOLUME("Capture Volume", 0x12, 0x0, HDA_OUTPUT),
764         HDA_CODEC_MUTE("Capture Switch", 0x12, 0x0, HDA_OUTPUT),
765         {
766                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
767                 .name = "Capture Source",
768                 .info = ad198x_mux_enum_info,
769                 .get = ad198x_mux_enum_get,
770                 .put = ad198x_mux_enum_put,
771         },
772         {
773                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
774                 .name = "External Amplifier",
775                 .info = ad198x_eapd_info,
776                 .get = ad198x_eapd_get,
777                 .put = ad198x_eapd_put,
778                 .private_value = 0x1b | (1 << 8), /* port-D, inversed */
779         },
780         { } /* end */
781 };
782
783 /*
784  * initialization verbs
785  */
786 static struct hda_verb ad1986a_init_verbs[] = {
787         /* Front, Surround, CLFE DAC; mute as default */
788         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
789         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
790         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
791         /* Downmix - off */
792         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
793         /* HP, Line-Out, Surround, CLFE selectors */
794         {0x0a, AC_VERB_SET_CONNECT_SEL, 0x0},
795         {0x0b, AC_VERB_SET_CONNECT_SEL, 0x0},
796         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x0},
797         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x0},
798         /* Mono selector */
799         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x0},
800         /* Mic selector: Mic 1/2 pin */
801         {0x0f, AC_VERB_SET_CONNECT_SEL, 0x0},
802         /* Line-in selector: Line-in */
803         {0x10, AC_VERB_SET_CONNECT_SEL, 0x0},
804         /* Mic 1/2 swap */
805         {0x11, AC_VERB_SET_CONNECT_SEL, 0x0},
806         /* Record selector: mic */
807         {0x12, AC_VERB_SET_CONNECT_SEL, 0x0},
808         /* Mic, Phone, CD, Aux, Line-In amp; mute as default */
809         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
810         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
811         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
812         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
813         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
814         /* PC beep */
815         {0x18, AC_VERB_SET_CONNECT_SEL, 0x0},
816         /* HP, Line-Out, Surround, CLFE, Mono pins; mute as default */
817         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
818         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
819         {0x1c, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
820         {0x1d, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
821         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
822         /* HP Pin */
823         {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0 },
824         /* Front, Surround, CLFE Pins */
825         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
826         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
827         {0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
828         /* Mono Pin */
829         {0x1e, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
830         /* Mic Pin */
831         {0x1f, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
832         /* Line, Aux, CD, Beep-In Pin */
833         {0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
834         {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
835         {0x22, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
836         {0x23, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
837         {0x24, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
838         { } /* end */
839 };
840
841 static struct hda_verb ad1986a_ch2_init[] = {
842         /* Surround out -> Line In */
843         { 0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
844         /* Line-in selectors */
845         { 0x10, AC_VERB_SET_CONNECT_SEL, 0x1 },
846         /* CLFE -> Mic in */
847         { 0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
848         /* Mic selector, mix C/LFE (backmic) and Mic (frontmic) */
849         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x4 },
850         { } /* end */
851 };
852
853 static struct hda_verb ad1986a_ch4_init[] = {
854         /* Surround out -> Surround */
855         { 0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
856         { 0x10, AC_VERB_SET_CONNECT_SEL, 0x0 },
857         /* CLFE -> Mic in */
858         { 0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
859         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x4 },
860         { } /* end */
861 };
862
863 static struct hda_verb ad1986a_ch6_init[] = {
864         /* Surround out -> Surround out */
865         { 0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
866         { 0x10, AC_VERB_SET_CONNECT_SEL, 0x0 },
867         /* CLFE -> CLFE */
868         { 0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
869         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x0 },
870         { } /* end */
871 };
872
873 static struct hda_channel_mode ad1986a_modes[3] = {
874         { 2, ad1986a_ch2_init },
875         { 4, ad1986a_ch4_init },
876         { 6, ad1986a_ch6_init },
877 };
878
879 /* eapd initialization */
880 static struct hda_verb ad1986a_eapd_init_verbs[] = {
881         {0x1b, AC_VERB_SET_EAPD_BTLENABLE, 0x00 },
882         {}
883 };
884
885 static struct hda_verb ad1986a_automic_verbs[] = {
886         {0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
887         {0x1f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
888         /*{0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},*/
889         {0x0f, AC_VERB_SET_CONNECT_SEL, 0x0},
890         {0x1f, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1986A_MIC_EVENT},
891         {}
892 };
893
894 /* Ultra initialization */
895 static struct hda_verb ad1986a_ultra_init[] = {
896         /* eapd initialization */
897         { 0x1b, AC_VERB_SET_EAPD_BTLENABLE, 0x00 },
898         /* CLFE -> Mic in */
899         { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x2 },
900         { 0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
901         { 0x1d, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080 },
902         { } /* end */
903 };
904
905 /* pin sensing on HP jack */
906 static struct hda_verb ad1986a_hp_init_verbs[] = {
907         {0x1a, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1986A_HP_EVENT},
908         {}
909 };
910
911
912 /* models */
913 enum {
914         AD1986A_6STACK,
915         AD1986A_3STACK,
916         AD1986A_LAPTOP,
917         AD1986A_LAPTOP_EAPD,
918         AD1986A_LAPTOP_AUTOMUTE,
919         AD1986A_ULTRA,
920         AD1986A_MODELS
921 };
922
923 static const char *ad1986a_models[AD1986A_MODELS] = {
924         [AD1986A_6STACK]        = "6stack",
925         [AD1986A_3STACK]        = "3stack",
926         [AD1986A_LAPTOP]        = "laptop",
927         [AD1986A_LAPTOP_EAPD]   = "laptop-eapd",
928         [AD1986A_LAPTOP_AUTOMUTE] = "laptop-automute",
929         [AD1986A_ULTRA]         = "ultra",
930 };
931
932 static struct snd_pci_quirk ad1986a_cfg_tbl[] = {
933         SND_PCI_QUIRK(0x103c, 0x30af, "HP B2800", AD1986A_LAPTOP_EAPD),
934         SND_PCI_QUIRK(0x1043, 0x1153, "ASUS M9", AD1986A_LAPTOP_EAPD),
935         SND_PCI_QUIRK(0x1043, 0x11f7, "ASUS U5A", AD1986A_LAPTOP_EAPD),
936         SND_PCI_QUIRK(0x1043, 0x1213, "ASUS A6J", AD1986A_LAPTOP_EAPD),
937         SND_PCI_QUIRK(0x1043, 0x1263, "ASUS U5F", AD1986A_LAPTOP_EAPD),
938         SND_PCI_QUIRK(0x1043, 0x1297, "ASUS Z62F", AD1986A_LAPTOP_EAPD),
939         SND_PCI_QUIRK(0x1043, 0x12b3, "ASUS V1j", AD1986A_LAPTOP_EAPD),
940         SND_PCI_QUIRK(0x1043, 0x1302, "ASUS W3j", AD1986A_LAPTOP_EAPD),
941         SND_PCI_QUIRK(0x1043, 0x1443, "ASUS VX1", AD1986A_LAPTOP),
942         SND_PCI_QUIRK(0x1043, 0x1447, "ASUS A8J", AD1986A_3STACK),
943         SND_PCI_QUIRK(0x1043, 0x817f, "ASUS P5", AD1986A_3STACK),
944         SND_PCI_QUIRK(0x1043, 0x818f, "ASUS P5", AD1986A_LAPTOP),
945         SND_PCI_QUIRK(0x1043, 0x81b3, "ASUS P5", AD1986A_3STACK),
946         SND_PCI_QUIRK(0x1043, 0x81cb, "ASUS M2N", AD1986A_3STACK),
947         SND_PCI_QUIRK(0x1043, 0x8234, "ASUS M2N", AD1986A_3STACK),
948         SND_PCI_QUIRK(0x10de, 0xcb84, "ASUS A8N-VM", AD1986A_3STACK),
949         SND_PCI_QUIRK(0x1179, 0xff40, "Toshiba", AD1986A_LAPTOP_EAPD),
950         SND_PCI_QUIRK(0x144d, 0xb03c, "Samsung R55", AD1986A_3STACK),
951         SND_PCI_QUIRK(0x144d, 0xc01e, "FSC V2060", AD1986A_LAPTOP),
952         SND_PCI_QUIRK(0x144d, 0xc023, "Samsung X60", AD1986A_LAPTOP_EAPD),
953         SND_PCI_QUIRK(0x144d, 0xc024, "Samsung R65", AD1986A_LAPTOP_EAPD),
954         SND_PCI_QUIRK(0x144d, 0xc026, "Samsung X11", AD1986A_LAPTOP_EAPD),
955         SND_PCI_QUIRK(0x144d, 0xc027, "Samsung Q1", AD1986A_ULTRA),
956         SND_PCI_QUIRK(0x144d, 0xc504, "Samsung Q35", AD1986A_3STACK),
957         SND_PCI_QUIRK(0x17aa, 0x1011, "Lenovo M55", AD1986A_LAPTOP),
958         SND_PCI_QUIRK(0x17aa, 0x1017, "Lenovo A60", AD1986A_3STACK),
959         SND_PCI_QUIRK(0x17aa, 0x2066, "Lenovo N100", AD1986A_LAPTOP_AUTOMUTE),
960         SND_PCI_QUIRK(0x17c0, 0x2017, "Samsung M50", AD1986A_LAPTOP),
961         {}
962 };
963
964 #ifdef CONFIG_SND_HDA_POWER_SAVE
965 static struct hda_amp_list ad1986a_loopbacks[] = {
966         { 0x13, HDA_OUTPUT, 0 }, /* Mic */
967         { 0x14, HDA_OUTPUT, 0 }, /* Phone */
968         { 0x15, HDA_OUTPUT, 0 }, /* CD */
969         { 0x16, HDA_OUTPUT, 0 }, /* Aux */
970         { 0x17, HDA_OUTPUT, 0 }, /* Line */
971         { } /* end */
972 };
973 #endif
974
975 static int is_jack_available(struct hda_codec *codec, hda_nid_t nid)
976 {
977         unsigned int conf = snd_hda_codec_read(codec, nid, 0,
978                                                AC_VERB_GET_CONFIG_DEFAULT, 0);
979         return get_defcfg_connect(conf) != AC_JACK_PORT_NONE;
980 }
981
982 static int patch_ad1986a(struct hda_codec *codec)
983 {
984         struct ad198x_spec *spec;
985         int board_config;
986
987         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
988         if (spec == NULL)
989                 return -ENOMEM;
990
991         codec->spec = spec;
992
993         spec->multiout.max_channels = 6;
994         spec->multiout.num_dacs = ARRAY_SIZE(ad1986a_dac_nids);
995         spec->multiout.dac_nids = ad1986a_dac_nids;
996         spec->multiout.dig_out_nid = AD1986A_SPDIF_OUT;
997         spec->num_adc_nids = 1;
998         spec->adc_nids = ad1986a_adc_nids;
999         spec->capsrc_nids = ad1986a_capsrc_nids;
1000         spec->input_mux = &ad1986a_capture_source;
1001         spec->num_mixers = 1;
1002         spec->mixers[0] = ad1986a_mixers;
1003         spec->num_init_verbs = 1;
1004         spec->init_verbs[0] = ad1986a_init_verbs;
1005 #ifdef CONFIG_SND_HDA_POWER_SAVE
1006         spec->loopback.amplist = ad1986a_loopbacks;
1007 #endif
1008         spec->vmaster_nid = 0x1b;
1009
1010         codec->patch_ops = ad198x_patch_ops;
1011
1012         /* override some parameters */
1013         board_config = snd_hda_check_board_config(codec, AD1986A_MODELS,
1014                                                   ad1986a_models,
1015                                                   ad1986a_cfg_tbl);
1016         switch (board_config) {
1017         case AD1986A_3STACK:
1018                 spec->num_mixers = 2;
1019                 spec->mixers[1] = ad1986a_3st_mixers;
1020                 spec->num_init_verbs = 2;
1021                 spec->init_verbs[1] = ad1986a_ch2_init;
1022                 spec->channel_mode = ad1986a_modes;
1023                 spec->num_channel_mode = ARRAY_SIZE(ad1986a_modes);
1024                 spec->need_dac_fix = 1;
1025                 spec->multiout.max_channels = 2;
1026                 spec->multiout.num_dacs = 1;
1027                 break;
1028         case AD1986A_LAPTOP:
1029                 spec->mixers[0] = ad1986a_laptop_mixers;
1030                 spec->multiout.max_channels = 2;
1031                 spec->multiout.num_dacs = 1;
1032                 spec->multiout.dac_nids = ad1986a_laptop_dac_nids;
1033                 break;
1034         case AD1986A_LAPTOP_EAPD:
1035                 spec->mixers[0] = ad1986a_laptop_eapd_mixers;
1036                 spec->num_init_verbs = 3;
1037                 spec->init_verbs[1] = ad1986a_eapd_init_verbs;
1038                 spec->init_verbs[2] = ad1986a_automic_verbs;
1039                 spec->multiout.max_channels = 2;
1040                 spec->multiout.num_dacs = 1;
1041                 spec->multiout.dac_nids = ad1986a_laptop_dac_nids;
1042                 if (!is_jack_available(codec, 0x25))
1043                         spec->multiout.dig_out_nid = 0;
1044                 spec->input_mux = &ad1986a_automic_capture_source;
1045                 codec->patch_ops.unsol_event = ad1986a_automic_unsol_event;
1046                 codec->patch_ops.init = ad1986a_automic_init;
1047                 break;
1048         case AD1986A_LAPTOP_AUTOMUTE:
1049                 spec->mixers[0] = ad1986a_laptop_automute_mixers;
1050                 spec->num_init_verbs = 3;
1051                 spec->init_verbs[1] = ad1986a_eapd_init_verbs;
1052                 spec->init_verbs[2] = ad1986a_hp_init_verbs;
1053                 spec->multiout.max_channels = 2;
1054                 spec->multiout.num_dacs = 1;
1055                 spec->multiout.dac_nids = ad1986a_laptop_dac_nids;
1056                 if (!is_jack_available(codec, 0x25))
1057                         spec->multiout.dig_out_nid = 0;
1058                 spec->input_mux = &ad1986a_laptop_eapd_capture_source;
1059                 codec->patch_ops.unsol_event = ad1986a_hp_unsol_event;
1060                 codec->patch_ops.init = ad1986a_hp_init;
1061                 break;
1062         case AD1986A_ULTRA:
1063                 spec->mixers[0] = ad1986a_laptop_eapd_mixers;
1064                 spec->num_init_verbs = 2;
1065                 spec->init_verbs[1] = ad1986a_ultra_init;
1066                 spec->multiout.max_channels = 2;
1067                 spec->multiout.num_dacs = 1;
1068                 spec->multiout.dac_nids = ad1986a_laptop_dac_nids;
1069                 spec->multiout.dig_out_nid = 0;
1070                 break;
1071         }
1072
1073         /* AD1986A has a hardware problem that it can't share a stream
1074          * with multiple output pins.  The copy of front to surrounds
1075          * causes noisy or silent outputs at a certain timing, e.g.
1076          * changing the volume.
1077          * So, let's disable the shared stream.
1078          */
1079         spec->multiout.no_share_stream = 1;
1080
1081         return 0;
1082 }
1083
1084 /*
1085  * AD1983 specific
1086  */
1087
1088 #define AD1983_SPDIF_OUT        0x02
1089 #define AD1983_DAC              0x03
1090 #define AD1983_ADC              0x04
1091
1092 static hda_nid_t ad1983_dac_nids[1] = { AD1983_DAC };
1093 static hda_nid_t ad1983_adc_nids[1] = { AD1983_ADC };
1094 static hda_nid_t ad1983_capsrc_nids[1] = { 0x15 };
1095
1096 static struct hda_input_mux ad1983_capture_source = {
1097         .num_items = 4,
1098         .items = {
1099                 { "Mic", 0x0 },
1100                 { "Line", 0x1 },
1101                 { "Mix", 0x2 },
1102                 { "Mix Mono", 0x3 },
1103         },
1104 };
1105
1106 /*
1107  * SPDIF playback route
1108  */
1109 static int ad1983_spdif_route_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
1110 {
1111         static char *texts[] = { "PCM", "ADC" };
1112
1113         uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1114         uinfo->count = 1;
1115         uinfo->value.enumerated.items = 2;
1116         if (uinfo->value.enumerated.item > 1)
1117                 uinfo->value.enumerated.item = 1;
1118         strcpy(uinfo->value.enumerated.name, texts[uinfo->value.enumerated.item]);
1119         return 0;
1120 }
1121
1122 static int ad1983_spdif_route_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1123 {
1124         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1125         struct ad198x_spec *spec = codec->spec;
1126
1127         ucontrol->value.enumerated.item[0] = spec->spdif_route;
1128         return 0;
1129 }
1130
1131 static int ad1983_spdif_route_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
1132 {
1133         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1134         struct ad198x_spec *spec = codec->spec;
1135
1136         if (ucontrol->value.enumerated.item[0] > 1)
1137                 return -EINVAL;
1138         if (spec->spdif_route != ucontrol->value.enumerated.item[0]) {
1139                 spec->spdif_route = ucontrol->value.enumerated.item[0];
1140                 snd_hda_codec_write_cache(codec, spec->multiout.dig_out_nid, 0,
1141                                           AC_VERB_SET_CONNECT_SEL,
1142                                           spec->spdif_route);
1143                 return 1;
1144         }
1145         return 0;
1146 }
1147
1148 static struct snd_kcontrol_new ad1983_mixers[] = {
1149         HDA_CODEC_VOLUME("Front Playback Volume", 0x05, 0x0, HDA_OUTPUT),
1150         HDA_CODEC_MUTE("Front Playback Switch", 0x05, 0x0, HDA_OUTPUT),
1151         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x06, 0x0, HDA_OUTPUT),
1152         HDA_CODEC_MUTE("Headphone Playback Switch", 0x06, 0x0, HDA_OUTPUT),
1153         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x07, 1, 0x0, HDA_OUTPUT),
1154         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x07, 1, 0x0, HDA_OUTPUT),
1155         HDA_CODEC_VOLUME("PCM Playback Volume", 0x11, 0x0, HDA_OUTPUT),
1156         HDA_CODEC_MUTE("PCM Playback Switch", 0x11, 0x0, HDA_OUTPUT),
1157         HDA_CODEC_VOLUME("Mic Playback Volume", 0x12, 0x0, HDA_OUTPUT),
1158         HDA_CODEC_MUTE("Mic Playback Switch", 0x12, 0x0, HDA_OUTPUT),
1159         HDA_CODEC_VOLUME("Line Playback Volume", 0x13, 0x0, HDA_OUTPUT),
1160         HDA_CODEC_MUTE("Line Playback Switch", 0x13, 0x0, HDA_OUTPUT),
1161         HDA_CODEC_VOLUME_MONO("PC Speaker Playback Volume", 0x10, 1, 0x0, HDA_OUTPUT),
1162         HDA_CODEC_MUTE_MONO("PC Speaker Playback Switch", 0x10, 1, 0x0, HDA_OUTPUT),
1163         HDA_CODEC_VOLUME("Mic Boost", 0x0c, 0x0, HDA_OUTPUT),
1164         HDA_CODEC_VOLUME("Capture Volume", 0x15, 0x0, HDA_OUTPUT),
1165         HDA_CODEC_MUTE("Capture Switch", 0x15, 0x0, HDA_OUTPUT),
1166         {
1167                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1168                 .name = "Capture Source",
1169                 .info = ad198x_mux_enum_info,
1170                 .get = ad198x_mux_enum_get,
1171                 .put = ad198x_mux_enum_put,
1172         },
1173         {
1174                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1175                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
1176                 .info = ad1983_spdif_route_info,
1177                 .get = ad1983_spdif_route_get,
1178                 .put = ad1983_spdif_route_put,
1179         },
1180         { } /* end */
1181 };
1182
1183 static struct hda_verb ad1983_init_verbs[] = {
1184         /* Front, HP, Mono; mute as default */
1185         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1186         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1187         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1188         /* Beep, PCM, Mic, Line-In: mute */
1189         {0x10, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1190         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1191         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1192         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1193         /* Front, HP selectors; from Mix */
1194         {0x05, AC_VERB_SET_CONNECT_SEL, 0x01},
1195         {0x06, AC_VERB_SET_CONNECT_SEL, 0x01},
1196         /* Mono selector; from Mix */
1197         {0x0b, AC_VERB_SET_CONNECT_SEL, 0x03},
1198         /* Mic selector; Mic */
1199         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x0},
1200         /* Line-in selector: Line-in */
1201         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x0},
1202         /* Mic boost: 0dB */
1203         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1204         /* Record selector: mic */
1205         {0x15, AC_VERB_SET_CONNECT_SEL, 0x0},
1206         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1207         /* SPDIF route: PCM */
1208         {0x02, AC_VERB_SET_CONNECT_SEL, 0x0},
1209         /* Front Pin */
1210         {0x05, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
1211         /* HP Pin */
1212         {0x06, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0 },
1213         /* Mono Pin */
1214         {0x07, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
1215         /* Mic Pin */
1216         {0x08, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
1217         /* Line Pin */
1218         {0x09, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
1219         { } /* end */
1220 };
1221
1222 #ifdef CONFIG_SND_HDA_POWER_SAVE
1223 static struct hda_amp_list ad1983_loopbacks[] = {
1224         { 0x12, HDA_OUTPUT, 0 }, /* Mic */
1225         { 0x13, HDA_OUTPUT, 0 }, /* Line */
1226         { } /* end */
1227 };
1228 #endif
1229
1230 static int patch_ad1983(struct hda_codec *codec)
1231 {
1232         struct ad198x_spec *spec;
1233
1234         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
1235         if (spec == NULL)
1236                 return -ENOMEM;
1237
1238         codec->spec = spec;
1239
1240         spec->multiout.max_channels = 2;
1241         spec->multiout.num_dacs = ARRAY_SIZE(ad1983_dac_nids);
1242         spec->multiout.dac_nids = ad1983_dac_nids;
1243         spec->multiout.dig_out_nid = AD1983_SPDIF_OUT;
1244         spec->num_adc_nids = 1;
1245         spec->adc_nids = ad1983_adc_nids;
1246         spec->capsrc_nids = ad1983_capsrc_nids;
1247         spec->input_mux = &ad1983_capture_source;
1248         spec->num_mixers = 1;
1249         spec->mixers[0] = ad1983_mixers;
1250         spec->num_init_verbs = 1;
1251         spec->init_verbs[0] = ad1983_init_verbs;
1252         spec->spdif_route = 0;
1253 #ifdef CONFIG_SND_HDA_POWER_SAVE
1254         spec->loopback.amplist = ad1983_loopbacks;
1255 #endif
1256         spec->vmaster_nid = 0x05;
1257
1258         codec->patch_ops = ad198x_patch_ops;
1259
1260         return 0;
1261 }
1262
1263
1264 /*
1265  * AD1981 HD specific
1266  */
1267
1268 #define AD1981_SPDIF_OUT        0x02
1269 #define AD1981_DAC              0x03
1270 #define AD1981_ADC              0x04
1271
1272 static hda_nid_t ad1981_dac_nids[1] = { AD1981_DAC };
1273 static hda_nid_t ad1981_adc_nids[1] = { AD1981_ADC };
1274 static hda_nid_t ad1981_capsrc_nids[1] = { 0x15 };
1275
1276 /* 0x0c, 0x09, 0x0e, 0x0f, 0x19, 0x05, 0x18, 0x17 */
1277 static struct hda_input_mux ad1981_capture_source = {
1278         .num_items = 7,
1279         .items = {
1280                 { "Front Mic", 0x0 },
1281                 { "Line", 0x1 },
1282                 { "Mix", 0x2 },
1283                 { "Mix Mono", 0x3 },
1284                 { "CD", 0x4 },
1285                 { "Mic", 0x6 },
1286                 { "Aux", 0x7 },
1287         },
1288 };
1289
1290 static struct snd_kcontrol_new ad1981_mixers[] = {
1291         HDA_CODEC_VOLUME("Front Playback Volume", 0x05, 0x0, HDA_OUTPUT),
1292         HDA_CODEC_MUTE("Front Playback Switch", 0x05, 0x0, HDA_OUTPUT),
1293         HDA_CODEC_VOLUME("Headphone Playback Volume", 0x06, 0x0, HDA_OUTPUT),
1294         HDA_CODEC_MUTE("Headphone Playback Switch", 0x06, 0x0, HDA_OUTPUT),
1295         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x07, 1, 0x0, HDA_OUTPUT),
1296         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x07, 1, 0x0, HDA_OUTPUT),
1297         HDA_CODEC_VOLUME("PCM Playback Volume", 0x11, 0x0, HDA_OUTPUT),
1298         HDA_CODEC_MUTE("PCM Playback Switch", 0x11, 0x0, HDA_OUTPUT),
1299         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x12, 0x0, HDA_OUTPUT),
1300         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x12, 0x0, HDA_OUTPUT),
1301         HDA_CODEC_VOLUME("Line Playback Volume", 0x13, 0x0, HDA_OUTPUT),
1302         HDA_CODEC_MUTE("Line Playback Switch", 0x13, 0x0, HDA_OUTPUT),
1303         HDA_CODEC_VOLUME("Aux Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
1304         HDA_CODEC_MUTE("Aux Playback Switch", 0x1b, 0x0, HDA_OUTPUT),
1305         HDA_CODEC_VOLUME("Mic Playback Volume", 0x1c, 0x0, HDA_OUTPUT),
1306         HDA_CODEC_MUTE("Mic Playback Switch", 0x1c, 0x0, HDA_OUTPUT),
1307         HDA_CODEC_VOLUME("CD Playback Volume", 0x1d, 0x0, HDA_OUTPUT),
1308         HDA_CODEC_MUTE("CD Playback Switch", 0x1d, 0x0, HDA_OUTPUT),
1309         HDA_CODEC_VOLUME_MONO("PC Speaker Playback Volume", 0x0d, 1, 0x0, HDA_OUTPUT),
1310         HDA_CODEC_MUTE_MONO("PC Speaker Playback Switch", 0x0d, 1, 0x0, HDA_OUTPUT),
1311         HDA_CODEC_VOLUME("Front Mic Boost", 0x08, 0x0, HDA_INPUT),
1312         HDA_CODEC_VOLUME("Mic Boost", 0x18, 0x0, HDA_INPUT),
1313         HDA_CODEC_VOLUME("Capture Volume", 0x15, 0x0, HDA_OUTPUT),
1314         HDA_CODEC_MUTE("Capture Switch", 0x15, 0x0, HDA_OUTPUT),
1315         {
1316                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1317                 .name = "Capture Source",
1318                 .info = ad198x_mux_enum_info,
1319                 .get = ad198x_mux_enum_get,
1320                 .put = ad198x_mux_enum_put,
1321         },
1322         /* identical with AD1983 */
1323         {
1324                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1325                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
1326                 .info = ad1983_spdif_route_info,
1327                 .get = ad1983_spdif_route_get,
1328                 .put = ad1983_spdif_route_put,
1329         },
1330         { } /* end */
1331 };
1332
1333 static struct hda_verb ad1981_init_verbs[] = {
1334         /* Front, HP, Mono; mute as default */
1335         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1336         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1337         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1338         /* Beep, PCM, Front Mic, Line, Rear Mic, Aux, CD-In: mute */
1339         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1340         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1341         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1342         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1343         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1344         {0x1c, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1345         {0x1d, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1346         /* Front, HP selectors; from Mix */
1347         {0x05, AC_VERB_SET_CONNECT_SEL, 0x01},
1348         {0x06, AC_VERB_SET_CONNECT_SEL, 0x01},
1349         /* Mono selector; from Mix */
1350         {0x0b, AC_VERB_SET_CONNECT_SEL, 0x03},
1351         /* Mic Mixer; select Front Mic */
1352         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1353         {0x1f, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1354         /* Mic boost: 0dB */
1355         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1356         {0x18, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1357         /* Record selector: Front mic */
1358         {0x15, AC_VERB_SET_CONNECT_SEL, 0x0},
1359         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1360         /* SPDIF route: PCM */
1361         {0x02, AC_VERB_SET_CONNECT_SEL, 0x0},
1362         /* Front Pin */
1363         {0x05, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
1364         /* HP Pin */
1365         {0x06, AC_VERB_SET_PIN_WIDGET_CONTROL, 0xc0 },
1366         /* Mono Pin */
1367         {0x07, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40 },
1368         /* Front & Rear Mic Pins */
1369         {0x08, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
1370         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x24 },
1371         /* Line Pin */
1372         {0x09, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20 },
1373         /* Digital Beep */
1374         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x00},
1375         /* Line-Out as Input: disabled */
1376         {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1377         { } /* end */
1378 };
1379
1380 #ifdef CONFIG_SND_HDA_POWER_SAVE
1381 static struct hda_amp_list ad1981_loopbacks[] = {
1382         { 0x12, HDA_OUTPUT, 0 }, /* Front Mic */
1383         { 0x13, HDA_OUTPUT, 0 }, /* Line */
1384         { 0x1b, HDA_OUTPUT, 0 }, /* Aux */
1385         { 0x1c, HDA_OUTPUT, 0 }, /* Mic */
1386         { 0x1d, HDA_OUTPUT, 0 }, /* CD */
1387         { } /* end */
1388 };
1389 #endif
1390
1391 /*
1392  * Patch for HP nx6320
1393  *
1394  * nx6320 uses EAPD in the reverse way - EAPD-on means the internal
1395  * speaker output enabled _and_ mute-LED off.
1396  */
1397
1398 #define AD1981_HP_EVENT         0x37
1399 #define AD1981_MIC_EVENT        0x38
1400
1401 static struct hda_verb ad1981_hp_init_verbs[] = {
1402         {0x05, AC_VERB_SET_EAPD_BTLENABLE, 0x00 }, /* default off */
1403         /* pin sensing on HP and Mic jacks */
1404         {0x06, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1981_HP_EVENT},
1405         {0x08, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1981_MIC_EVENT},
1406         {}
1407 };
1408
1409 /* turn on/off EAPD (+ mute HP) as a master switch */
1410 static int ad1981_hp_master_sw_put(struct snd_kcontrol *kcontrol,
1411                                    struct snd_ctl_elem_value *ucontrol)
1412 {
1413         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1414         struct ad198x_spec *spec = codec->spec;
1415
1416         if (! ad198x_eapd_put(kcontrol, ucontrol))
1417                 return 0;
1418         /* change speaker pin appropriately */
1419         snd_hda_codec_write(codec, 0x05, 0,
1420                             AC_VERB_SET_PIN_WIDGET_CONTROL,
1421                             spec->cur_eapd ? PIN_OUT : 0);
1422         /* toggle HP mute appropriately */
1423         snd_hda_codec_amp_stereo(codec, 0x06, HDA_OUTPUT, 0,
1424                                  HDA_AMP_MUTE,
1425                                  spec->cur_eapd ? 0 : HDA_AMP_MUTE);
1426         return 1;
1427 }
1428
1429 /* bind volumes of both NID 0x05 and 0x06 */
1430 static struct hda_bind_ctls ad1981_hp_bind_master_vol = {
1431         .ops = &snd_hda_bind_vol,
1432         .values = {
1433                 HDA_COMPOSE_AMP_VAL(0x05, 3, 0, HDA_OUTPUT),
1434                 HDA_COMPOSE_AMP_VAL(0x06, 3, 0, HDA_OUTPUT),
1435                 0
1436         },
1437 };
1438
1439 /* mute internal speaker if HP is plugged */
1440 static void ad1981_hp_automute(struct hda_codec *codec)
1441 {
1442         unsigned int present;
1443
1444         present = snd_hda_codec_read(codec, 0x06, 0,
1445                                      AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
1446         snd_hda_codec_amp_stereo(codec, 0x05, HDA_OUTPUT, 0,
1447                                  HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0);
1448 }
1449
1450 /* toggle input of built-in and mic jack appropriately */
1451 static void ad1981_hp_automic(struct hda_codec *codec)
1452 {
1453         static struct hda_verb mic_jack_on[] = {
1454                 {0x1f, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1455                 {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1456                 {}
1457         };
1458         static struct hda_verb mic_jack_off[] = {
1459                 {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, 0xb080},
1460                 {0x1f, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1461                 {}
1462         };
1463         unsigned int present;
1464
1465         present = snd_hda_codec_read(codec, 0x08, 0,
1466                                  AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
1467         if (present)
1468                 snd_hda_sequence_write(codec, mic_jack_on);
1469         else
1470                 snd_hda_sequence_write(codec, mic_jack_off);
1471 }
1472
1473 /* unsolicited event for HP jack sensing */
1474 static void ad1981_hp_unsol_event(struct hda_codec *codec,
1475                                   unsigned int res)
1476 {
1477         res >>= 26;
1478         switch (res) {
1479         case AD1981_HP_EVENT:
1480                 ad1981_hp_automute(codec);
1481                 break;
1482         case AD1981_MIC_EVENT:
1483                 ad1981_hp_automic(codec);
1484                 break;
1485         }
1486 }
1487
1488 static struct hda_input_mux ad1981_hp_capture_source = {
1489         .num_items = 3,
1490         .items = {
1491                 { "Mic", 0x0 },
1492                 { "Docking-Station", 0x1 },
1493                 { "Mix", 0x2 },
1494         },
1495 };
1496
1497 static struct snd_kcontrol_new ad1981_hp_mixers[] = {
1498         HDA_BIND_VOL("Master Playback Volume", &ad1981_hp_bind_master_vol),
1499         {
1500                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1501                 .name = "Master Playback Switch",
1502                 .info = ad198x_eapd_info,
1503                 .get = ad198x_eapd_get,
1504                 .put = ad1981_hp_master_sw_put,
1505                 .private_value = 0x05,
1506         },
1507         HDA_CODEC_VOLUME("PCM Playback Volume", 0x11, 0x0, HDA_OUTPUT),
1508         HDA_CODEC_MUTE("PCM Playback Switch", 0x11, 0x0, HDA_OUTPUT),
1509 #if 0
1510         /* FIXME: analog mic/line loopback doesn't work with my tests...
1511          *        (although recording is OK)
1512          */
1513         HDA_CODEC_VOLUME("Mic Playback Volume", 0x12, 0x0, HDA_OUTPUT),
1514         HDA_CODEC_MUTE("Mic Playback Switch", 0x12, 0x0, HDA_OUTPUT),
1515         HDA_CODEC_VOLUME("Docking-Station Playback Volume", 0x13, 0x0, HDA_OUTPUT),
1516         HDA_CODEC_MUTE("Docking-Station Playback Switch", 0x13, 0x0, HDA_OUTPUT),
1517         HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x1c, 0x0, HDA_OUTPUT),
1518         HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x1c, 0x0, HDA_OUTPUT),
1519         /* FIXME: does this laptop have analog CD connection? */
1520         HDA_CODEC_VOLUME("CD Playback Volume", 0x1d, 0x0, HDA_OUTPUT),
1521         HDA_CODEC_MUTE("CD Playback Switch", 0x1d, 0x0, HDA_OUTPUT),
1522 #endif
1523         HDA_CODEC_VOLUME("Mic Boost", 0x08, 0x0, HDA_INPUT),
1524         HDA_CODEC_VOLUME("Internal Mic Boost", 0x18, 0x0, HDA_INPUT),
1525         HDA_CODEC_VOLUME("Capture Volume", 0x15, 0x0, HDA_OUTPUT),
1526         HDA_CODEC_MUTE("Capture Switch", 0x15, 0x0, HDA_OUTPUT),
1527         {
1528                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1529                 .name = "Capture Source",
1530                 .info = ad198x_mux_enum_info,
1531                 .get = ad198x_mux_enum_get,
1532                 .put = ad198x_mux_enum_put,
1533         },
1534         { } /* end */
1535 };
1536
1537 /* initialize jack-sensing, too */
1538 static int ad1981_hp_init(struct hda_codec *codec)
1539 {
1540         ad198x_init(codec);
1541         ad1981_hp_automute(codec);
1542         ad1981_hp_automic(codec);
1543         return 0;
1544 }
1545
1546 /* configuration for Toshiba Laptops */
1547 static struct hda_verb ad1981_toshiba_init_verbs[] = {
1548         {0x05, AC_VERB_SET_EAPD_BTLENABLE, 0x01 }, /* default on */
1549         /* pin sensing on HP and Mic jacks */
1550         {0x06, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1981_HP_EVENT},
1551         {0x08, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1981_MIC_EVENT},
1552         {}
1553 };
1554
1555 static struct snd_kcontrol_new ad1981_toshiba_mixers[] = {
1556         HDA_CODEC_VOLUME("Amp Volume", 0x1a, 0x0, HDA_OUTPUT),
1557         HDA_CODEC_MUTE("Amp Switch", 0x1a, 0x0, HDA_OUTPUT),
1558         { }
1559 };
1560
1561 /* configuration for Lenovo Thinkpad T60 */
1562 static struct snd_kcontrol_new ad1981_thinkpad_mixers[] = {
1563         HDA_CODEC_VOLUME("Master Playback Volume", 0x05, 0x0, HDA_OUTPUT),
1564         HDA_CODEC_MUTE("Master Playback Switch", 0x05, 0x0, HDA_OUTPUT),
1565         HDA_CODEC_VOLUME("PCM Playback Volume", 0x11, 0x0, HDA_OUTPUT),
1566         HDA_CODEC_MUTE("PCM Playback Switch", 0x11, 0x0, HDA_OUTPUT),
1567         HDA_CODEC_VOLUME("Mic Playback Volume", 0x12, 0x0, HDA_OUTPUT),
1568         HDA_CODEC_MUTE("Mic Playback Switch", 0x12, 0x0, HDA_OUTPUT),
1569         HDA_CODEC_VOLUME("CD Playback Volume", 0x1d, 0x0, HDA_OUTPUT),
1570         HDA_CODEC_MUTE("CD Playback Switch", 0x1d, 0x0, HDA_OUTPUT),
1571         HDA_CODEC_VOLUME("Mic Boost", 0x08, 0x0, HDA_INPUT),
1572         HDA_CODEC_VOLUME("Capture Volume", 0x15, 0x0, HDA_OUTPUT),
1573         HDA_CODEC_MUTE("Capture Switch", 0x15, 0x0, HDA_OUTPUT),
1574         {
1575                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1576                 .name = "Capture Source",
1577                 .info = ad198x_mux_enum_info,
1578                 .get = ad198x_mux_enum_get,
1579                 .put = ad198x_mux_enum_put,
1580         },
1581         /* identical with AD1983 */
1582         {
1583                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1584                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
1585                 .info = ad1983_spdif_route_info,
1586                 .get = ad1983_spdif_route_get,
1587                 .put = ad1983_spdif_route_put,
1588         },
1589         { } /* end */
1590 };
1591
1592 static struct hda_input_mux ad1981_thinkpad_capture_source = {
1593         .num_items = 3,
1594         .items = {
1595                 { "Mic", 0x0 },
1596                 { "Mix", 0x2 },
1597                 { "CD", 0x4 },
1598         },
1599 };
1600
1601 /* models */
1602 enum {
1603         AD1981_BASIC,
1604         AD1981_HP,
1605         AD1981_THINKPAD,
1606         AD1981_TOSHIBA,
1607         AD1981_MODELS
1608 };
1609
1610 static const char *ad1981_models[AD1981_MODELS] = {
1611         [AD1981_HP]             = "hp",
1612         [AD1981_THINKPAD]       = "thinkpad",
1613         [AD1981_BASIC]          = "basic",
1614         [AD1981_TOSHIBA]        = "toshiba"
1615 };
1616
1617 static struct snd_pci_quirk ad1981_cfg_tbl[] = {
1618         SND_PCI_QUIRK(0x1014, 0x0597, "Lenovo Z60", AD1981_THINKPAD),
1619         SND_PCI_QUIRK(0x1014, 0x05b7, "Lenovo Z60m", AD1981_THINKPAD),
1620         /* All HP models */
1621         SND_PCI_QUIRK(0x103c, 0, "HP nx", AD1981_HP),
1622         SND_PCI_QUIRK(0x1179, 0x0001, "Toshiba U205", AD1981_TOSHIBA),
1623         /* Lenovo Thinkpad T60/X60/Z6xx */
1624         SND_PCI_QUIRK(0x17aa, 0, "Lenovo Thinkpad", AD1981_THINKPAD),
1625         /* HP nx6320 (reversed SSID, H/W bug) */
1626         SND_PCI_QUIRK(0x30b0, 0x103c, "HP nx6320", AD1981_HP),
1627         {}
1628 };
1629
1630 static int patch_ad1981(struct hda_codec *codec)
1631 {
1632         struct ad198x_spec *spec;
1633         int board_config;
1634
1635         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
1636         if (spec == NULL)
1637                 return -ENOMEM;
1638
1639         codec->spec = spec;
1640
1641         spec->multiout.max_channels = 2;
1642         spec->multiout.num_dacs = ARRAY_SIZE(ad1981_dac_nids);
1643         spec->multiout.dac_nids = ad1981_dac_nids;
1644         spec->multiout.dig_out_nid = AD1981_SPDIF_OUT;
1645         spec->num_adc_nids = 1;
1646         spec->adc_nids = ad1981_adc_nids;
1647         spec->capsrc_nids = ad1981_capsrc_nids;
1648         spec->input_mux = &ad1981_capture_source;
1649         spec->num_mixers = 1;
1650         spec->mixers[0] = ad1981_mixers;
1651         spec->num_init_verbs = 1;
1652         spec->init_verbs[0] = ad1981_init_verbs;
1653         spec->spdif_route = 0;
1654 #ifdef CONFIG_SND_HDA_POWER_SAVE
1655         spec->loopback.amplist = ad1981_loopbacks;
1656 #endif
1657         spec->vmaster_nid = 0x05;
1658
1659         codec->patch_ops = ad198x_patch_ops;
1660
1661         /* override some parameters */
1662         board_config = snd_hda_check_board_config(codec, AD1981_MODELS,
1663                                                   ad1981_models,
1664                                                   ad1981_cfg_tbl);
1665         switch (board_config) {
1666         case AD1981_HP:
1667                 spec->mixers[0] = ad1981_hp_mixers;
1668                 spec->num_init_verbs = 2;
1669                 spec->init_verbs[1] = ad1981_hp_init_verbs;
1670                 spec->multiout.dig_out_nid = 0;
1671                 spec->input_mux = &ad1981_hp_capture_source;
1672
1673                 codec->patch_ops.init = ad1981_hp_init;
1674                 codec->patch_ops.unsol_event = ad1981_hp_unsol_event;
1675                 break;
1676         case AD1981_THINKPAD:
1677                 spec->mixers[0] = ad1981_thinkpad_mixers;
1678                 spec->input_mux = &ad1981_thinkpad_capture_source;
1679                 break;
1680         case AD1981_TOSHIBA:
1681                 spec->mixers[0] = ad1981_hp_mixers;
1682                 spec->mixers[1] = ad1981_toshiba_mixers;
1683                 spec->num_init_verbs = 2;
1684                 spec->init_verbs[1] = ad1981_toshiba_init_verbs;
1685                 spec->multiout.dig_out_nid = 0;
1686                 spec->input_mux = &ad1981_hp_capture_source;
1687                 codec->patch_ops.init = ad1981_hp_init;
1688                 codec->patch_ops.unsol_event = ad1981_hp_unsol_event;
1689                 break;
1690         }
1691         return 0;
1692 }
1693
1694
1695 /*
1696  * AD1988
1697  *
1698  * Output pins and routes
1699  *
1700  *        Pin               Mix     Sel     DAC (*)
1701  * port-A 0x11 (mute/hp) <- 0x22 <- 0x37 <- 03/04/06
1702  * port-B 0x14 (mute/hp) <- 0x2b <- 0x30 <- 03/04/06
1703  * port-C 0x15 (mute)    <- 0x2c <- 0x31 <- 05/0a
1704  * port-D 0x12 (mute/hp) <- 0x29         <- 04
1705  * port-E 0x17 (mute/hp) <- 0x26 <- 0x32 <- 05/0a
1706  * port-F 0x16 (mute)    <- 0x2a         <- 06
1707  * port-G 0x24 (mute)    <- 0x27         <- 05
1708  * port-H 0x25 (mute)    <- 0x28         <- 0a
1709  * mono   0x13 (mute/amp)<- 0x1e <- 0x36 <- 03/04/06
1710  *
1711  * DAC0 = 03h, DAC1 = 04h, DAC2 = 05h, DAC3 = 06h, DAC4 = 0ah
1712  * (*) DAC2/3/4 are swapped to DAC3/4/2 on AD198A rev.2 due to a h/w bug.
1713  *
1714  * Input pins and routes
1715  *
1716  *        pin     boost   mix input # / adc input #
1717  * port-A 0x11 -> 0x38 -> mix 2, ADC 0
1718  * port-B 0x14 -> 0x39 -> mix 0, ADC 1
1719  * port-C 0x15 -> 0x3a -> 33:0 - mix 1, ADC 2
1720  * port-D 0x12 -> 0x3d -> mix 3, ADC 8
1721  * port-E 0x17 -> 0x3c -> 34:0 - mix 4, ADC 4
1722  * port-F 0x16 -> 0x3b -> mix 5, ADC 3
1723  * port-G 0x24 -> N/A  -> 33:1 - mix 1, 34:1 - mix 4, ADC 6
1724  * port-H 0x25 -> N/A  -> 33:2 - mix 1, 34:2 - mix 4, ADC 7
1725  *
1726  *
1727  * DAC assignment
1728  *   6stack - front/surr/CLFE/side/opt DACs - 04/06/05/0a/03
1729  *   3stack - front/surr/CLFE/opt DACs - 04/05/0a/03
1730  *
1731  * Inputs of Analog Mix (0x20)
1732  *   0:Port-B (front mic)
1733  *   1:Port-C/G/H (line-in)
1734  *   2:Port-A
1735  *   3:Port-D (line-in/2)
1736  *   4:Port-E/G/H (mic-in)
1737  *   5:Port-F (mic2-in)
1738  *   6:CD
1739  *   7:Beep
1740  *
1741  * ADC selection
1742  *   0:Port-A
1743  *   1:Port-B (front mic-in)
1744  *   2:Port-C (line-in)
1745  *   3:Port-F (mic2-in)
1746  *   4:Port-E (mic-in)
1747  *   5:CD
1748  *   6:Port-G
1749  *   7:Port-H
1750  *   8:Port-D (line-in/2)
1751  *   9:Mix
1752  *
1753  * Proposed pin assignments by the datasheet
1754  *
1755  * 6-stack
1756  * Port-A front headphone
1757  *      B front mic-in
1758  *      C rear line-in
1759  *      D rear front-out
1760  *      E rear mic-in
1761  *      F rear surround
1762  *      G rear CLFE
1763  *      H rear side
1764  *
1765  * 3-stack
1766  * Port-A front headphone
1767  *      B front mic
1768  *      C rear line-in/surround
1769  *      D rear front-out
1770  *      E rear mic-in/CLFE
1771  *
1772  * laptop
1773  * Port-A headphone
1774  *      B mic-in
1775  *      C docking station
1776  *      D internal speaker (with EAPD)
1777  *      E/F quad mic array
1778  */
1779
1780
1781 /* models */
1782 enum {
1783         AD1988_6STACK,
1784         AD1988_6STACK_DIG,
1785         AD1988_3STACK,
1786         AD1988_3STACK_DIG,
1787         AD1988_LAPTOP,
1788         AD1988_LAPTOP_DIG,
1789         AD1988_AUTO,
1790         AD1988_MODEL_LAST,
1791 };
1792
1793 /* reivision id to check workarounds */
1794 #define AD1988A_REV2            0x100200
1795
1796 #define is_rev2(codec) \
1797         ((codec)->vendor_id == 0x11d41988 && \
1798          (codec)->revision_id == AD1988A_REV2)
1799
1800 /*
1801  * mixers
1802  */
1803
1804 static hda_nid_t ad1988_6stack_dac_nids[4] = {
1805         0x04, 0x06, 0x05, 0x0a
1806 };
1807
1808 static hda_nid_t ad1988_3stack_dac_nids[3] = {
1809         0x04, 0x05, 0x0a
1810 };
1811
1812 /* for AD1988A revision-2, DAC2-4 are swapped */
1813 static hda_nid_t ad1988_6stack_dac_nids_rev2[4] = {
1814         0x04, 0x05, 0x0a, 0x06
1815 };
1816
1817 static hda_nid_t ad1988_3stack_dac_nids_rev2[3] = {
1818         0x04, 0x0a, 0x06
1819 };
1820
1821 static hda_nid_t ad1988_adc_nids[3] = {
1822         0x08, 0x09, 0x0f
1823 };
1824
1825 static hda_nid_t ad1988_capsrc_nids[3] = {
1826         0x0c, 0x0d, 0x0e
1827 };
1828
1829 #define AD1988_SPDIF_OUT                0x02
1830 #define AD1988_SPDIF_OUT_HDMI   0x0b
1831 #define AD1988_SPDIF_IN         0x07
1832
1833 static hda_nid_t ad1989b_slave_dig_outs[2] = {
1834         AD1988_SPDIF_OUT, AD1988_SPDIF_OUT_HDMI
1835 };
1836
1837 static struct hda_input_mux ad1988_6stack_capture_source = {
1838         .num_items = 5,
1839         .items = {
1840                 { "Front Mic", 0x1 },   /* port-B */
1841                 { "Line", 0x2 },        /* port-C */
1842                 { "Mic", 0x4 },         /* port-E */
1843                 { "CD", 0x5 },
1844                 { "Mix", 0x9 },
1845         },
1846 };
1847
1848 static struct hda_input_mux ad1988_laptop_capture_source = {
1849         .num_items = 3,
1850         .items = {
1851                 { "Mic/Line", 0x1 },    /* port-B */
1852                 { "CD", 0x5 },
1853                 { "Mix", 0x9 },
1854         },
1855 };
1856
1857 /*
1858  */
1859 static int ad198x_ch_mode_info(struct snd_kcontrol *kcontrol,
1860                                struct snd_ctl_elem_info *uinfo)
1861 {
1862         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1863         struct ad198x_spec *spec = codec->spec;
1864         return snd_hda_ch_mode_info(codec, uinfo, spec->channel_mode,
1865                                     spec->num_channel_mode);
1866 }
1867
1868 static int ad198x_ch_mode_get(struct snd_kcontrol *kcontrol,
1869                               struct snd_ctl_elem_value *ucontrol)
1870 {
1871         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1872         struct ad198x_spec *spec = codec->spec;
1873         return snd_hda_ch_mode_get(codec, ucontrol, spec->channel_mode,
1874                                    spec->num_channel_mode, spec->multiout.max_channels);
1875 }
1876
1877 static int ad198x_ch_mode_put(struct snd_kcontrol *kcontrol,
1878                               struct snd_ctl_elem_value *ucontrol)
1879 {
1880         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
1881         struct ad198x_spec *spec = codec->spec;
1882         int err = snd_hda_ch_mode_put(codec, ucontrol, spec->channel_mode,
1883                                       spec->num_channel_mode,
1884                                       &spec->multiout.max_channels);
1885         if (err >= 0 && spec->need_dac_fix)
1886                 spec->multiout.num_dacs = spec->multiout.max_channels / 2;
1887         return err;
1888 }
1889
1890 /* 6-stack mode */
1891 static struct snd_kcontrol_new ad1988_6stack_mixers1[] = {
1892         HDA_CODEC_VOLUME("Front Playback Volume", 0x04, 0x0, HDA_OUTPUT),
1893         HDA_CODEC_VOLUME("Surround Playback Volume", 0x06, 0x0, HDA_OUTPUT),
1894         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x05, 1, 0x0, HDA_OUTPUT),
1895         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x05, 2, 0x0, HDA_OUTPUT),
1896         HDA_CODEC_VOLUME("Side Playback Volume", 0x0a, 0x0, HDA_OUTPUT),
1897         { } /* end */
1898 };
1899
1900 static struct snd_kcontrol_new ad1988_6stack_mixers1_rev2[] = {
1901         HDA_CODEC_VOLUME("Front Playback Volume", 0x04, 0x0, HDA_OUTPUT),
1902         HDA_CODEC_VOLUME("Surround Playback Volume", 0x05, 0x0, HDA_OUTPUT),
1903         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x0a, 1, 0x0, HDA_OUTPUT),
1904         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x0a, 2, 0x0, HDA_OUTPUT),
1905         HDA_CODEC_VOLUME("Side Playback Volume", 0x06, 0x0, HDA_OUTPUT),
1906         { } /* end */
1907 };
1908
1909 static struct snd_kcontrol_new ad1988_6stack_mixers2[] = {
1910         HDA_BIND_MUTE("Front Playback Switch", 0x29, 2, HDA_INPUT),
1911         HDA_BIND_MUTE("Surround Playback Switch", 0x2a, 2, HDA_INPUT),
1912         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x27, 1, 2, HDA_INPUT),
1913         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x27, 2, 2, HDA_INPUT),
1914         HDA_BIND_MUTE("Side Playback Switch", 0x28, 2, HDA_INPUT),
1915         HDA_BIND_MUTE("Headphone Playback Switch", 0x22, 2, HDA_INPUT),
1916         HDA_BIND_MUTE("Mono Playback Switch", 0x1e, 2, HDA_INPUT),
1917
1918         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x6, HDA_INPUT),
1919         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x6, HDA_INPUT),
1920         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x0, HDA_INPUT),
1921         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x0, HDA_INPUT),
1922         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x1, HDA_INPUT),
1923         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x1, HDA_INPUT),
1924         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x4, HDA_INPUT),
1925         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x4, HDA_INPUT),
1926
1927         HDA_CODEC_VOLUME("Beep Playback Volume", 0x10, 0x0, HDA_OUTPUT),
1928         HDA_CODEC_MUTE("Beep Playback Switch", 0x10, 0x0, HDA_OUTPUT),
1929
1930         HDA_CODEC_VOLUME("Analog Mix Playback Volume", 0x21, 0x0, HDA_OUTPUT),
1931         HDA_CODEC_MUTE("Analog Mix Playback Switch", 0x21, 0x0, HDA_OUTPUT),
1932
1933         HDA_CODEC_VOLUME("Front Mic Boost", 0x39, 0x0, HDA_OUTPUT),
1934         HDA_CODEC_VOLUME("Mic Boost", 0x3c, 0x0, HDA_OUTPUT),
1935
1936         { } /* end */
1937 };
1938
1939 /* 3-stack mode */
1940 static struct snd_kcontrol_new ad1988_3stack_mixers1[] = {
1941         HDA_CODEC_VOLUME("Front Playback Volume", 0x04, 0x0, HDA_OUTPUT),
1942         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0a, 0x0, HDA_OUTPUT),
1943         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x05, 1, 0x0, HDA_OUTPUT),
1944         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x05, 2, 0x0, HDA_OUTPUT),
1945         { } /* end */
1946 };
1947
1948 static struct snd_kcontrol_new ad1988_3stack_mixers1_rev2[] = {
1949         HDA_CODEC_VOLUME("Front Playback Volume", 0x04, 0x0, HDA_OUTPUT),
1950         HDA_CODEC_VOLUME("Surround Playback Volume", 0x0a, 0x0, HDA_OUTPUT),
1951         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x06, 1, 0x0, HDA_OUTPUT),
1952         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x06, 2, 0x0, HDA_OUTPUT),
1953         { } /* end */
1954 };
1955
1956 static struct snd_kcontrol_new ad1988_3stack_mixers2[] = {
1957         HDA_BIND_MUTE("Front Playback Switch", 0x29, 2, HDA_INPUT),
1958         HDA_BIND_MUTE("Surround Playback Switch", 0x2c, 2, HDA_INPUT),
1959         HDA_BIND_MUTE_MONO("Center Playback Switch", 0x26, 1, 2, HDA_INPUT),
1960         HDA_BIND_MUTE_MONO("LFE Playback Switch", 0x26, 2, 2, HDA_INPUT),
1961         HDA_BIND_MUTE("Headphone Playback Switch", 0x22, 2, HDA_INPUT),
1962         HDA_BIND_MUTE("Mono Playback Switch", 0x1e, 2, HDA_INPUT),
1963
1964         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x6, HDA_INPUT),
1965         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x6, HDA_INPUT),
1966         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x0, HDA_INPUT),
1967         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x0, HDA_INPUT),
1968         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x1, HDA_INPUT),
1969         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x1, HDA_INPUT),
1970         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x4, HDA_INPUT),
1971         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x4, HDA_INPUT),
1972
1973         HDA_CODEC_VOLUME("Beep Playback Volume", 0x10, 0x0, HDA_OUTPUT),
1974         HDA_CODEC_MUTE("Beep Playback Switch", 0x10, 0x0, HDA_OUTPUT),
1975
1976         HDA_CODEC_VOLUME("Analog Mix Playback Volume", 0x21, 0x0, HDA_OUTPUT),
1977         HDA_CODEC_MUTE("Analog Mix Playback Switch", 0x21, 0x0, HDA_OUTPUT),
1978
1979         HDA_CODEC_VOLUME("Front Mic Boost", 0x39, 0x0, HDA_OUTPUT),
1980         HDA_CODEC_VOLUME("Mic Boost", 0x3c, 0x0, HDA_OUTPUT),
1981         {
1982                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1983                 .name = "Channel Mode",
1984                 .info = ad198x_ch_mode_info,
1985                 .get = ad198x_ch_mode_get,
1986                 .put = ad198x_ch_mode_put,
1987         },
1988
1989         { } /* end */
1990 };
1991
1992 /* laptop mode */
1993 static struct snd_kcontrol_new ad1988_laptop_mixers[] = {
1994         HDA_CODEC_VOLUME("PCM Playback Volume", 0x04, 0x0, HDA_OUTPUT),
1995         HDA_CODEC_MUTE("PCM Playback Switch", 0x29, 0x0, HDA_INPUT),
1996         HDA_BIND_MUTE("Mono Playback Switch", 0x1e, 2, HDA_INPUT),
1997
1998         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x6, HDA_INPUT),
1999         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x6, HDA_INPUT),
2000         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x0, HDA_INPUT),
2001         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x0, HDA_INPUT),
2002         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x1, HDA_INPUT),
2003         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x1, HDA_INPUT),
2004
2005         HDA_CODEC_VOLUME("Beep Playback Volume", 0x10, 0x0, HDA_OUTPUT),
2006         HDA_CODEC_MUTE("Beep Playback Switch", 0x10, 0x0, HDA_OUTPUT),
2007
2008         HDA_CODEC_VOLUME("Analog Mix Playback Volume", 0x21, 0x0, HDA_OUTPUT),
2009         HDA_CODEC_MUTE("Analog Mix Playback Switch", 0x21, 0x0, HDA_OUTPUT),
2010
2011         HDA_CODEC_VOLUME("Mic Boost", 0x39, 0x0, HDA_OUTPUT),
2012
2013         {
2014                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2015                 .name = "External Amplifier",
2016                 .info = ad198x_eapd_info,
2017                 .get = ad198x_eapd_get,
2018                 .put = ad198x_eapd_put,
2019                 .private_value = 0x12 | (1 << 8), /* port-D, inversed */
2020         },
2021
2022         { } /* end */
2023 };
2024
2025 /* capture */
2026 static struct snd_kcontrol_new ad1988_capture_mixers[] = {
2027         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
2028         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
2029         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
2030         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
2031         HDA_CODEC_VOLUME_IDX("Capture Volume", 2, 0x0e, 0x0, HDA_OUTPUT),
2032         HDA_CODEC_MUTE_IDX("Capture Switch", 2, 0x0e, 0x0, HDA_OUTPUT),
2033         {
2034                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2035                 /* The multiple "Capture Source" controls confuse alsamixer
2036                  * So call somewhat different..
2037                  */
2038                 /* .name = "Capture Source", */
2039                 .name = "Input Source",
2040                 .count = 3,
2041                 .info = ad198x_mux_enum_info,
2042                 .get = ad198x_mux_enum_get,
2043                 .put = ad198x_mux_enum_put,
2044         },
2045         { } /* end */
2046 };
2047
2048 static int ad1988_spdif_playback_source_info(struct snd_kcontrol *kcontrol,
2049                                              struct snd_ctl_elem_info *uinfo)
2050 {
2051         static char *texts[] = {
2052                 "PCM", "ADC1", "ADC2", "ADC3"
2053         };
2054         uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
2055         uinfo->count = 1;
2056         uinfo->value.enumerated.items = 4;
2057         if (uinfo->value.enumerated.item >= 4)
2058                 uinfo->value.enumerated.item = 3;
2059         strcpy(uinfo->value.enumerated.name, texts[uinfo->value.enumerated.item]);
2060         return 0;
2061 }
2062
2063 static int ad1988_spdif_playback_source_get(struct snd_kcontrol *kcontrol,
2064                                             struct snd_ctl_elem_value *ucontrol)
2065 {
2066         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2067         unsigned int sel;
2068
2069         sel = snd_hda_codec_read(codec, 0x1d, 0, AC_VERB_GET_AMP_GAIN_MUTE,
2070                                  AC_AMP_GET_INPUT);
2071         if (!(sel & 0x80))
2072                 ucontrol->value.enumerated.item[0] = 0;
2073         else {
2074                 sel = snd_hda_codec_read(codec, 0x0b, 0,
2075                                          AC_VERB_GET_CONNECT_SEL, 0);
2076                 if (sel < 3)
2077                         sel++;
2078                 else
2079                         sel = 0;
2080                 ucontrol->value.enumerated.item[0] = sel;
2081         }
2082         return 0;
2083 }
2084
2085 static int ad1988_spdif_playback_source_put(struct snd_kcontrol *kcontrol,
2086                                             struct snd_ctl_elem_value *ucontrol)
2087 {
2088         struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2089         unsigned int val, sel;
2090         int change;
2091
2092         val = ucontrol->value.enumerated.item[0];
2093         if (val > 3)
2094                 return -EINVAL;
2095         if (!val) {
2096                 sel = snd_hda_codec_read(codec, 0x1d, 0,
2097                                          AC_VERB_GET_AMP_GAIN_MUTE,
2098                                          AC_AMP_GET_INPUT);
2099                 change = sel & 0x80;
2100                 if (change) {
2101                         snd_hda_codec_write_cache(codec, 0x1d, 0,
2102                                                   AC_VERB_SET_AMP_GAIN_MUTE,
2103                                                   AMP_IN_UNMUTE(0));
2104                         snd_hda_codec_write_cache(codec, 0x1d, 0,
2105                                                   AC_VERB_SET_AMP_GAIN_MUTE,
2106                                                   AMP_IN_MUTE(1));
2107                 }
2108         } else {
2109                 sel = snd_hda_codec_read(codec, 0x1d, 0,
2110                                          AC_VERB_GET_AMP_GAIN_MUTE,
2111                                          AC_AMP_GET_INPUT | 0x01);
2112                 change = sel & 0x80;
2113                 if (change) {
2114                         snd_hda_codec_write_cache(codec, 0x1d, 0,
2115                                                   AC_VERB_SET_AMP_GAIN_MUTE,
2116                                                   AMP_IN_MUTE(0));
2117                         snd_hda_codec_write_cache(codec, 0x1d, 0,
2118                                                   AC_VERB_SET_AMP_GAIN_MUTE,
2119                                                   AMP_IN_UNMUTE(1));
2120                 }
2121                 sel = snd_hda_codec_read(codec, 0x0b, 0,
2122                                          AC_VERB_GET_CONNECT_SEL, 0) + 1;
2123                 change |= sel != val;
2124                 if (change)
2125                         snd_hda_codec_write_cache(codec, 0x0b, 0,
2126                                                   AC_VERB_SET_CONNECT_SEL,
2127                                                   val - 1);
2128         }
2129         return change;
2130 }
2131
2132 static struct snd_kcontrol_new ad1988_spdif_out_mixers[] = {
2133         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
2134         {
2135                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2136                 .name = "IEC958 Playback Source",
2137                 .info = ad1988_spdif_playback_source_info,
2138                 .get = ad1988_spdif_playback_source_get,
2139                 .put = ad1988_spdif_playback_source_put,
2140         },
2141         { } /* end */
2142 };
2143
2144 static struct snd_kcontrol_new ad1988_spdif_in_mixers[] = {
2145         HDA_CODEC_VOLUME("IEC958 Capture Volume", 0x1c, 0x0, HDA_INPUT),
2146         { } /* end */
2147 };
2148
2149 static struct snd_kcontrol_new ad1989_spdif_out_mixers[] = {
2150         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
2151         HDA_CODEC_VOLUME("HDMI Playback Volume", 0x1d, 0x0, HDA_OUTPUT),
2152         { } /* end */
2153 };
2154
2155 /*
2156  * initialization verbs
2157  */
2158
2159 /*
2160  * for 6-stack (+dig)
2161  */
2162 static struct hda_verb ad1988_6stack_init_verbs[] = {
2163         /* Front, Surround, CLFE, side DAC; unmute as default */
2164         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2165         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2166         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2167         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2168         /* Port-A front headphon path */
2169         {0x37, AC_VERB_SET_CONNECT_SEL, 0x01}, /* DAC1:04h */
2170         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2171         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2172         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2173         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
2174         /* Port-D line-out path */
2175         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2176         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2177         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2178         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2179         /* Port-F surround path */
2180         {0x2a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2181         {0x2a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2182         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2183         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2184         /* Port-G CLFE path */
2185         {0x27, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2186         {0x27, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2187         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2188         {0x24, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2189         /* Port-H side path */
2190         {0x28, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2191         {0x28, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2192         {0x25, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2193         {0x25, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2194         /* Mono out path */
2195         {0x36, AC_VERB_SET_CONNECT_SEL, 0x1}, /* DAC1:04h */
2196         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2197         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2198         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2199         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb01f}, /* unmute, 0dB */
2200         /* Port-B front mic-in path */
2201         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2202         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2203         {0x39, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2204         /* Port-C line-in path */
2205         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2206         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
2207         {0x3a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2208         {0x33, AC_VERB_SET_CONNECT_SEL, 0x0},
2209         /* Port-E mic-in path */
2210         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2211         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2212         {0x3c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2213         {0x34, AC_VERB_SET_CONNECT_SEL, 0x0},
2214         /* Analog CD Input */
2215         {0x18, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
2216         /* Analog Mix output amp */
2217         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x1f}, /* 0dB */
2218
2219         { }
2220 };
2221
2222 static struct hda_verb ad1988_capture_init_verbs[] = {
2223         /* mute analog mix */
2224         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2225         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2226         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
2227         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
2228         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
2229         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)},
2230         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)},
2231         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)},
2232         /* select ADCs - front-mic */
2233         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x1},
2234         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x1},
2235         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x1},
2236         /* ADCs; muted */
2237         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2238         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2239         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2240
2241         { }
2242 };
2243
2244 static struct hda_verb ad1988_spdif_init_verbs[] = {
2245         /* SPDIF out sel */
2246         {0x02, AC_VERB_SET_CONNECT_SEL, 0x0}, /* PCM */
2247         {0x0b, AC_VERB_SET_CONNECT_SEL, 0x0}, /* ADC1 */
2248         {0x1d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
2249         {0x1d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2250         /* SPDIF out pin */
2251         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
2252
2253         { }
2254 };
2255
2256 /* AD1989 has no ADC -> SPDIF route */
2257 static struct hda_verb ad1989_spdif_init_verbs[] = {
2258         /* SPDIF-1 out pin */
2259         {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
2260         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
2261         /* SPDIF-2/HDMI out pin */
2262         {0x1d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
2263         {0x1d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
2264         { }
2265 };
2266
2267 /*
2268  * verbs for 3stack (+dig)
2269  */
2270 static struct hda_verb ad1988_3stack_ch2_init[] = {
2271         /* set port-C to line-in */
2272         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
2273         { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN },
2274         /* set port-E to mic-in */
2275         { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
2276         { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 },
2277         { } /* end */
2278 };
2279
2280 static struct hda_verb ad1988_3stack_ch6_init[] = {
2281         /* set port-C to surround out */
2282         { 0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
2283         { 0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
2284         /* set port-E to CLFE out */
2285         { 0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },
2286         { 0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
2287         { } /* end */
2288 };
2289
2290 static struct hda_channel_mode ad1988_3stack_modes[2] = {
2291         { 2, ad1988_3stack_ch2_init },
2292         { 6, ad1988_3stack_ch6_init },
2293 };
2294
2295 static struct hda_verb ad1988_3stack_init_verbs[] = {
2296         /* Front, Surround, CLFE, side DAC; unmute as default */
2297         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2298         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2299         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2300         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2301         /* Port-A front headphon path */
2302         {0x37, AC_VERB_SET_CONNECT_SEL, 0x01}, /* DAC1:04h */
2303         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2304         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2305         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2306         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
2307         /* Port-D line-out path */
2308         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2309         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2310         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2311         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2312         /* Mono out path */
2313         {0x36, AC_VERB_SET_CONNECT_SEL, 0x1}, /* DAC1:04h */
2314         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2315         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2316         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2317         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb01f}, /* unmute, 0dB */
2318         /* Port-B front mic-in path */
2319         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2320         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2321         {0x39, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2322         /* Port-C line-in/surround path - 6ch mode as default */
2323         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2324         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2325         {0x3a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2326         {0x31, AC_VERB_SET_CONNECT_SEL, 0x0}, /* output sel: DAC 0x05 */
2327         {0x33, AC_VERB_SET_CONNECT_SEL, 0x0},
2328         /* Port-E mic-in/CLFE path - 6ch mode as default */
2329         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2330         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2331         {0x3c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2332         {0x32, AC_VERB_SET_CONNECT_SEL, 0x1}, /* output sel: DAC 0x0a */
2333         {0x34, AC_VERB_SET_CONNECT_SEL, 0x0},
2334         /* mute analog mix */
2335         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2336         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2337         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
2338         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
2339         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
2340         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)},
2341         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)},
2342         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)},
2343         /* select ADCs - front-mic */
2344         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x1},
2345         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x1},
2346         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x1},
2347         /* ADCs; muted */
2348         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2349         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2350         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2351         /* Analog Mix output amp */
2352         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x1f}, /* 0dB */
2353         { }
2354 };
2355
2356 /*
2357  * verbs for laptop mode (+dig)
2358  */
2359 static struct hda_verb ad1988_laptop_hp_on[] = {
2360         /* unmute port-A and mute port-D */
2361         { 0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
2362         { 0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
2363         { } /* end */
2364 };
2365 static struct hda_verb ad1988_laptop_hp_off[] = {
2366         /* mute port-A and unmute port-D */
2367         { 0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
2368         { 0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE },
2369         { } /* end */
2370 };
2371
2372 #define AD1988_HP_EVENT 0x01
2373
2374 static struct hda_verb ad1988_laptop_init_verbs[] = {
2375         /* Front, Surround, CLFE, side DAC; unmute as default */
2376         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2377         {0x06, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2378         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2379         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2380         /* Port-A front headphon path */
2381         {0x37, AC_VERB_SET_CONNECT_SEL, 0x01}, /* DAC1:04h */
2382         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2383         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2384         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2385         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
2386         /* unsolicited event for pin-sense */
2387         {0x11, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1988_HP_EVENT },
2388         /* Port-D line-out path + EAPD */
2389         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2390         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2391         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2392         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2393         {0x12, AC_VERB_SET_EAPD_BTLENABLE, 0x00}, /* EAPD-off */
2394         /* Mono out path */
2395         {0x36, AC_VERB_SET_CONNECT_SEL, 0x1}, /* DAC1:04h */
2396         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2397         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2398         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2399         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, 0xb01f}, /* unmute, 0dB */
2400         /* Port-B mic-in path */
2401         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2402         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
2403         {0x39, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2404         /* Port-C docking station - try to output */
2405         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
2406         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
2407         {0x3a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
2408         {0x33, AC_VERB_SET_CONNECT_SEL, 0x0},
2409         /* mute analog mix */
2410         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
2411         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
2412         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
2413         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
2414         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
2415         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)},
2416         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)},
2417         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)},
2418         /* select ADCs - mic */
2419         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x1},
2420         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x1},
2421         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x1},
2422         /* ADCs; muted */
2423         {0x08, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2424         {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2425         {0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
2426         /* Analog Mix output amp */
2427         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x1f}, /* 0dB */
2428         { }
2429 };
2430
2431 static void ad1988_laptop_unsol_event(struct hda_codec *codec, unsigned int res)
2432 {
2433         if ((res >> 26) != AD1988_HP_EVENT)
2434                 return;
2435         if (snd_hda_codec_read(codec, 0x11, 0, AC_VERB_GET_PIN_SENSE, 0) & (1 << 31))
2436                 snd_hda_sequence_write(codec, ad1988_laptop_hp_on);
2437         else
2438                 snd_hda_sequence_write(codec, ad1988_laptop_hp_off);
2439
2440
2441 #ifdef CONFIG_SND_HDA_POWER_SAVE
2442 static struct hda_amp_list ad1988_loopbacks[] = {
2443         { 0x20, HDA_INPUT, 0 }, /* Front Mic */
2444         { 0x20, HDA_INPUT, 1 }, /* Line */
2445         { 0x20, HDA_INPUT, 4 }, /* Mic */
2446         { 0x20, HDA_INPUT, 6 }, /* CD */
2447         { } /* end */
2448 };
2449 #endif
2450
2451 /*
2452  * Automatic parse of I/O pins from the BIOS configuration
2453  */
2454
2455 #define NUM_CONTROL_ALLOC       32
2456 #define NUM_VERB_ALLOC          32
2457
2458 enum {
2459         AD_CTL_WIDGET_VOL,
2460         AD_CTL_WIDGET_MUTE,
2461         AD_CTL_BIND_MUTE,
2462 };
2463 static struct snd_kcontrol_new ad1988_control_templates[] = {
2464         HDA_CODEC_VOLUME(NULL, 0, 0, 0),
2465         HDA_CODEC_MUTE(NULL, 0, 0, 0),
2466         HDA_BIND_MUTE(NULL, 0, 0, 0),
2467 };
2468
2469 /* add dynamic controls */
2470 static int add_control(struct ad198x_spec *spec, int type, const char *name,
2471                        unsigned long val)
2472 {
2473         struct snd_kcontrol_new *knew;
2474
2475         if (spec->num_kctl_used >= spec->num_kctl_alloc) {
2476                 int num = spec->num_kctl_alloc + NUM_CONTROL_ALLOC;
2477
2478                 knew = kcalloc(num + 1, sizeof(*knew), GFP_KERNEL); /* array + terminator */
2479                 if (! knew)
2480                         return -ENOMEM;
2481                 if (spec->kctl_alloc) {
2482                         memcpy(knew, spec->kctl_alloc, sizeof(*knew) * spec->num_kctl_alloc);
2483                         kfree(spec->kctl_alloc);
2484                 }
2485                 spec->kctl_alloc = knew;
2486                 spec->num_kctl_alloc = num;
2487         }
2488
2489         knew = &spec->kctl_alloc[spec->num_kctl_used];
2490         *knew = ad1988_control_templates[type];
2491         knew->name = kstrdup(name, GFP_KERNEL);
2492         if (! knew->name)
2493                 return -ENOMEM;
2494         knew->private_value = val;
2495         spec->num_kctl_used++;
2496         return 0;
2497 }
2498
2499 #define AD1988_PIN_CD_NID               0x18
2500 #define AD1988_PIN_BEEP_NID             0x10
2501
2502 static hda_nid_t ad1988_mixer_nids[8] = {
2503         /* A     B     C     D     E     F     G     H */
2504         0x22, 0x2b, 0x2c, 0x29, 0x26, 0x2a, 0x27, 0x28
2505 };
2506
2507 static inline hda_nid_t ad1988_idx_to_dac(struct hda_codec *codec, int idx)
2508 {
2509         static hda_nid_t idx_to_dac[8] = {
2510                 /* A     B     C     D     E     F     G     H */
2511                 0x04, 0x06, 0x05, 0x04, 0x0a, 0x06, 0x05, 0x0a
2512         };
2513         static hda_nid_t idx_to_dac_rev2[8] = {
2514                 /* A     B     C     D     E     F     G     H */
2515                 0x04, 0x05, 0x0a, 0x04, 0x06, 0x05, 0x0a, 0x06
2516         };
2517         if (is_rev2(codec))
2518                 return idx_to_dac_rev2[idx];
2519         else
2520                 return idx_to_dac[idx];
2521 }
2522
2523 static hda_nid_t ad1988_boost_nids[8] = {
2524         0x38, 0x39, 0x3a, 0x3d, 0x3c, 0x3b, 0, 0
2525 };
2526
2527 static int ad1988_pin_idx(hda_nid_t nid)
2528 {
2529         static hda_nid_t ad1988_io_pins[8] = {
2530                 0x11, 0x14, 0x15, 0x12, 0x17, 0x16, 0x24, 0x25
2531         };
2532         int i;
2533         for (i = 0; i < ARRAY_SIZE(ad1988_io_pins); i++)
2534                 if (ad1988_io_pins[i] == nid)
2535                         return i;
2536         return 0; /* should be -1 */
2537 }
2538
2539 static int ad1988_pin_to_loopback_idx(hda_nid_t nid)
2540 {
2541         static int loopback_idx[8] = {
2542                 2, 0, 1, 3, 4, 5, 1, 4
2543         };
2544         switch (nid) {
2545         case AD1988_PIN_CD_NID:
2546                 return 6;
2547         default:
2548                 return loopback_idx[ad1988_pin_idx(nid)];
2549         }
2550 }
2551
2552 static int ad1988_pin_to_adc_idx(hda_nid_t nid)
2553 {
2554         static int adc_idx[8] = {
2555                 0, 1, 2, 8, 4, 3, 6, 7
2556         };
2557         switch (nid) {
2558         case AD1988_PIN_CD_NID:
2559                 return 5;
2560         default:
2561                 return adc_idx[ad1988_pin_idx(nid)];
2562         }
2563 }
2564
2565 /* fill in the dac_nids table from the parsed pin configuration */
2566 static int ad1988_auto_fill_dac_nids(struct hda_codec *codec,
2567                                      const struct auto_pin_cfg *cfg)
2568 {
2569         struct ad198x_spec *spec = codec->spec;
2570         int i, idx;
2571
2572         spec->multiout.dac_nids = spec->private_dac_nids;
2573
2574         /* check the pins hardwired to audio widget */
2575         for (i = 0; i < cfg->line_outs; i++) {
2576                 idx = ad1988_pin_idx(cfg->line_out_pins[i]);
2577                 spec->multiout.dac_nids[i] = ad1988_idx_to_dac(codec, idx);
2578         }
2579         spec->multiout.num_dacs = cfg->line_outs;
2580         return 0;
2581 }
2582
2583 /* add playback controls from the parsed DAC table */
2584 static int ad1988_auto_create_multi_out_ctls(struct ad198x_spec *spec,
2585                                              const struct auto_pin_cfg *cfg)
2586 {
2587         char name[32];
2588         static const char *chname[4] = { "Front", "Surround", NULL /*CLFE*/, "Side" };
2589         hda_nid_t nid;
2590         int i, err;
2591
2592         for (i = 0; i < cfg->line_outs; i++) {
2593                 hda_nid_t dac = spec->multiout.dac_nids[i];
2594                 if (! dac)
2595                         continue;
2596                 nid = ad1988_mixer_nids[ad1988_pin_idx(cfg->line_out_pins[i])];
2597                 if (i == 2) {
2598                         /* Center/LFE */
2599                         err = add_control(spec, AD_CTL_WIDGET_VOL,
2600                                           "Center Playback Volume",
2601                                           HDA_COMPOSE_AMP_VAL(dac, 1, 0, HDA_OUTPUT));
2602                         if (err < 0)
2603                                 return err;
2604                         err = add_control(spec, AD_CTL_WIDGET_VOL,
2605                                           "LFE Playback Volume",
2606                                           HDA_COMPOSE_AMP_VAL(dac, 2, 0, HDA_OUTPUT));
2607                         if (err < 0)
2608                                 return err;
2609                         err = add_control(spec, AD_CTL_BIND_MUTE,
2610                                           "Center Playback Switch",
2611                                           HDA_COMPOSE_AMP_VAL(nid, 1, 2, HDA_INPUT));
2612                         if (err < 0)
2613                                 return err;
2614                         err = add_control(spec, AD_CTL_BIND_MUTE,
2615                                           "LFE Playback Switch",
2616                                           HDA_COMPOSE_AMP_VAL(nid, 2, 2, HDA_INPUT));
2617                         if (err < 0)
2618                                 return err;
2619                 } else {
2620                         sprintf(name, "%s Playback Volume", chname[i]);
2621                         err = add_control(spec, AD_CTL_WIDGET_VOL, name,
2622                                           HDA_COMPOSE_AMP_VAL(dac, 3, 0, HDA_OUTPUT));
2623                         if (err < 0)
2624                                 return err;
2625                         sprintf(name, "%s Playback Switch", chname[i]);
2626                         err = add_control(spec, AD_CTL_BIND_MUTE, name,
2627                                           HDA_COMPOSE_AMP_VAL(nid, 3, 2, HDA_INPUT));
2628                         if (err < 0)
2629                                 return err;
2630                 }
2631         }
2632         return 0;
2633 }
2634
2635 /* add playback controls for speaker and HP outputs */
2636 static int ad1988_auto_create_extra_out(struct hda_codec *codec, hda_nid_t pin,
2637                                         const char *pfx)
2638 {
2639         struct ad198x_spec *spec = codec->spec;
2640         hda_nid_t nid;
2641         int i, idx, err;
2642         char name[32];
2643
2644         if (! pin)
2645                 return 0;
2646
2647         idx = ad1988_pin_idx(pin);
2648         nid = ad1988_idx_to_dac(codec, idx);
2649         /* check whether the corresponding DAC was already taken */
2650         for (i = 0; i < spec->autocfg.line_outs; i++) {
2651                 hda_nid_t pin = spec->autocfg.line_out_pins[i];
2652                 hda_nid_t dac = ad1988_idx_to_dac(codec, ad1988_pin_idx(pin));
2653                 if (dac == nid)
2654                         break;
2655         }
2656         if (i >= spec->autocfg.line_outs) {
2657                 /* specify the DAC as the extra output */
2658                 if (!spec->multiout.hp_nid)
2659                         spec->multiout.hp_nid = nid;
2660                 else
2661                         spec->multiout.extra_out_nid[0] = nid;
2662                 /* control HP volume/switch on the output mixer amp */
2663                 sprintf(name, "%s Playback Volume", pfx);
2664                 err = add_control(spec, AD_CTL_WIDGET_VOL, name,
2665                                   HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT));
2666                 if (err < 0)
2667                         return err;
2668         }
2669         nid = ad1988_mixer_nids[idx];
2670         sprintf(name, "%s Playback Switch", pfx);
2671         if ((err = add_control(spec, AD_CTL_BIND_MUTE, name,
2672                                HDA_COMPOSE_AMP_VAL(nid, 3, 2, HDA_INPUT))) < 0)
2673                 return err;
2674         return 0;
2675 }
2676
2677 /* create input playback/capture controls for the given pin */
2678 static int new_analog_input(struct ad198x_spec *spec, hda_nid_t pin,
2679                             const char *ctlname, int boost)
2680 {
2681         char name[32];
2682         int err, idx;
2683
2684         sprintf(name, "%s Playback Volume", ctlname);
2685         idx = ad1988_pin_to_loopback_idx(pin);
2686         if ((err = add_control(spec, AD_CTL_WIDGET_VOL, name,
2687                                HDA_COMPOSE_AMP_VAL(0x20, 3, idx, HDA_INPUT))) < 0)
2688                 return err;
2689         sprintf(name, "%s Playback Switch", ctlname);
2690         if ((err = add_control(spec, AD_CTL_WIDGET_MUTE, name,
2691                                HDA_COMPOSE_AMP_VAL(0x20, 3, idx, HDA_INPUT))) < 0)
2692                 return err;
2693         if (boost) {
2694                 hda_nid_t bnid;
2695                 idx = ad1988_pin_idx(pin);
2696                 bnid = ad1988_boost_nids[idx];
2697                 if (bnid) {
2698                         sprintf(name, "%s Boost", ctlname);
2699                         return add_control(spec, AD_CTL_WIDGET_VOL, name,
2700                                            HDA_COMPOSE_AMP_VAL(bnid, 3, idx, HDA_OUTPUT));
2701
2702                 }
2703         }
2704         return 0;
2705 }
2706
2707 /* create playback/capture controls for input pins */
2708 static int ad1988_auto_create_analog_input_ctls(struct ad198x_spec *spec,
2709                                                 const struct auto_pin_cfg *cfg)
2710 {
2711         struct hda_input_mux *imux = &spec->private_imux;
2712         int i, err;
2713
2714         for (i = 0; i < AUTO_PIN_LAST; i++) {
2715                 err = new_analog_input(spec, cfg->input_pins[i],
2716                                        auto_pin_cfg_labels[i],
2717                                        i <= AUTO_PIN_FRONT_MIC);
2718                 if (err < 0)
2719                         return err;
2720                 imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
2721                 imux->items[imux->num_items].index = ad1988_pin_to_adc_idx(cfg->input_pins[i]);
2722                 imux->num_items++;
2723         }
2724         imux->items[imux->num_items].label = "Mix";
2725         imux->items[imux->num_items].index = 9;
2726         imux->num_items++;
2727
2728         if ((err = add_control(spec, AD_CTL_WIDGET_VOL,
2729                                "Analog Mix Playback Volume",
2730                                HDA_COMPOSE_AMP_VAL(0x21, 3, 0x0, HDA_OUTPUT))) < 0)
2731                 return err;
2732         if ((err = add_control(spec, AD_CTL_WIDGET_MUTE,
2733                                "Analog Mix Playback Switch",
2734                                HDA_COMPOSE_AMP_VAL(0x21, 3, 0x0, HDA_OUTPUT))) < 0)
2735                 return err;
2736
2737         return 0;
2738 }
2739
2740 static void ad1988_auto_set_output_and_unmute(struct hda_codec *codec,
2741                                               hda_nid_t nid, int pin_type,
2742                                               int dac_idx)
2743 {
2744         /* set as output */
2745         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
2746         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE);
2747         switch (nid) {
2748         case 0x11: /* port-A - DAC 04 */
2749                 snd_hda_codec_write(codec, 0x37, 0, AC_VERB_SET_CONNECT_SEL, 0x01);
2750                 break;
2751         case 0x14: /* port-B - DAC 06 */
2752                 snd_hda_codec_write(codec, 0x30, 0, AC_VERB_SET_CONNECT_SEL, 0x02);
2753                 break;
2754         case 0x15: /* port-C - DAC 05 */
2755                 snd_hda_codec_write(codec, 0x31, 0, AC_VERB_SET_CONNECT_SEL, 0x00);
2756                 break;
2757         case 0x17: /* port-E - DAC 0a */
2758                 snd_hda_codec_write(codec, 0x32, 0, AC_VERB_SET_CONNECT_SEL, 0x01);
2759                 break;
2760         case 0x13: /* mono - DAC 04 */
2761                 snd_hda_codec_write(codec, 0x36, 0, AC_VERB_SET_CONNECT_SEL, 0x01);
2762                 break;
2763         }
2764 }
2765
2766 static void ad1988_auto_init_multi_out(struct hda_codec *codec)
2767 {
2768         struct ad198x_spec *spec = codec->spec;
2769         int i;
2770
2771         for (i = 0; i < spec->autocfg.line_outs; i++) {
2772                 hda_nid_t nid = spec->autocfg.line_out_pins[i];
2773                 ad1988_auto_set_output_and_unmute(codec, nid, PIN_OUT, i);
2774         }
2775 }
2776
2777 static void ad1988_auto_init_extra_out(struct hda_codec *codec)
2778 {
2779         struct ad198x_spec *spec = codec->spec;
2780         hda_nid_t pin;
2781
2782         pin = spec->autocfg.speaker_pins[0];
2783         if (pin) /* connect to front */
2784                 ad1988_auto_set_output_and_unmute(codec, pin, PIN_OUT, 0);
2785         pin = spec->autocfg.hp_pins[0];
2786         if (pin) /* connect to front */
2787                 ad1988_auto_set_output_and_unmute(codec, pin, PIN_HP, 0);
2788 }
2789
2790 static void ad1988_auto_init_analog_input(struct hda_codec *codec)
2791 {
2792         struct ad198x_spec *spec = codec->spec;
2793         int i, idx;
2794
2795         for (i = 0; i < AUTO_PIN_LAST; i++) {
2796                 hda_nid_t nid = spec->autocfg.input_pins[i];
2797                 if (! nid)
2798                         continue;
2799                 switch (nid) {
2800                 case 0x15: /* port-C */
2801                         snd_hda_codec_write(codec, 0x33, 0, AC_VERB_SET_CONNECT_SEL, 0x0);
2802                         break;
2803                 case 0x17: /* port-E */
2804                         snd_hda_codec_write(codec, 0x34, 0, AC_VERB_SET_CONNECT_SEL, 0x0);
2805                         break;
2806                 }
2807                 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
2808                                     i <= AUTO_PIN_FRONT_MIC ? PIN_VREF80 : PIN_IN);
2809                 if (nid != AD1988_PIN_CD_NID)
2810                         snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
2811                                             AMP_OUT_MUTE);
2812                 idx = ad1988_pin_idx(nid);
2813                 if (ad1988_boost_nids[idx])
2814                         snd_hda_codec_write(codec, ad1988_boost_nids[idx], 0,
2815                                             AC_VERB_SET_AMP_GAIN_MUTE,
2816                                             AMP_OUT_ZERO);
2817         }
2818 }
2819
2820 /* parse the BIOS configuration and set up the alc_spec */
2821 /* return 1 if successful, 0 if the proper config is not found, or a negative error code */
2822 static int ad1988_parse_auto_config(struct hda_codec *codec)
2823 {
2824         struct ad198x_spec *spec = codec->spec;
2825         int err;
2826
2827         if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL)) < 0)
2828                 return err;
2829         if ((err = ad1988_auto_fill_dac_nids(codec, &spec->autocfg)) < 0)
2830                 return err;
2831         if (! spec->autocfg.line_outs)
2832                 return 0; /* can't find valid BIOS pin config */
2833         if ((err = ad1988_auto_create_multi_out_ctls(spec, &spec->autocfg)) < 0 ||
2834             (err = ad1988_auto_create_extra_out(codec,
2835                                                 spec->autocfg.speaker_pins[0],
2836                                                 "Speaker")) < 0 ||
2837             (err = ad1988_auto_create_extra_out(codec, spec->autocfg.hp_pins[0],
2838                                                 "Headphone")) < 0 ||
2839             (err = ad1988_auto_create_analog_input_ctls(spec, &spec->autocfg)) < 0)
2840                 return err;
2841
2842         spec->multiout.max_channels = spec->multiout.num_dacs * 2;
2843
2844         if (spec->autocfg.dig_out_pin)
2845                 spec->multiout.dig_out_nid = AD1988_SPDIF_OUT;
2846         if (spec->autocfg.dig_in_pin)
2847                 spec->dig_in_nid = AD1988_SPDIF_IN;
2848
2849         if (spec->kctl_alloc)
2850                 spec->mixers[spec->num_mixers++] = spec->kctl_alloc;
2851
2852         spec->init_verbs[spec->num_init_verbs++] = ad1988_6stack_init_verbs;
2853
2854         spec->input_mux = &spec->private_imux;
2855
2856         return 1;
2857 }
2858
2859 /* init callback for auto-configuration model -- overriding the default init */
2860 static int ad1988_auto_init(struct hda_codec *codec)
2861 {
2862         ad198x_init(codec);
2863         ad1988_auto_init_multi_out(codec);
2864         ad1988_auto_init_extra_out(codec);
2865         ad1988_auto_init_analog_input(codec);
2866         return 0;
2867 }
2868
2869
2870 /*
2871  */
2872
2873 static const char *ad1988_models[AD1988_MODEL_LAST] = {
2874         [AD1988_6STACK]         = "6stack",
2875         [AD1988_6STACK_DIG]     = "6stack-dig",
2876         [AD1988_3STACK]         = "3stack",
2877         [AD1988_3STACK_DIG]     = "3stack-dig",
2878         [AD1988_LAPTOP]         = "laptop",
2879         [AD1988_LAPTOP_DIG]     = "laptop-dig",
2880         [AD1988_AUTO]           = "auto",
2881 };
2882
2883 static struct snd_pci_quirk ad1988_cfg_tbl[] = {
2884         SND_PCI_QUIRK(0x1043, 0x81ec, "Asus P5B-DLX", AD1988_6STACK_DIG),
2885         SND_PCI_QUIRK(0x1043, 0x81f6, "Asus M2N-SLI", AD1988_6STACK_DIG),
2886         SND_PCI_QUIRK(0x1043, 0x8277, "Asus P5K-E/WIFI-AP", AD1988_6STACK_DIG),
2887         SND_PCI_QUIRK(0x1043, 0x8311, "Asus P5Q-Premium/Pro", AD1988_6STACK_DIG),
2888         {}
2889 };
2890
2891 static int patch_ad1988(struct hda_codec *codec)
2892 {
2893         struct ad198x_spec *spec;
2894         int board_config;
2895
2896         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
2897         if (spec == NULL)
2898                 return -ENOMEM;
2899
2900         codec->spec = spec;
2901
2902         if (is_rev2(codec))
2903                 snd_printk(KERN_INFO "patch_analog: AD1988A rev.2 is detected, enable workarounds\n");
2904
2905         board_config = snd_hda_check_board_config(codec, AD1988_MODEL_LAST,
2906                                                   ad1988_models, ad1988_cfg_tbl);
2907         if (board_config < 0) {
2908                 printk(KERN_INFO "hda_codec: Unknown model for AD1988, trying auto-probe from BIOS...\n");
2909                 board_config = AD1988_AUTO;
2910         }
2911
2912         if (board_config == AD1988_AUTO) {
2913                 /* automatic parse from the BIOS config */
2914                 int err = ad1988_parse_auto_config(codec);
2915                 if (err < 0) {
2916                         ad198x_free(codec);
2917                         return err;
2918                 } else if (! err) {
2919                         printk(KERN_INFO "hda_codec: Cannot set up configuration from BIOS.  Using 6-stack mode...\n");
2920                         board_config = AD1988_6STACK;
2921                 }
2922         }
2923
2924         switch (board_config) {
2925         case AD1988_6STACK:
2926         case AD1988_6STACK_DIG:
2927                 spec->multiout.max_channels = 8;
2928                 spec->multiout.num_dacs = 4;
2929                 if (is_rev2(codec))
2930                         spec->multiout.dac_nids = ad1988_6stack_dac_nids_rev2;
2931                 else
2932                         spec->multiout.dac_nids = ad1988_6stack_dac_nids;
2933                 spec->input_mux = &ad1988_6stack_capture_source;
2934                 spec->num_mixers = 2;
2935                 if (is_rev2(codec))
2936                         spec->mixers[0] = ad1988_6stack_mixers1_rev2;
2937                 else
2938                         spec->mixers[0] = ad1988_6stack_mixers1;
2939                 spec->mixers[1] = ad1988_6stack_mixers2;
2940                 spec->num_init_verbs = 1;
2941                 spec->init_verbs[0] = ad1988_6stack_init_verbs;
2942                 if (board_config == AD1988_6STACK_DIG) {
2943                         spec->multiout.dig_out_nid = AD1988_SPDIF_OUT;
2944                         spec->dig_in_nid = AD1988_SPDIF_IN;
2945                 }
2946                 break;
2947         case AD1988_3STACK:
2948         case AD1988_3STACK_DIG:
2949                 spec->multiout.max_channels = 6;
2950                 spec->multiout.num_dacs = 3;
2951                 if (is_rev2(codec))
2952                         spec->multiout.dac_nids = ad1988_3stack_dac_nids_rev2;
2953                 else
2954                         spec->multiout.dac_nids = ad1988_3stack_dac_nids;
2955                 spec->input_mux = &ad1988_6stack_capture_source;
2956                 spec->channel_mode = ad1988_3stack_modes;
2957                 spec->num_channel_mode = ARRAY_SIZE(ad1988_3stack_modes);
2958                 spec->num_mixers = 2;
2959                 if (is_rev2(codec))
2960                         spec->mixers[0] = ad1988_3stack_mixers1_rev2;
2961                 else
2962                         spec->mixers[0] = ad1988_3stack_mixers1;
2963                 spec->mixers[1] = ad1988_3stack_mixers2;
2964                 spec->num_init_verbs = 1;
2965                 spec->init_verbs[0] = ad1988_3stack_init_verbs;
2966                 if (board_config == AD1988_3STACK_DIG)
2967                         spec->multiout.dig_out_nid = AD1988_SPDIF_OUT;
2968                 break;
2969         case AD1988_LAPTOP:
2970         case AD1988_LAPTOP_DIG:
2971                 spec->multiout.max_channels = 2;
2972                 spec->multiout.num_dacs = 1;
2973                 spec->multiout.dac_nids = ad1988_3stack_dac_nids;
2974                 spec->input_mux = &ad1988_laptop_capture_source;
2975                 spec->num_mixers = 1;
2976                 spec->mixers[0] = ad1988_laptop_mixers;
2977                 spec->num_init_verbs = 1;
2978                 spec->init_verbs[0] = ad1988_laptop_init_verbs;
2979                 if (board_config == AD1988_LAPTOP_DIG)
2980                         spec->multiout.dig_out_nid = AD1988_SPDIF_OUT;
2981                 break;
2982         }
2983
2984         spec->num_adc_nids = ARRAY_SIZE(ad1988_adc_nids);
2985         spec->adc_nids = ad1988_adc_nids;
2986         spec->capsrc_nids = ad1988_capsrc_nids;
2987         spec->mixers[spec->num_mixers++] = ad1988_capture_mixers;
2988         spec->init_verbs[spec->num_init_verbs++] = ad1988_capture_init_verbs;
2989         if (spec->multiout.dig_out_nid) {
2990                 if (codec->vendor_id >= 0x11d4989a) {
2991                         spec->mixers[spec->num_mixers++] =
2992                                 ad1989_spdif_out_mixers;
2993                         spec->init_verbs[spec->num_init_verbs++] =
2994                                 ad1989_spdif_init_verbs;
2995                         codec->slave_dig_outs = ad1989b_slave_dig_outs;
2996                 } else {
2997                         spec->mixers[spec->num_mixers++] =
2998                                 ad1988_spdif_out_mixers;
2999                         spec->init_verbs[spec->num_init_verbs++] =
3000                                 ad1988_spdif_init_verbs;
3001                 }
3002         }
3003         if (spec->dig_in_nid && codec->vendor_id < 0x11d4989a)
3004                 spec->mixers[spec->num_mixers++] = ad1988_spdif_in_mixers;
3005
3006         codec->patch_ops = ad198x_patch_ops;
3007         switch (board_config) {
3008         case AD1988_AUTO:
3009                 codec->patch_ops.init = ad1988_auto_init;
3010                 break;
3011         case AD1988_LAPTOP:
3012         case AD1988_LAPTOP_DIG:
3013                 codec->patch_ops.unsol_event = ad1988_laptop_unsol_event;
3014                 break;
3015         }
3016 #ifdef CONFIG_SND_HDA_POWER_SAVE
3017         spec->loopback.amplist = ad1988_loopbacks;
3018 #endif
3019         spec->vmaster_nid = 0x04;
3020
3021         return 0;
3022 }
3023
3024
3025 /*
3026  * AD1884 / AD1984
3027  *
3028  * port-B - front line/mic-in
3029  * port-E - aux in/out
3030  * port-F - aux in/out
3031  * port-C - rear line/mic-in
3032  * port-D - rear line/hp-out
3033  * port-A - front line/hp-out
3034  *
3035  * AD1984 = AD1884 + two digital mic-ins
3036  *
3037  * FIXME:
3038  * For simplicity, we share the single DAC for both HP and line-outs
3039  * right now.  The inidividual playbacks could be easily implemented,
3040  * but no build-up framework is given, so far.
3041  */
3042
3043 static hda_nid_t ad1884_dac_nids[1] = {
3044         0x04,
3045 };
3046
3047 static hda_nid_t ad1884_adc_nids[2] = {
3048         0x08, 0x09,
3049 };
3050
3051 static hda_nid_t ad1884_capsrc_nids[2] = {
3052         0x0c, 0x0d,
3053 };
3054
3055 #define AD1884_SPDIF_OUT        0x02
3056
3057 static struct hda_input_mux ad1884_capture_source = {
3058         .num_items = 4,
3059         .items = {
3060                 { "Front Mic", 0x0 },
3061                 { "Mic", 0x1 },
3062                 { "CD", 0x2 },
3063                 { "Mix", 0x3 },
3064         },
3065 };
3066
3067 static struct snd_kcontrol_new ad1884_base_mixers[] = {
3068         HDA_CODEC_VOLUME("PCM Playback Volume", 0x04, 0x0, HDA_OUTPUT),
3069         /* HDA_CODEC_VOLUME_IDX("PCM Playback Volume", 1, 0x03, 0x0, HDA_OUTPUT), */
3070         HDA_CODEC_MUTE("Headphone Playback Switch", 0x11, 0x0, HDA_OUTPUT),
3071         HDA_CODEC_MUTE("Front Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3072         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x13, 1, 0x0, HDA_OUTPUT),
3073         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x13, 1, 0x0, HDA_OUTPUT),
3074         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3075         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3076         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x01, HDA_INPUT),
3077         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x01, HDA_INPUT),
3078         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x02, HDA_INPUT),
3079         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x02, HDA_INPUT),
3080         /*
3081         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x20, 0x03, HDA_INPUT),
3082         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x20, 0x03, HDA_INPUT),
3083         HDA_CODEC_VOLUME("Digital Beep Playback Volume", 0x10, 0x0, HDA_OUTPUT),
3084         HDA_CODEC_MUTE("Digital Beep Playback Switch", 0x10, 0x0, HDA_OUTPUT),
3085         */
3086         HDA_CODEC_VOLUME("Mic Boost", 0x15, 0x0, HDA_INPUT),
3087         HDA_CODEC_VOLUME("Front Mic Boost", 0x14, 0x0, HDA_INPUT),
3088         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3089         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3090         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3091         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3092         {
3093                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3094                 /* The multiple "Capture Source" controls confuse alsamixer
3095                  * So call somewhat different..
3096                  */
3097                 /* .name = "Capture Source", */
3098                 .name = "Input Source",
3099                 .count = 2,
3100                 .info = ad198x_mux_enum_info,
3101                 .get = ad198x_mux_enum_get,
3102                 .put = ad198x_mux_enum_put,
3103         },
3104         /* SPDIF controls */
3105         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
3106         {
3107                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3108                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
3109                 /* identical with ad1983 */
3110                 .info = ad1983_spdif_route_info,
3111                 .get = ad1983_spdif_route_get,
3112                 .put = ad1983_spdif_route_put,
3113         },
3114         { } /* end */
3115 };
3116
3117 static struct snd_kcontrol_new ad1984_dmic_mixers[] = {
3118         HDA_CODEC_VOLUME("Digital Mic Capture Volume", 0x05, 0x0, HDA_INPUT),
3119         HDA_CODEC_MUTE("Digital Mic Capture Switch", 0x05, 0x0, HDA_INPUT),
3120         HDA_CODEC_VOLUME_IDX("Digital Mic Capture Volume", 1, 0x06, 0x0,
3121                              HDA_INPUT),
3122         HDA_CODEC_MUTE_IDX("Digital Mic Capture Switch", 1, 0x06, 0x0,
3123                            HDA_INPUT),
3124         { } /* end */
3125 };
3126
3127 /*
3128  * initialization verbs
3129  */
3130 static struct hda_verb ad1884_init_verbs[] = {
3131         /* DACs; mute as default */
3132         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3133         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
3134         /* Port-A (HP) mixer */
3135         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3136         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3137         /* Port-A pin */
3138         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3139         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3140         /* HP selector - select DAC2 */
3141         {0x22, AC_VERB_SET_CONNECT_SEL, 0x1},
3142         /* Port-D (Line-out) mixer */
3143         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3144         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3145         /* Port-D pin */
3146         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3147         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3148         /* Mono-out mixer */
3149         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
3150         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3151         /* Mono-out pin */
3152         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3153         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3154         /* Mono selector */
3155         {0x0e, AC_VERB_SET_CONNECT_SEL, 0x1},
3156         /* Port-B (front mic) pin */
3157         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3158         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3159         /* Port-C (rear mic) pin */
3160         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3161         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3162         /* Analog mixer; mute as default */
3163         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3164         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3165         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
3166         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
3167         /* Analog Mix output amp */
3168         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x1f}, /* 0dB */
3169         /* SPDIF output selector */
3170         {0x02, AC_VERB_SET_CONNECT_SEL, 0x0}, /* PCM */
3171         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
3172         { } /* end */
3173 };
3174
3175 #ifdef CONFIG_SND_HDA_POWER_SAVE
3176 static struct hda_amp_list ad1884_loopbacks[] = {
3177         { 0x20, HDA_INPUT, 0 }, /* Front Mic */
3178         { 0x20, HDA_INPUT, 1 }, /* Mic */
3179         { 0x20, HDA_INPUT, 2 }, /* CD */
3180         { 0x20, HDA_INPUT, 4 }, /* Docking */
3181         { } /* end */
3182 };
3183 #endif
3184
3185 static const char *ad1884_slave_vols[] = {
3186         "PCM Playback Volume",
3187         "Mic Playback Volume",
3188         "Mono Playback Volume",
3189         "Front Mic Playback Volume",
3190         "Mic Playback Volume",
3191         "CD Playback Volume",
3192         "Internal Mic Playback Volume",
3193         "Docking Mic Playback Volume"
3194         "Beep Playback Volume",
3195         "IEC958 Playback Volume",
3196         NULL
3197 };
3198
3199 static int patch_ad1884(struct hda_codec *codec)
3200 {
3201         struct ad198x_spec *spec;
3202
3203         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
3204         if (spec == NULL)
3205                 return -ENOMEM;
3206
3207         codec->spec = spec;
3208
3209         spec->multiout.max_channels = 2;
3210         spec->multiout.num_dacs = ARRAY_SIZE(ad1884_dac_nids);
3211         spec->multiout.dac_nids = ad1884_dac_nids;
3212         spec->multiout.dig_out_nid = AD1884_SPDIF_OUT;
3213         spec->num_adc_nids = ARRAY_SIZE(ad1884_adc_nids);
3214         spec->adc_nids = ad1884_adc_nids;
3215         spec->capsrc_nids = ad1884_capsrc_nids;
3216         spec->input_mux = &ad1884_capture_source;
3217         spec->num_mixers = 1;
3218         spec->mixers[0] = ad1884_base_mixers;
3219         spec->num_init_verbs = 1;
3220         spec->init_verbs[0] = ad1884_init_verbs;
3221         spec->spdif_route = 0;
3222 #ifdef CONFIG_SND_HDA_POWER_SAVE
3223         spec->loopback.amplist = ad1884_loopbacks;
3224 #endif
3225         spec->vmaster_nid = 0x04;
3226         /* we need to cover all playback volumes */
3227         spec->slave_vols = ad1884_slave_vols;
3228
3229         codec->patch_ops = ad198x_patch_ops;
3230
3231         return 0;
3232 }
3233
3234 /*
3235  * Lenovo Thinkpad T61/X61
3236  */
3237 static struct hda_input_mux ad1984_thinkpad_capture_source = {
3238         .num_items = 4,
3239         .items = {
3240                 { "Mic", 0x0 },
3241                 { "Internal Mic", 0x1 },
3242                 { "Mix", 0x3 },
3243                 { "Docking-Station", 0x4 },
3244         },
3245 };
3246
3247
3248 /*
3249  * Dell Precision T3400
3250  */
3251 static struct hda_input_mux ad1984_dell_desktop_capture_source = {
3252         .num_items = 3,
3253         .items = {
3254                 { "Front Mic", 0x0 },
3255                 { "Line-In", 0x1 },
3256                 { "Mix", 0x3 },
3257         },
3258 };
3259
3260
3261 static struct snd_kcontrol_new ad1984_thinkpad_mixers[] = {
3262         HDA_CODEC_VOLUME("PCM Playback Volume", 0x04, 0x0, HDA_OUTPUT),
3263         /* HDA_CODEC_VOLUME_IDX("PCM Playback Volume", 1, 0x03, 0x0, HDA_OUTPUT), */
3264         HDA_CODEC_MUTE("Headphone Playback Switch", 0x11, 0x0, HDA_OUTPUT),
3265         HDA_CODEC_MUTE("Speaker Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3266         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3267         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3268         HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x20, 0x01, HDA_INPUT),
3269         HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x20, 0x01, HDA_INPUT),
3270         HDA_CODEC_VOLUME("Docking Mic Playback Volume", 0x20, 0x04, HDA_INPUT),
3271         HDA_CODEC_MUTE("Docking Mic Playback Switch", 0x20, 0x04, HDA_INPUT),
3272         HDA_CODEC_VOLUME("Mic Boost", 0x14, 0x0, HDA_INPUT),
3273         HDA_CODEC_VOLUME("Internal Mic Boost", 0x15, 0x0, HDA_INPUT),
3274         HDA_CODEC_VOLUME("Docking Mic Boost", 0x25, 0x0, HDA_OUTPUT),
3275         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x03, HDA_INPUT),
3276         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x03, HDA_INPUT),
3277         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3278         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3279         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3280         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3281         {
3282                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3283                 /* The multiple "Capture Source" controls confuse alsamixer
3284                  * So call somewhat different..
3285                  */
3286                 /* .name = "Capture Source", */
3287                 .name = "Input Source",
3288                 .count = 2,
3289                 .info = ad198x_mux_enum_info,
3290                 .get = ad198x_mux_enum_get,
3291                 .put = ad198x_mux_enum_put,
3292         },
3293         /* SPDIF controls */
3294         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
3295         {
3296                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3297                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
3298                 /* identical with ad1983 */
3299                 .info = ad1983_spdif_route_info,
3300                 .get = ad1983_spdif_route_get,
3301                 .put = ad1983_spdif_route_put,
3302         },
3303         { } /* end */
3304 };
3305
3306 /* additional verbs */
3307 static struct hda_verb ad1984_thinkpad_init_verbs[] = {
3308         /* Port-E (docking station mic) pin */
3309         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3310         {0x1c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3311         /* docking mic boost */
3312         {0x25, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3313         /* Analog mixer - docking mic; mute as default */
3314         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
3315         /* enable EAPD bit */
3316         {0x12, AC_VERB_SET_EAPD_BTLENABLE, 0x02},
3317         { } /* end */
3318 };
3319
3320 /*
3321  * Dell Precision T3400
3322  */
3323 static struct snd_kcontrol_new ad1984_dell_desktop_mixers[] = {
3324         HDA_CODEC_VOLUME("PCM Playback Volume", 0x04, 0x0, HDA_OUTPUT),
3325         HDA_CODEC_MUTE("Headphone Playback Switch", 0x11, 0x0, HDA_OUTPUT),
3326         HDA_CODEC_MUTE("Speaker Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3327         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x13, 1, 0x0, HDA_OUTPUT),
3328         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x13, 1, 0x0, HDA_OUTPUT),
3329         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3330         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3331         HDA_CODEC_VOLUME("Line-In Playback Volume", 0x20, 0x01, HDA_INPUT),
3332         HDA_CODEC_MUTE("Line-In Playback Switch", 0x20, 0x01, HDA_INPUT),
3333         /*
3334         HDA_CODEC_VOLUME("PC Speaker Playback Volume", 0x20, 0x03, HDA_INPUT),
3335         HDA_CODEC_MUTE("PC Speaker Playback Switch", 0x20, 0x03, HDA_INPUT),
3336         */
3337         HDA_CODEC_VOLUME("Line-In Boost", 0x15, 0x0, HDA_INPUT),
3338         HDA_CODEC_VOLUME("Front Mic Boost", 0x14, 0x0, HDA_INPUT),
3339         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3340         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3341         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3342         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3343         {
3344                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3345                 /* The multiple "Capture Source" controls confuse alsamixer
3346                  * So call somewhat different..
3347                  */
3348                 /* .name = "Capture Source", */
3349                 .name = "Input Source",
3350                 .count = 2,
3351                 .info = ad198x_mux_enum_info,
3352                 .get = ad198x_mux_enum_get,
3353                 .put = ad198x_mux_enum_put,
3354         },
3355         { } /* end */
3356 };
3357
3358 /* Digial MIC ADC NID 0x05 + 0x06 */
3359 static int ad1984_pcm_dmic_prepare(struct hda_pcm_stream *hinfo,
3360                                    struct hda_codec *codec,
3361                                    unsigned int stream_tag,
3362                                    unsigned int format,
3363                                    struct snd_pcm_substream *substream)
3364 {
3365         snd_hda_codec_setup_stream(codec, 0x05 + substream->number,
3366                                    stream_tag, 0, format);
3367         return 0;
3368 }
3369
3370 static int ad1984_pcm_dmic_cleanup(struct hda_pcm_stream *hinfo,
3371                                    struct hda_codec *codec,
3372                                    struct snd_pcm_substream *substream)
3373 {
3374         snd_hda_codec_cleanup_stream(codec, 0x05 + substream->number);
3375         return 0;
3376 }
3377
3378 static struct hda_pcm_stream ad1984_pcm_dmic_capture = {
3379         .substreams = 2,
3380         .channels_min = 2,
3381         .channels_max = 2,
3382         .nid = 0x05,
3383         .ops = {
3384                 .prepare = ad1984_pcm_dmic_prepare,
3385                 .cleanup = ad1984_pcm_dmic_cleanup
3386         },
3387 };
3388
3389 static int ad1984_build_pcms(struct hda_codec *codec)
3390 {
3391         struct ad198x_spec *spec = codec->spec;
3392         struct hda_pcm *info;
3393         int err;
3394
3395         err = ad198x_build_pcms(codec);
3396         if (err < 0)
3397                 return err;
3398
3399         info = spec->pcm_rec + codec->num_pcms;
3400         codec->num_pcms++;
3401         info->name = "AD1984 Digital Mic";
3402         info->stream[SNDRV_PCM_STREAM_CAPTURE] = ad1984_pcm_dmic_capture;
3403         return 0;
3404 }
3405
3406 /* models */
3407 enum {
3408         AD1984_BASIC,
3409         AD1984_THINKPAD,
3410         AD1984_DELL_DESKTOP,
3411         AD1984_MODELS
3412 };
3413
3414 static const char *ad1984_models[AD1984_MODELS] = {
3415         [AD1984_BASIC]          = "basic",
3416         [AD1984_THINKPAD]       = "thinkpad",
3417         [AD1984_DELL_DESKTOP]   = "dell_desktop",
3418 };
3419
3420 static struct snd_pci_quirk ad1984_cfg_tbl[] = {
3421         /* Lenovo Thinkpad T61/X61 */
3422         SND_PCI_QUIRK(0x17aa, 0, "Lenovo Thinkpad", AD1984_THINKPAD),
3423         SND_PCI_QUIRK(0x1028, 0x0214, "Dell T3400", AD1984_DELL_DESKTOP),
3424         {}
3425 };
3426
3427 static int patch_ad1984(struct hda_codec *codec)
3428 {
3429         struct ad198x_spec *spec;
3430         int board_config, err;
3431
3432         err = patch_ad1884(codec);
3433         if (err < 0)
3434                 return err;
3435         spec = codec->spec;
3436         board_config = snd_hda_check_board_config(codec, AD1984_MODELS,
3437                                                   ad1984_models, ad1984_cfg_tbl);
3438         switch (board_config) {
3439         case AD1984_BASIC:
3440                 /* additional digital mics */
3441                 spec->mixers[spec->num_mixers++] = ad1984_dmic_mixers;
3442                 codec->patch_ops.build_pcms = ad1984_build_pcms;
3443                 break;
3444         case AD1984_THINKPAD:
3445                 spec->multiout.dig_out_nid = AD1884_SPDIF_OUT;
3446                 spec->input_mux = &ad1984_thinkpad_capture_source;
3447                 spec->mixers[0] = ad1984_thinkpad_mixers;
3448                 spec->init_verbs[spec->num_init_verbs++] = ad1984_thinkpad_init_verbs;
3449                 break;
3450         case AD1984_DELL_DESKTOP:
3451                 spec->multiout.dig_out_nid = 0;
3452                 spec->input_mux = &ad1984_dell_desktop_capture_source;
3453                 spec->mixers[0] = ad1984_dell_desktop_mixers;
3454                 break;
3455         }
3456         return 0;
3457 }
3458
3459
3460 /*
3461  * AD1883 / AD1884A / AD1984A / AD1984B
3462  *
3463  * port-B (0x14) - front mic-in
3464  * port-E (0x1c) - rear mic-in
3465  * port-F (0x16) - CD / ext out
3466  * port-C (0x15) - rear line-in
3467  * port-D (0x12) - rear line-out
3468  * port-A (0x11) - front hp-out
3469  *
3470  * AD1984A = AD1884A + digital-mic
3471  * AD1883 = equivalent with AD1984A
3472  * AD1984B = AD1984A + extra SPDIF-out
3473  *
3474  * FIXME:
3475  * We share the single DAC for both HP and line-outs (see AD1884/1984).
3476  */
3477
3478 static hda_nid_t ad1884a_dac_nids[1] = {
3479         0x03,
3480 };
3481
3482 #define ad1884a_adc_nids        ad1884_adc_nids
3483 #define ad1884a_capsrc_nids     ad1884_capsrc_nids
3484
3485 #define AD1884A_SPDIF_OUT       0x02
3486
3487 static struct hda_input_mux ad1884a_capture_source = {
3488         .num_items = 5,
3489         .items = {
3490                 { "Front Mic", 0x0 },
3491                 { "Mic", 0x4 },
3492                 { "Line", 0x1 },
3493                 { "CD", 0x2 },
3494                 { "Mix", 0x3 },
3495         },
3496 };
3497
3498 static struct snd_kcontrol_new ad1884a_base_mixers[] = {
3499         HDA_CODEC_VOLUME("Master Playback Volume", 0x21, 0x0, HDA_OUTPUT),
3500         HDA_CODEC_MUTE("Master Playback Switch", 0x21, 0x0, HDA_OUTPUT),
3501         HDA_CODEC_MUTE("Headphone Playback Switch", 0x11, 0x0, HDA_OUTPUT),
3502         HDA_CODEC_MUTE("Front Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3503         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x13, 1, 0x0, HDA_OUTPUT),
3504         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x13, 1, 0x0, HDA_OUTPUT),
3505         HDA_CODEC_VOLUME("PCM Playback Volume", 0x20, 0x5, HDA_INPUT),
3506         HDA_CODEC_MUTE("PCM Playback Switch", 0x20, 0x5, HDA_INPUT),
3507         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3508         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3509         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x01, HDA_INPUT),
3510         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x01, HDA_INPUT),
3511         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x04, HDA_INPUT),
3512         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x04, HDA_INPUT),
3513         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x02, HDA_INPUT),
3514         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x02, HDA_INPUT),
3515         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x03, HDA_INPUT),
3516         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x03, HDA_INPUT),
3517         HDA_CODEC_VOLUME("Front Mic Boost", 0x14, 0x0, HDA_INPUT),
3518         HDA_CODEC_VOLUME("Line Boost", 0x15, 0x0, HDA_INPUT),
3519         HDA_CODEC_VOLUME("Mic Boost", 0x25, 0x0, HDA_OUTPUT),
3520         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3521         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3522         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3523         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3524         {
3525                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3526                 /* The multiple "Capture Source" controls confuse alsamixer
3527                  * So call somewhat different..
3528                  */
3529                 /* .name = "Capture Source", */
3530                 .name = "Input Source",
3531                 .count = 2,
3532                 .info = ad198x_mux_enum_info,
3533                 .get = ad198x_mux_enum_get,
3534                 .put = ad198x_mux_enum_put,
3535         },
3536         /* SPDIF controls */
3537         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
3538         {
3539                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3540                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
3541                 /* identical with ad1983 */
3542                 .info = ad1983_spdif_route_info,
3543                 .get = ad1983_spdif_route_get,
3544                 .put = ad1983_spdif_route_put,
3545         },
3546         { } /* end */
3547 };
3548
3549 /*
3550  * initialization verbs
3551  */
3552 static struct hda_verb ad1884a_init_verbs[] = {
3553         /* DACs; unmute as default */
3554         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, 0x27}, /* 0dB */
3555         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, 0x27}, /* 0dB */
3556         /* Port-A (HP) mixer - route only from analog mixer */
3557         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3558         {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3559         /* Port-A pin */
3560         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3561         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3562         /* Port-D (Line-out) mixer - route only from analog mixer */
3563         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3564         {0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3565         /* Port-D pin */
3566         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3567         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3568         /* Mono-out mixer - route only from analog mixer */
3569         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3570         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3571         /* Mono-out pin */
3572         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3573         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3574         /* Port-B (front mic) pin */
3575         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3576         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3577         /* Port-C (rear line-in) pin */
3578         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3579         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3580         /* Port-E (rear mic) pin */
3581         {0x1c, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3582         {0x1c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3583         {0x25, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, /* no boost */
3584         /* Port-F (CD) pin */
3585         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3586         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3587         /* Analog mixer; mute as default */
3588         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3589         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
3590         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
3591         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
3592         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)}, /* aux */
3593         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)},
3594         /* Analog Mix output amp */
3595         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3596         /* capture sources */
3597         {0x0c, AC_VERB_SET_CONNECT_SEL, 0x0},
3598         {0x0c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3599         {0x0d, AC_VERB_SET_CONNECT_SEL, 0x0},
3600         {0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3601         /* SPDIF output amp */
3602         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
3603         { } /* end */
3604 };
3605
3606 #ifdef CONFIG_SND_HDA_POWER_SAVE
3607 static struct hda_amp_list ad1884a_loopbacks[] = {
3608         { 0x20, HDA_INPUT, 0 }, /* Front Mic */
3609         { 0x20, HDA_INPUT, 1 }, /* Mic */
3610         { 0x20, HDA_INPUT, 2 }, /* CD */
3611         { 0x20, HDA_INPUT, 4 }, /* Docking */
3612         { } /* end */
3613 };
3614 #endif
3615
3616 /*
3617  * Laptop model
3618  *
3619  * Port A: Headphone jack
3620  * Port B: MIC jack
3621  * Port C: Internal MIC
3622  * Port D: Dock Line Out (if enabled)
3623  * Port E: Dock Line In (if enabled)
3624  * Port F: Internal speakers
3625  */
3626
3627 static struct hda_input_mux ad1884a_laptop_capture_source = {
3628         .num_items = 4,
3629         .items = {
3630                 { "Mic", 0x0 },         /* port-B */
3631                 { "Internal Mic", 0x1 }, /* port-C */
3632                 { "Dock Mic", 0x4 },    /* port-E */
3633                 { "Mix", 0x3 },
3634         },
3635 };
3636
3637 static struct snd_kcontrol_new ad1884a_laptop_mixers[] = {
3638         HDA_CODEC_VOLUME("Master Playback Volume", 0x21, 0x0, HDA_OUTPUT),
3639         HDA_CODEC_MUTE("Master Playback Switch", 0x21, 0x0, HDA_OUTPUT),
3640         HDA_CODEC_MUTE("Dock Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3641         HDA_CODEC_VOLUME("PCM Playback Volume", 0x20, 0x5, HDA_INPUT),
3642         HDA_CODEC_MUTE("PCM Playback Switch", 0x20, 0x5, HDA_INPUT),
3643         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3644         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3645         HDA_CODEC_VOLUME("Internal Mic Playback Volume", 0x20, 0x01, HDA_INPUT),
3646         HDA_CODEC_MUTE("Internal Mic Playback Switch", 0x20, 0x01, HDA_INPUT),
3647         HDA_CODEC_VOLUME("Dock Mic Playback Volume", 0x20, 0x04, HDA_INPUT),
3648         HDA_CODEC_MUTE("Dock Mic Playback Switch", 0x20, 0x04, HDA_INPUT),
3649         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x03, HDA_INPUT),
3650         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x03, HDA_INPUT),
3651         HDA_CODEC_VOLUME("Mic Boost", 0x14, 0x0, HDA_INPUT),
3652         HDA_CODEC_VOLUME("Internal Mic Boost", 0x15, 0x0, HDA_INPUT),
3653         HDA_CODEC_VOLUME("Dock Mic Boost", 0x25, 0x0, HDA_OUTPUT),
3654         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3655         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3656         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3657         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3658         {
3659                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3660                 /* The multiple "Capture Source" controls confuse alsamixer
3661                  * So call somewhat different..
3662                  */
3663                 /* .name = "Capture Source", */
3664                 .name = "Input Source",
3665                 .count = 2,
3666                 .info = ad198x_mux_enum_info,
3667                 .get = ad198x_mux_enum_get,
3668                 .put = ad198x_mux_enum_put,
3669         },
3670         { } /* end */
3671 };
3672
3673 static struct snd_kcontrol_new ad1884a_mobile_mixers[] = {
3674         HDA_CODEC_VOLUME("Master Playback Volume", 0x21, 0x0, HDA_OUTPUT),
3675         HDA_CODEC_MUTE("Master Playback Switch", 0x21, 0x0, HDA_OUTPUT),
3676         HDA_CODEC_VOLUME("PCM Playback Volume", 0x20, 0x5, HDA_INPUT),
3677         HDA_CODEC_MUTE("PCM Playback Switch", 0x20, 0x5, HDA_INPUT),
3678         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x03, HDA_INPUT),
3679         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x03, HDA_INPUT),
3680         HDA_CODEC_VOLUME("Mic Capture Volume", 0x14, 0x0, HDA_INPUT),
3681         HDA_CODEC_VOLUME("Internal Mic Capture Volume", 0x15, 0x0, HDA_INPUT),
3682         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3683         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3684         { } /* end */
3685 };
3686
3687 /* mute internal speaker if HP is plugged */
3688 static void ad1884a_hp_automute(struct hda_codec *codec)
3689 {
3690         unsigned int present;
3691
3692         present = snd_hda_codec_read(codec, 0x11, 0,
3693                                      AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
3694         snd_hda_codec_amp_stereo(codec, 0x16, HDA_OUTPUT, 0,
3695                                  HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0);
3696         snd_hda_codec_write(codec, 0x16, 0, AC_VERB_SET_EAPD_BTLENABLE,
3697                             present ? 0x00 : 0x02);
3698 }
3699
3700 /* switch to external mic if plugged */
3701 static void ad1884a_hp_automic(struct hda_codec *codec)
3702 {
3703         unsigned int present;
3704
3705         present = snd_hda_codec_read(codec, 0x14, 0,
3706                                      AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
3707         snd_hda_codec_write(codec, 0x0c, 0, AC_VERB_SET_CONNECT_SEL,
3708                             present ? 0 : 1);
3709 }
3710
3711 #define AD1884A_HP_EVENT                0x37
3712 #define AD1884A_MIC_EVENT               0x36
3713
3714 /* unsolicited event for HP jack sensing */
3715 static void ad1884a_hp_unsol_event(struct hda_codec *codec, unsigned int res)
3716 {
3717         switch (res >> 26) {
3718         case AD1884A_HP_EVENT:
3719                 ad1884a_hp_automute(codec);
3720                 break;
3721         case AD1884A_MIC_EVENT:
3722                 ad1884a_hp_automic(codec);
3723                 break;
3724         }
3725 }
3726
3727 /* initialize jack-sensing, too */
3728 static int ad1884a_hp_init(struct hda_codec *codec)
3729 {
3730         ad198x_init(codec);
3731         ad1884a_hp_automute(codec);
3732         ad1884a_hp_automic(codec);
3733         return 0;
3734 }
3735
3736 /* additional verbs for laptop model */
3737 static struct hda_verb ad1884a_laptop_verbs[] = {
3738         /* Port-A (HP) pin - always unmuted */
3739         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3740         /* Port-F (int speaker) mixer - route only from analog mixer */
3741         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
3742         {0x0b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
3743         /* Port-F pin */
3744         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
3745         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
3746         /* Port-C pin - internal mic-in */
3747         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
3748         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, 0x7002}, /* raise mic as default */
3749         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, 0x7002}, /* raise mic as default */
3750         /* analog mix */
3751         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
3752         /* unsolicited event for pin-sense */
3753         {0x11, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1884A_HP_EVENT},
3754         {0x14, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1884A_MIC_EVENT},
3755         { } /* end */
3756 };
3757
3758 /*
3759  * Thinkpad X300
3760  * 0x11 - HP
3761  * 0x12 - speaker
3762  * 0x14 - mic-in
3763  * 0x17 - built-in mic
3764  */
3765
3766 static struct hda_verb ad1984a_thinkpad_verbs[] = {
3767         /* HP unmute */
3768         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE},
3769         /* analog mix */
3770         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
3771         /* turn on EAPD */
3772         {0x12, AC_VERB_SET_EAPD_BTLENABLE, 0x02},
3773         /* unsolicited event for pin-sense */
3774         {0x11, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | AD1884A_HP_EVENT},
3775         /* internal mic - dmic */
3776         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
3777         /* set magic COEFs for dmic */
3778         {0x01, AC_VERB_SET_COEF_INDEX, 0x13f7},
3779         {0x01, AC_VERB_SET_PROC_COEF, 0x08},
3780         { } /* end */
3781 };
3782
3783 static struct snd_kcontrol_new ad1984a_thinkpad_mixers[] = {
3784         HDA_CODEC_VOLUME("Master Playback Volume", 0x21, 0x0, HDA_OUTPUT),
3785         HDA_CODEC_MUTE("Master Playback Switch", 0x21, 0x0, HDA_OUTPUT),
3786         HDA_CODEC_VOLUME("PCM Playback Volume", 0x20, 0x5, HDA_INPUT),
3787         HDA_CODEC_MUTE("PCM Playback Switch", 0x20, 0x5, HDA_INPUT),
3788         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
3789         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
3790         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x03, HDA_INPUT),
3791         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x03, HDA_INPUT),
3792         HDA_CODEC_VOLUME("Mic Boost", 0x14, 0x0, HDA_INPUT),
3793         HDA_CODEC_VOLUME("Internal Mic Boost", 0x17, 0x0, HDA_INPUT),
3794         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3795         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3796         {
3797                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3798                 .name = "Capture Source",
3799                 .info = ad198x_mux_enum_info,
3800                 .get = ad198x_mux_enum_get,
3801                 .put = ad198x_mux_enum_put,
3802         },
3803         { } /* end */
3804 };
3805
3806 static struct hda_input_mux ad1984a_thinkpad_capture_source = {
3807         .num_items = 3,
3808         .items = {
3809                 { "Mic", 0x0 },
3810                 { "Internal Mic", 0x5 },
3811                 { "Mix", 0x3 },
3812         },
3813 };
3814
3815 /* mute internal speaker if HP is plugged */
3816 static void ad1984a_thinkpad_automute(struct hda_codec *codec)
3817 {
3818         unsigned int present;
3819
3820         present = snd_hda_codec_read(codec, 0x11, 0, AC_VERB_GET_PIN_SENSE, 0)
3821                 & AC_PINSENSE_PRESENCE;
3822         snd_hda_codec_amp_stereo(codec, 0x12, HDA_OUTPUT, 0,
3823                                  HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0);
3824 }
3825
3826 /* unsolicited event for HP jack sensing */
3827 static void ad1984a_thinkpad_unsol_event(struct hda_codec *codec,
3828                                          unsigned int res)
3829 {
3830         if ((res >> 26) != AD1884A_HP_EVENT)
3831                 return;
3832         ad1984a_thinkpad_automute(codec);
3833 }
3834
3835 /* initialize jack-sensing, too */
3836 static int ad1984a_thinkpad_init(struct hda_codec *codec)
3837 {
3838         ad198x_init(codec);
3839         ad1984a_thinkpad_automute(codec);
3840         return 0;
3841 }
3842
3843 /*
3844  */
3845
3846 enum {
3847         AD1884A_DESKTOP,
3848         AD1884A_LAPTOP,
3849         AD1884A_MOBILE,
3850         AD1884A_THINKPAD,
3851         AD1884A_MODELS
3852 };
3853
3854 static const char *ad1884a_models[AD1884A_MODELS] = {
3855         [AD1884A_DESKTOP]       = "desktop",
3856         [AD1884A_LAPTOP]        = "laptop",
3857         [AD1884A_MOBILE]        = "mobile",
3858         [AD1884A_THINKPAD]      = "thinkpad",
3859 };
3860
3861 static struct snd_pci_quirk ad1884a_cfg_tbl[] = {
3862         SND_PCI_QUIRK(0x103c, 0x3030, "HP", AD1884A_MOBILE),
3863         SND_PCI_QUIRK(0x103c, 0x3056, "HP", AD1884A_MOBILE),
3864         SND_PCI_QUIRK(0x17aa, 0x20ac, "Thinkpad X300", AD1884A_THINKPAD),
3865         {}
3866 };
3867
3868 static int patch_ad1884a(struct hda_codec *codec)
3869 {
3870         struct ad198x_spec *spec;
3871         int board_config;
3872
3873         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
3874         if (spec == NULL)
3875                 return -ENOMEM;
3876
3877         codec->spec = spec;
3878
3879         spec->multiout.max_channels = 2;
3880         spec->multiout.num_dacs = ARRAY_SIZE(ad1884a_dac_nids);
3881         spec->multiout.dac_nids = ad1884a_dac_nids;
3882         spec->multiout.dig_out_nid = AD1884A_SPDIF_OUT;
3883         spec->num_adc_nids = ARRAY_SIZE(ad1884a_adc_nids);
3884         spec->adc_nids = ad1884a_adc_nids;
3885         spec->capsrc_nids = ad1884a_capsrc_nids;
3886         spec->input_mux = &ad1884a_capture_source;
3887         spec->num_mixers = 1;
3888         spec->mixers[0] = ad1884a_base_mixers;
3889         spec->num_init_verbs = 1;
3890         spec->init_verbs[0] = ad1884a_init_verbs;
3891         spec->spdif_route = 0;
3892 #ifdef CONFIG_SND_HDA_POWER_SAVE
3893         spec->loopback.amplist = ad1884a_loopbacks;
3894 #endif
3895         codec->patch_ops = ad198x_patch_ops;
3896
3897         /* override some parameters */
3898         board_config = snd_hda_check_board_config(codec, AD1884A_MODELS,
3899                                                   ad1884a_models,
3900                                                   ad1884a_cfg_tbl);
3901         switch (board_config) {
3902         case AD1884A_LAPTOP:
3903                 spec->mixers[0] = ad1884a_laptop_mixers;
3904                 spec->init_verbs[spec->num_init_verbs++] = ad1884a_laptop_verbs;
3905                 spec->multiout.dig_out_nid = 0;
3906                 spec->input_mux = &ad1884a_laptop_capture_source;
3907                 codec->patch_ops.unsol_event = ad1884a_hp_unsol_event;
3908                 codec->patch_ops.init = ad1884a_hp_init;
3909                 break;
3910         case AD1884A_MOBILE:
3911                 spec->mixers[0] = ad1884a_mobile_mixers;
3912                 spec->init_verbs[spec->num_init_verbs++] = ad1884a_laptop_verbs;
3913                 spec->multiout.dig_out_nid = 0;
3914                 codec->patch_ops.unsol_event = ad1884a_hp_unsol_event;
3915                 codec->patch_ops.init = ad1884a_hp_init;
3916                 break;
3917         case AD1884A_THINKPAD:
3918                 spec->mixers[0] = ad1984a_thinkpad_mixers;
3919                 spec->init_verbs[spec->num_init_verbs++] =
3920                         ad1984a_thinkpad_verbs;
3921                 spec->multiout.dig_out_nid = 0;
3922                 spec->input_mux = &ad1984a_thinkpad_capture_source;
3923                 codec->patch_ops.unsol_event = ad1984a_thinkpad_unsol_event;
3924                 codec->patch_ops.init = ad1984a_thinkpad_init;
3925                 break;
3926         }
3927
3928         return 0;
3929 }
3930
3931
3932 /*
3933  * AD1882 / AD1882A
3934  *
3935  * port-A - front hp-out
3936  * port-B - front mic-in
3937  * port-C - rear line-in, shared surr-out (3stack)
3938  * port-D - rear line-out
3939  * port-E - rear mic-in, shared clfe-out (3stack)
3940  * port-F - rear surr-out (6stack)
3941  * port-G - rear clfe-out (6stack)
3942  */
3943
3944 static hda_nid_t ad1882_dac_nids[3] = {
3945         0x04, 0x03, 0x05
3946 };
3947
3948 static hda_nid_t ad1882_adc_nids[2] = {
3949         0x08, 0x09,
3950 };
3951
3952 static hda_nid_t ad1882_capsrc_nids[2] = {
3953         0x0c, 0x0d,
3954 };
3955
3956 #define AD1882_SPDIF_OUT        0x02
3957
3958 /* list: 0x11, 0x39, 0x3a, 0x18, 0x3c, 0x3b, 0x12, 0x20 */
3959 static struct hda_input_mux ad1882_capture_source = {
3960         .num_items = 5,
3961         .items = {
3962                 { "Front Mic", 0x1 },
3963                 { "Mic", 0x4 },
3964                 { "Line", 0x2 },
3965                 { "CD", 0x3 },
3966                 { "Mix", 0x7 },
3967         },
3968 };
3969
3970 /* list: 0x11, 0x39, 0x3a, 0x3c, 0x18, 0x1f, 0x12, 0x20 */
3971 static struct hda_input_mux ad1882a_capture_source = {
3972         .num_items = 5,
3973         .items = {
3974                 { "Front Mic", 0x1 },
3975                 { "Mic", 0x4},
3976                 { "Line", 0x2 },
3977                 { "Digital Mic", 0x06 },
3978                 { "Mix", 0x7 },
3979         },
3980 };
3981
3982 static struct snd_kcontrol_new ad1882_base_mixers[] = {
3983         HDA_CODEC_VOLUME("Front Playback Volume", 0x04, 0x0, HDA_OUTPUT),
3984         HDA_CODEC_VOLUME("Surround Playback Volume", 0x03, 0x0, HDA_OUTPUT),
3985         HDA_CODEC_VOLUME_MONO("Center Playback Volume", 0x05, 1, 0x0, HDA_OUTPUT),
3986         HDA_CODEC_VOLUME_MONO("LFE Playback Volume", 0x05, 2, 0x0, HDA_OUTPUT),
3987         HDA_CODEC_MUTE("Headphone Playback Switch", 0x11, 0x0, HDA_OUTPUT),
3988         HDA_CODEC_MUTE("Front Playback Switch", 0x12, 0x0, HDA_OUTPUT),
3989         HDA_CODEC_VOLUME_MONO("Mono Playback Volume", 0x13, 1, 0x0, HDA_OUTPUT),
3990         HDA_CODEC_MUTE_MONO("Mono Playback Switch", 0x13, 1, 0x0, HDA_OUTPUT),
3991
3992         HDA_CODEC_VOLUME("Mic Boost", 0x3c, 0x0, HDA_OUTPUT),
3993         HDA_CODEC_VOLUME("Front Mic Boost", 0x39, 0x0, HDA_OUTPUT),
3994         HDA_CODEC_VOLUME("Line-In Boost", 0x3a, 0x0, HDA_OUTPUT),
3995         HDA_CODEC_VOLUME("Capture Volume", 0x0c, 0x0, HDA_OUTPUT),
3996         HDA_CODEC_MUTE("Capture Switch", 0x0c, 0x0, HDA_OUTPUT),
3997         HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x0d, 0x0, HDA_OUTPUT),
3998         HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x0d, 0x0, HDA_OUTPUT),
3999         {
4000                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4001                 /* The multiple "Capture Source" controls confuse alsamixer
4002                  * So call somewhat different..
4003                  */
4004                 /* .name = "Capture Source", */
4005                 .name = "Input Source",
4006                 .count = 2,
4007                 .info = ad198x_mux_enum_info,
4008                 .get = ad198x_mux_enum_get,
4009                 .put = ad198x_mux_enum_put,
4010         },
4011         /* SPDIF controls */
4012         HDA_CODEC_VOLUME("IEC958 Playback Volume", 0x1b, 0x0, HDA_OUTPUT),
4013         {
4014                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4015                 .name = SNDRV_CTL_NAME_IEC958("",PLAYBACK,NONE) "Source",
4016                 /* identical with ad1983 */
4017                 .info = ad1983_spdif_route_info,
4018                 .get = ad1983_spdif_route_get,
4019                 .put = ad1983_spdif_route_put,
4020         },
4021         { } /* end */
4022 };
4023
4024 static struct snd_kcontrol_new ad1882_loopback_mixers[] = {
4025         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
4026         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
4027         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x01, HDA_INPUT),
4028         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x01, HDA_INPUT),
4029         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x04, HDA_INPUT),
4030         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x04, HDA_INPUT),
4031         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x06, HDA_INPUT),
4032         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x06, HDA_INPUT),
4033         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x07, HDA_INPUT),
4034         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x07, HDA_INPUT),
4035         { } /* end */
4036 };
4037
4038 static struct snd_kcontrol_new ad1882a_loopback_mixers[] = {
4039         HDA_CODEC_VOLUME("Front Mic Playback Volume", 0x20, 0x00, HDA_INPUT),
4040         HDA_CODEC_MUTE("Front Mic Playback Switch", 0x20, 0x00, HDA_INPUT),
4041         HDA_CODEC_VOLUME("Mic Playback Volume", 0x20, 0x04, HDA_INPUT),
4042         HDA_CODEC_MUTE("Mic Playback Switch", 0x20, 0x04, HDA_INPUT),
4043         HDA_CODEC_VOLUME("Line Playback Volume", 0x20, 0x01, HDA_INPUT),
4044         HDA_CODEC_MUTE("Line Playback Switch", 0x20, 0x01, HDA_INPUT),
4045         HDA_CODEC_VOLUME("CD Playback Volume", 0x20, 0x06, HDA_INPUT),
4046         HDA_CODEC_MUTE("CD Playback Switch", 0x20, 0x06, HDA_INPUT),
4047         HDA_CODEC_VOLUME("Beep Playback Volume", 0x20, 0x07, HDA_INPUT),
4048         HDA_CODEC_MUTE("Beep Playback Switch", 0x20, 0x07, HDA_INPUT),
4049         HDA_CODEC_VOLUME("Digital Mic Boost", 0x1f, 0x0, HDA_INPUT),
4050         { } /* end */
4051 };
4052
4053 static struct snd_kcontrol_new ad1882_3stack_mixers[] = {
4054         HDA_CODEC_MUTE("Surround Playback Switch", 0x15, 0x0, HDA_OUTPUT),
4055         HDA_CODEC_MUTE_MONO("Center Playback Switch", 0x17, 1, 0x0, HDA_OUTPUT),
4056         HDA_CODEC_MUTE_MONO("LFE Playback Switch", 0x17, 2, 0x0, HDA_OUTPUT),
4057         {
4058                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
4059                 .name = "Channel Mode",
4060                 .info = ad198x_ch_mode_info,
4061                 .get = ad198x_ch_mode_get,
4062                 .put = ad198x_ch_mode_put,
4063         },
4064         { } /* end */
4065 };
4066
4067 static struct snd_kcontrol_new ad1882_6stack_mixers[] = {
4068         HDA_CODEC_MUTE("Surround Playback Switch", 0x16, 0x0, HDA_OUTPUT),
4069         HDA_CODEC_MUTE_MONO("Center Playback Switch", 0x24, 1, 0x0, HDA_OUTPUT),
4070         HDA_CODEC_MUTE_MONO("LFE Playback Switch", 0x24, 2, 0x0, HDA_OUTPUT),
4071         { } /* end */
4072 };
4073
4074 static struct hda_verb ad1882_ch2_init[] = {
4075         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
4076         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4077         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4078         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
4079         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4080         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4081         { } /* end */
4082 };
4083
4084 static struct hda_verb ad1882_ch4_init[] = {
4085         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
4086         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4087         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4088         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
4089         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4090         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4091         { } /* end */
4092 };
4093
4094 static struct hda_verb ad1882_ch6_init[] = {
4095         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
4096         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4097         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4098         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
4099         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4100         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4101         { } /* end */
4102 };
4103
4104 static struct hda_channel_mode ad1882_modes[3] = {
4105         { 2, ad1882_ch2_init },
4106         { 4, ad1882_ch4_init },
4107         { 6, ad1882_ch6_init },
4108 };
4109
4110 /*
4111  * initialization verbs
4112  */
4113 static struct hda_verb ad1882_init_verbs[] = {
4114         /* DACs; mute as default */
4115         {0x03, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4116         {0x04, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4117         {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
4118         /* Port-A (HP) mixer */
4119         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4120         {0x22, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4121         /* Port-A pin */
4122         {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
4123         {0x11, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4124         /* HP selector - select DAC2 */
4125         {0x37, AC_VERB_SET_CONNECT_SEL, 0x1},
4126         /* Port-D (Line-out) mixer */
4127         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4128         {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4129         /* Port-D pin */
4130         {0x12, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
4131         {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4132         /* Mono-out mixer */
4133         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
4134         {0x1e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
4135         /* Mono-out pin */
4136         {0x13, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP},
4137         {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4138         /* Port-B (front mic) pin */
4139         {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
4140         {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4141         {0x39, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, /* boost */
4142         /* Port-C (line-in) pin */
4143         {0x15, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN},
4144         {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4145         {0x3a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, /* boost */
4146         /* Port-C mixer - mute as input */
4147         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4148         {0x2c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4149         /* Port-E (mic-in) pin */
4150         {0x17, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80},
4151         {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4152         {0x3c, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO}, /* boost */
4153         /* Port-E mixer - mute as input */
4154         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4155         {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4156         /* Port-F (surround) */
4157         {0x16, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
4158         {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4159         /* Port-G (CLFE) */
4160         {0x24, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
4161         {0x24, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},
4162         /* Analog mixer; mute as default */
4163         /* list: 0x39, 0x3a, 0x11, 0x12, 0x3c, 0x3b, 0x18, 0x1a */
4164         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)},
4165         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(1)},
4166         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(2)},
4167         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(3)},
4168         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
4169         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(5)},
4170         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(6)},
4171         {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(7)},
4172         /* Analog Mix output amp */
4173         {0x21, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x1f}, /* 0dB */
4174         /* SPDIF output selector */
4175         {0x02, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
4176         {0x02, AC_VERB_SET_CONNECT_SEL, 0x0}, /* PCM */
4177         {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE | 0x27}, /* 0dB */
4178         { } /* end */
4179 };
4180
4181 #ifdef CONFIG_SND_HDA_POWER_SAVE
4182 static struct hda_amp_list ad1882_loopbacks[] = {
4183         { 0x20, HDA_INPUT, 0 }, /* Front Mic */
4184         { 0x20, HDA_INPUT, 1 }, /* Mic */
4185         { 0x20, HDA_INPUT, 4 }, /* Line */
4186         { 0x20, HDA_INPUT, 6 }, /* CD */
4187         { } /* end */
4188 };
4189 #endif
4190
4191 /* models */
4192 enum {
4193         AD1882_3STACK,
4194         AD1882_6STACK,
4195         AD1882_MODELS
4196 };
4197
4198 static const char *ad1882_models[AD1986A_MODELS] = {
4199         [AD1882_3STACK]         = "3stack",
4200         [AD1882_6STACK]         = "6stack",
4201 };
4202
4203
4204 static int patch_ad1882(struct hda_codec *codec)
4205 {
4206         struct ad198x_spec *spec;
4207         int board_config;
4208
4209         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4210         if (spec == NULL)
4211                 return -ENOMEM;
4212
4213         codec->spec = spec;
4214
4215         spec->multiout.max_channels = 6;
4216         spec->multiout.num_dacs = 3;
4217         spec->multiout.dac_nids = ad1882_dac_nids;
4218         spec->multiout.dig_out_nid = AD1882_SPDIF_OUT;
4219         spec->num_adc_nids = ARRAY_SIZE(ad1882_adc_nids);
4220         spec->adc_nids = ad1882_adc_nids;
4221         spec->capsrc_nids = ad1882_capsrc_nids;
4222         if (codec->vendor_id == 0x11d1882)
4223                 spec->input_mux = &ad1882_capture_source;
4224         else
4225                 spec->input_mux = &ad1882a_capture_source;
4226         spec->num_mixers = 2;
4227         spec->mixers[0] = ad1882_base_mixers;
4228         if (codec->vendor_id == 0x11d1882)
4229                 spec->mixers[1] = ad1882_loopback_mixers;
4230         else
4231                 spec->mixers[1] = ad1882a_loopback_mixers;
4232         spec->num_init_verbs = 1;
4233         spec->init_verbs[0] = ad1882_init_verbs;
4234         spec->spdif_route = 0;
4235 #ifdef CONFIG_SND_HDA_POWER_SAVE
4236         spec->loopback.amplist = ad1882_loopbacks;
4237 #endif
4238         spec->vmaster_nid = 0x04;
4239
4240         codec->patch_ops = ad198x_patch_ops;
4241
4242         /* override some parameters */
4243         board_config = snd_hda_check_board_config(codec, AD1882_MODELS,
4244                                                   ad1882_models, NULL);
4245         switch (board_config) {
4246         default:
4247         case AD1882_3STACK:
4248                 spec->num_mixers = 3;
4249                 spec->mixers[2] = ad1882_3stack_mixers;
4250                 spec->channel_mode = ad1882_modes;
4251                 spec->num_channel_mode = ARRAY_SIZE(ad1882_modes);
4252                 spec->need_dac_fix = 1;
4253                 spec->multiout.max_channels = 2;
4254                 spec->multiout.num_dacs = 1;
4255                 break;
4256         case AD1882_6STACK:
4257                 spec->num_mixers = 3;
4258                 spec->mixers[2] = ad1882_6stack_mixers;
4259                 break;
4260         }
4261         return 0;
4262 }
4263
4264
4265 /*
4266  * patch entries
4267  */
4268 struct hda_codec_preset snd_hda_preset_analog[] = {
4269         { .id = 0x11d4184a, .name = "AD1884A", .patch = patch_ad1884a },
4270         { .id = 0x11d41882, .name = "AD1882", .patch = patch_ad1882 },
4271         { .id = 0x11d41883, .name = "AD1883", .patch = patch_ad1884a },
4272         { .id = 0x11d41884, .name = "AD1884", .patch = patch_ad1884 },
4273         { .id = 0x11d4194a, .name = "AD1984A", .patch = patch_ad1884a },
4274         { .id = 0x11d4194b, .name = "AD1984B", .patch = patch_ad1884a },
4275         { .id = 0x11d41981, .name = "AD1981", .patch = patch_ad1981 },
4276         { .id = 0x11d41983, .name = "AD1983", .patch = patch_ad1983 },
4277         { .id = 0x11d41984, .name = "AD1984", .patch = patch_ad1984 },
4278         { .id = 0x11d41986, .name = "AD1986A", .patch = patch_ad1986a },
4279         { .id = 0x11d41988, .name = "AD1988", .patch = patch_ad1988 },
4280         { .id = 0x11d4198b, .name = "AD1988B", .patch = patch_ad1988 },
4281         { .id = 0x11d4882a, .name = "AD1882A", .patch = patch_ad1882 },
4282         { .id = 0x11d4989a, .name = "AD1989A", .patch = patch_ad1988 },
4283         { .id = 0x11d4989b, .name = "AD1989B", .patch = patch_ad1988 },
4284         {} /* terminator */
4285 };