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