Email/web address change
[linux-2.6-block.git] / sound / pci / hda / patch_via.c
CommitLineData
c577b8a1
JC
1/*
2 * Universal Interface for Intel High Definition Audio Codec
3 *
8e86597f 4 * HD audio interface patch for VIA VT17xx/VT18xx/VT20xx codec
c577b8a1 5 *
8e86597f
LW
6 * (C) 2006-2009 VIA Technology, Inc.
7 * (C) 2006-2008 Takashi Iwai <tiwai@suse.de>
c577b8a1
JC
8 *
9 * This driver is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * This driver is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 */
23
24/* * * * * * * * * * * * * * Release History * * * * * * * * * * * * * * * * */
377ff31a 25/* */
c577b8a1 26/* 2006-03-03 Lydia Wang Create the basic patch to support VT1708 codec */
377ff31a
LW
27/* 2006-03-14 Lydia Wang Modify hard code for some pin widget nid */
28/* 2006-08-02 Lydia Wang Add support to VT1709 codec */
c577b8a1 29/* 2006-09-08 Lydia Wang Fix internal loopback recording source select bug */
377ff31a
LW
30/* 2007-09-12 Lydia Wang Add EAPD enable during driver initialization */
31/* 2007-09-17 Lydia Wang Add VT1708B codec support */
76d9b0dd 32/* 2007-11-14 Lydia Wang Add VT1708A codec HP and CD pin connect config */
fb4cb772 33/* 2008-02-03 Lydia Wang Fix Rear channels and Back channels inverse issue */
377ff31a
LW
34/* 2008-03-06 Lydia Wang Add VT1702 codec and VT1708S codec support */
35/* 2008-04-09 Lydia Wang Add mute front speaker when HP plugin */
36/* 2008-04-09 Lydia Wang Add Independent HP feature */
98aa34c0 37/* 2008-05-28 Lydia Wang Add second S/PDIF Out support for VT1702 */
377ff31a 38/* 2008-09-15 Logan Li Add VT1708S Mic Boost workaround/backdoor */
8e86597f
LW
39/* 2009-02-16 Logan Li Add support for VT1718S */
40/* 2009-03-13 Logan Li Add support for VT1716S */
41/* 2009-04-14 Lydai Wang Add support for VT1828S and VT2020 */
42/* 2009-07-08 Lydia Wang Add support for VT2002P */
43/* 2009-07-21 Lydia Wang Add support for VT1812 */
36dd5c4a 44/* 2009-09-19 Lydia Wang Add support for VT1818S */
377ff31a 45/* */
c577b8a1
JC
46/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
47
48
c577b8a1
JC
49#include <linux/init.h>
50#include <linux/delay.h>
51#include <linux/slab.h>
da155d5b 52#include <linux/module.h>
c577b8a1 53#include <sound/core.h>
0aa62aef 54#include <sound/asoundef.h>
c577b8a1
JC
55#include "hda_codec.h"
56#include "hda_local.h"
1835a0f9 57#include "hda_jack.h"
c577b8a1 58
c577b8a1 59/* Pin Widget NID */
d949cac1
HW
60#define VT1708_HP_PIN_NID 0x20
61#define VT1708_CD_PIN_NID 0x24
c577b8a1 62
d7426329
HW
63enum VIA_HDA_CODEC {
64 UNKNOWN = -1,
65 VT1708,
66 VT1709_10CH,
67 VT1709_6CH,
68 VT1708B_8CH,
69 VT1708B_4CH,
70 VT1708S,
518bf3ba 71 VT1708BCE,
d7426329 72 VT1702,
eb7188ca 73 VT1718S,
f3db423d 74 VT1716S,
25eaba2f 75 VT2002P,
ab6734e7 76 VT1812,
11890956 77 VT1802,
d7426329
HW
78 CODEC_TYPES,
79};
80
11890956
LW
81#define VT2002P_COMPATIBLE(spec) \
82 ((spec)->codec_type == VT2002P ||\
83 (spec)->codec_type == VT1812 ||\
84 (spec)->codec_type == VT1802)
85
8e3679dc
TI
86#define MAX_NID_PATH_DEPTH 5
87
09a9ad69
TI
88/* output-path: DAC -> ... -> pin
89 * idx[] contains the source index number of the next widget;
90 * e.g. idx[0] is the index of the DAC selected by path[1] widget
91 * multi[] indicates whether it's a selector widget with multi-connectors
92 * (i.e. the connection selection is mandatory)
93 * vol_ctl and mute_ctl contains the NIDs for the assigned mixers
94 */
4a79616d
TI
95struct nid_path {
96 int depth;
8e3679dc 97 hda_nid_t path[MAX_NID_PATH_DEPTH];
09a9ad69
TI
98 unsigned char idx[MAX_NID_PATH_DEPTH];
99 unsigned char multi[MAX_NID_PATH_DEPTH];
100 unsigned int vol_ctl;
101 unsigned int mute_ctl;
4a79616d
TI
102};
103
a86a88ea
TI
104/* input-path */
105struct via_input {
106 hda_nid_t pin; /* input-pin or aa-mix */
107 int adc_idx; /* ADC index to be used */
108 int mux_idx; /* MUX index (if any) */
109 const char *label; /* input-source label */
110};
111
de6c74f3
TI
112#define VIA_MAX_ADCS 3
113
3b607e3d
TI
114enum {
115 STREAM_MULTI_OUT = (1 << 0),
116 STREAM_INDEP_HP = (1 << 1),
117};
118
1f2e99fe
LW
119struct via_spec {
120 /* codec parameterization */
90dd48a1 121 const struct snd_kcontrol_new *mixers[6];
1f2e99fe
LW
122 unsigned int num_mixers;
123
90dd48a1 124 const struct hda_verb *init_verbs[5];
1f2e99fe
LW
125 unsigned int num_iverbs;
126
82673bc8 127 char stream_name_analog[32];
7eb56e84 128 char stream_name_hp[32];
90dd48a1
TI
129 const struct hda_pcm_stream *stream_analog_playback;
130 const struct hda_pcm_stream *stream_analog_capture;
1f2e99fe 131
82673bc8 132 char stream_name_digital[32];
90dd48a1
TI
133 const struct hda_pcm_stream *stream_digital_playback;
134 const struct hda_pcm_stream *stream_digital_capture;
1f2e99fe
LW
135
136 /* playback */
137 struct hda_multi_out multiout;
138 hda_nid_t slave_dig_outs[2];
ece8d043 139 hda_nid_t hp_dac_nid;
3214b966
TI
140 hda_nid_t speaker_dac_nid;
141 int hp_indep_shared; /* indep HP-DAC is shared with side ch */
3b607e3d
TI
142 int opened_streams; /* STREAM_* bits */
143 int active_streams; /* STREAM_* bits */
3214b966
TI
144 int aamix_mode; /* loopback is enabled for output-path? */
145
146 /* Output-paths:
147 * There are different output-paths depending on the setup.
148 * out_path, hp_path and speaker_path are primary paths. If both
149 * direct DAC and aa-loopback routes are available, these contain
150 * the former paths. Meanwhile *_mix_path contain the paths with
151 * loopback mixer. (Since the loopback is only for front channel,
152 * no out_mix_path for surround channels.)
153 * The HP output has another path, hp_indep_path, which is used in
154 * the independent-HP mode.
155 */
de6c74f3 156 struct nid_path out_path[HDA_SIDE + 1];
3214b966 157 struct nid_path out_mix_path;
4a79616d 158 struct nid_path hp_path;
3214b966
TI
159 struct nid_path hp_mix_path;
160 struct nid_path hp_indep_path;
4a918ffe 161 struct nid_path speaker_path;
3214b966 162 struct nid_path speaker_mix_path;
4a79616d 163
1f2e99fe
LW
164 /* capture */
165 unsigned int num_adc_nids;
de6c74f3
TI
166 hda_nid_t adc_nids[VIA_MAX_ADCS];
167 hda_nid_t mux_nids[VIA_MAX_ADCS];
620e2b28 168 hda_nid_t aa_mix_nid;
1f2e99fe 169 hda_nid_t dig_in_nid;
1f2e99fe
LW
170
171 /* capture source */
a86a88ea
TI
172 bool dyn_adc_switch;
173 int num_inputs;
174 struct via_input inputs[AUTO_CFG_MAX_INS + 1];
de6c74f3 175 unsigned int cur_mux[VIA_MAX_ADCS];
1f2e99fe 176
3b607e3d
TI
177 /* dynamic DAC switching */
178 unsigned int cur_dac_stream_tag;
179 unsigned int cur_dac_format;
180 unsigned int cur_hp_stream_tag;
181 unsigned int cur_hp_format;
182
a86a88ea
TI
183 /* dynamic ADC switching */
184 hda_nid_t cur_adc;
185 unsigned int cur_adc_stream_tag;
186 unsigned int cur_adc_format;
187
1f2e99fe
LW
188 /* PCM information */
189 struct hda_pcm pcm_rec[3];
190
191 /* dynamic controls, init_verbs and input_mux */
192 struct auto_pin_cfg autocfg;
193 struct snd_array kctls;
1f2e99fe
LW
194 hda_nid_t private_dac_nids[AUTO_CFG_MAX_OUTS];
195
196 /* HP mode source */
1f2e99fe 197 unsigned int hp_independent_mode;
f3db423d 198 unsigned int dmic_enabled;
24088a58 199 unsigned int no_pin_power_ctl;
1f2e99fe
LW
200 enum VIA_HDA_CODEC codec_type;
201
e9d010c2
TI
202 /* analog low-power control */
203 bool alc_mode;
204
e3d7a143
TI
205 /* smart51 setup */
206 unsigned int smart51_nums;
207 hda_nid_t smart51_pins[2];
208 int smart51_idxs[2];
209 const char *smart51_labels[2];
210 unsigned int smart51_enabled;
211
1f2e99fe
LW
212 /* work to check hp jack state */
213 struct hda_codec *codec;
214 struct delayed_work vt1708_hp_work;
187d333e 215 int hp_work_active;
e06e5a29 216 int vt1708_jack_detect;
1f2e99fe 217 int vt1708_hp_present;
3e95b9ab
LW
218
219 void (*set_widgets_power_state)(struct hda_codec *codec);
220
1f2e99fe 221 struct hda_loopback_check loopback;
13af8e77
TI
222 int num_loopbacks;
223 struct hda_amp_list loopback_list[8];
a86a88ea
TI
224
225 /* bind capture-volume */
226 struct hda_bind_ctls *bind_cap_vol;
227 struct hda_bind_ctls *bind_cap_sw;
3b607e3d
TI
228
229 struct mutex config_mutex;
1f2e99fe
LW
230};
231
0341ccd7 232static enum VIA_HDA_CODEC get_codec_type(struct hda_codec *codec);
5b0cb1d8
JK
233static struct via_spec * via_new_spec(struct hda_codec *codec)
234{
235 struct via_spec *spec;
236
237 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
238 if (spec == NULL)
239 return NULL;
240
3b607e3d 241 mutex_init(&spec->config_mutex);
5b0cb1d8
JK
242 codec->spec = spec;
243 spec->codec = codec;
0341ccd7
LW
244 spec->codec_type = get_codec_type(codec);
245 /* VT1708BCE & VT1708S are almost same */
246 if (spec->codec_type == VT1708BCE)
247 spec->codec_type = VT1708S;
5b0cb1d8
JK
248 return spec;
249}
250
744ff5f4 251static enum VIA_HDA_CODEC get_codec_type(struct hda_codec *codec)
d7426329 252{
744ff5f4 253 u32 vendor_id = codec->vendor_id;
d7426329
HW
254 u16 ven_id = vendor_id >> 16;
255 u16 dev_id = vendor_id & 0xffff;
256 enum VIA_HDA_CODEC codec_type;
257
258 /* get codec type */
259 if (ven_id != 0x1106)
260 codec_type = UNKNOWN;
261 else if (dev_id >= 0x1708 && dev_id <= 0x170b)
262 codec_type = VT1708;
263 else if (dev_id >= 0xe710 && dev_id <= 0xe713)
264 codec_type = VT1709_10CH;
265 else if (dev_id >= 0xe714 && dev_id <= 0xe717)
266 codec_type = VT1709_6CH;
518bf3ba 267 else if (dev_id >= 0xe720 && dev_id <= 0xe723) {
d7426329 268 codec_type = VT1708B_8CH;
518bf3ba
LW
269 if (snd_hda_param_read(codec, 0x16, AC_PAR_CONNLIST_LEN) == 0x7)
270 codec_type = VT1708BCE;
271 } else if (dev_id >= 0xe724 && dev_id <= 0xe727)
d7426329
HW
272 codec_type = VT1708B_4CH;
273 else if ((dev_id & 0xfff) == 0x397
274 && (dev_id >> 12) < 8)
275 codec_type = VT1708S;
276 else if ((dev_id & 0xfff) == 0x398
277 && (dev_id >> 12) < 8)
278 codec_type = VT1702;
eb7188ca
LW
279 else if ((dev_id & 0xfff) == 0x428
280 && (dev_id >> 12) < 8)
281 codec_type = VT1718S;
f3db423d
LW
282 else if (dev_id == 0x0433 || dev_id == 0xa721)
283 codec_type = VT1716S;
bb3c6bfc
LW
284 else if (dev_id == 0x0441 || dev_id == 0x4441)
285 codec_type = VT1718S;
25eaba2f
LW
286 else if (dev_id == 0x0438 || dev_id == 0x4438)
287 codec_type = VT2002P;
ab6734e7
LW
288 else if (dev_id == 0x0448)
289 codec_type = VT1812;
36dd5c4a
LW
290 else if (dev_id == 0x0440)
291 codec_type = VT1708S;
11890956
LW
292 else if ((dev_id & 0xfff) == 0x446)
293 codec_type = VT1802;
d7426329
HW
294 else
295 codec_type = UNKNOWN;
296 return codec_type;
297};
298
ec7e7e42 299#define VIA_JACK_EVENT 0x20
69e52a80
HW
300#define VIA_HP_EVENT 0x01
301#define VIA_GPIO_EVENT 0x02
4a918ffe 302#define VIA_LINE_EVENT 0x03
69e52a80 303
c577b8a1
JC
304enum {
305 VIA_CTL_WIDGET_VOL,
306 VIA_CTL_WIDGET_MUTE,
f5271101 307 VIA_CTL_WIDGET_ANALOG_MUTE,
c577b8a1
JC
308};
309
ada509ec
TI
310static void analog_low_current_mode(struct hda_codec *codec);
311static bool is_aa_path_mute(struct hda_codec *codec);
1f2e99fe 312
187d333e
TI
313#define hp_detect_with_aa(codec) \
314 (snd_hda_get_bool_hint(codec, "analog_loopback_hp_detect") == 1 && \
315 !is_aa_path_mute(codec))
316
317static void vt1708_stop_hp_work(struct via_spec *spec)
1f2e99fe
LW
318{
319 if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0)
320 return;
187d333e
TI
321 if (spec->hp_work_active) {
322 snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, 1);
323 cancel_delayed_work_sync(&spec->vt1708_hp_work);
324 spec->hp_work_active = 0;
325 }
1f2e99fe
LW
326}
327
187d333e 328static void vt1708_update_hp_work(struct via_spec *spec)
1f2e99fe
LW
329{
330 if (spec->codec_type != VT1708 || spec->autocfg.hp_pins[0] == 0)
331 return;
187d333e
TI
332 if (spec->vt1708_jack_detect &&
333 (spec->active_streams || hp_detect_with_aa(spec->codec))) {
334 if (!spec->hp_work_active) {
335 snd_hda_codec_write(spec->codec, 0x1, 0, 0xf81, 0);
336 schedule_delayed_work(&spec->vt1708_hp_work,
337 msecs_to_jiffies(100));
338 spec->hp_work_active = 1;
339 }
340 } else if (!hp_detect_with_aa(spec->codec))
341 vt1708_stop_hp_work(spec);
1f2e99fe 342}
f5271101 343
3e95b9ab
LW
344static void set_widgets_power_state(struct hda_codec *codec)
345{
346 struct via_spec *spec = codec->spec;
347 if (spec->set_widgets_power_state)
348 spec->set_widgets_power_state(codec);
349}
25eaba2f 350
f5271101
LW
351static int analog_input_switch_put(struct snd_kcontrol *kcontrol,
352 struct snd_ctl_elem_value *ucontrol)
353{
354 int change = snd_hda_mixer_amp_switch_put(kcontrol, ucontrol);
355 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
356
3e95b9ab 357 set_widgets_power_state(codec);
ada509ec 358 analog_low_current_mode(snd_kcontrol_chip(kcontrol));
187d333e 359 vt1708_update_hp_work(codec->spec);
f5271101
LW
360 return change;
361}
362
363/* modify .put = snd_hda_mixer_amp_switch_put */
364#define ANALOG_INPUT_MUTE \
365 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
366 .name = NULL, \
367 .index = 0, \
368 .info = snd_hda_mixer_amp_switch_info, \
369 .get = snd_hda_mixer_amp_switch_get, \
370 .put = analog_input_switch_put, \
371 .private_value = HDA_COMPOSE_AMP_VAL(0, 3, 0, 0) }
372
90dd48a1 373static const struct snd_kcontrol_new via_control_templates[] = {
c577b8a1
JC
374 HDA_CODEC_VOLUME(NULL, 0, 0, 0),
375 HDA_CODEC_MUTE(NULL, 0, 0, 0),
f5271101 376 ANALOG_INPUT_MUTE,
c577b8a1
JC
377};
378
ab6734e7 379
c577b8a1 380/* add dynamic controls */
291c9e33
TI
381static struct snd_kcontrol_new *__via_clone_ctl(struct via_spec *spec,
382 const struct snd_kcontrol_new *tmpl,
383 const char *name)
c577b8a1
JC
384{
385 struct snd_kcontrol_new *knew;
386
603c4019
TI
387 snd_array_init(&spec->kctls, sizeof(*knew), 32);
388 knew = snd_array_new(&spec->kctls);
389 if (!knew)
291c9e33
TI
390 return NULL;
391 *knew = *tmpl;
392 if (!name)
393 name = tmpl->name;
394 if (name) {
395 knew->name = kstrdup(name, GFP_KERNEL);
396 if (!knew->name)
397 return NULL;
398 }
399 return knew;
400}
401
402static int __via_add_control(struct via_spec *spec, int type, const char *name,
403 int idx, unsigned long val)
404{
405 struct snd_kcontrol_new *knew;
406
407 knew = __via_clone_ctl(spec, &via_control_templates[type], name);
408 if (!knew)
c577b8a1 409 return -ENOMEM;
d7a99cce 410 knew->index = idx;
4d02d1b6 411 if (get_amp_nid_(val))
5e26dfd0 412 knew->subdevice = HDA_SUBDEV_AMP_FLAG;
c577b8a1 413 knew->private_value = val;
c577b8a1
JC
414 return 0;
415}
416
7b315bb4
TI
417#define via_add_control(spec, type, name, val) \
418 __via_add_control(spec, type, name, 0, val)
419
291c9e33 420#define via_clone_control(spec, tmpl) __via_clone_ctl(spec, tmpl, NULL)
5b0cb1d8 421
603c4019
TI
422static void via_free_kctls(struct hda_codec *codec)
423{
424 struct via_spec *spec = codec->spec;
425
426 if (spec->kctls.list) {
427 struct snd_kcontrol_new *kctl = spec->kctls.list;
428 int i;
429 for (i = 0; i < spec->kctls.used; i++)
430 kfree(kctl[i].name);
431 }
432 snd_array_free(&spec->kctls);
433}
434
c577b8a1 435/* create input playback/capture controls for the given pin */
9510e8dd 436static int via_new_analog_input(struct via_spec *spec, const char *ctlname,
7b315bb4 437 int type_idx, int idx, int mix_nid)
c577b8a1
JC
438{
439 char name[32];
440 int err;
441
442 sprintf(name, "%s Playback Volume", ctlname);
7b315bb4 443 err = __via_add_control(spec, VIA_CTL_WIDGET_VOL, name, type_idx,
c577b8a1
JC
444 HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT));
445 if (err < 0)
446 return err;
447 sprintf(name, "%s Playback Switch", ctlname);
7b315bb4 448 err = __via_add_control(spec, VIA_CTL_WIDGET_ANALOG_MUTE, name, type_idx,
c577b8a1
JC
449 HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT));
450 if (err < 0)
451 return err;
452 return 0;
453}
454
5d41762a 455#define get_connection_index(codec, mux, nid) \
8d087c76 456 snd_hda_get_conn_index(codec, mux, nid, 0)
5d41762a 457
8df2a312
TI
458static bool check_amp_caps(struct hda_codec *codec, hda_nid_t nid, int dir,
459 unsigned int mask)
460{
a934d5a9
TI
461 unsigned int caps;
462 if (!nid)
463 return false;
464 caps = get_wcaps(codec, nid);
8df2a312
TI
465 if (dir == HDA_INPUT)
466 caps &= AC_WCAP_IN_AMP;
467 else
468 caps &= AC_WCAP_OUT_AMP;
469 if (!caps)
470 return false;
471 if (query_amp_caps(codec, nid, dir) & mask)
472 return true;
473 return false;
474}
475
09a9ad69
TI
476#define have_mute(codec, nid, dir) \
477 check_amp_caps(codec, nid, dir, AC_AMPCAP_MUTE)
8df2a312 478
d69607b3
LW
479/* enable/disable the output-route mixers */
480static void activate_output_mix(struct hda_codec *codec, struct nid_path *path,
3214b966 481 hda_nid_t mix_nid, int idx, bool enable)
d69607b3
LW
482{
483 int i, num, val;
d69607b3
LW
484
485 if (!path)
486 return;
487 num = snd_hda_get_conn_list(codec, mix_nid, NULL);
d69607b3 488 for (i = 0; i < num; i++) {
3214b966
TI
489 if (i == idx)
490 val = AMP_IN_UNMUTE(i);
491 else
492 val = AMP_IN_MUTE(i);
d69607b3
LW
493 snd_hda_codec_write(codec, mix_nid, 0,
494 AC_VERB_SET_AMP_GAIN_MUTE, val);
495 }
496}
497
09a9ad69
TI
498/* enable/disable the output-route */
499static void activate_output_path(struct hda_codec *codec, struct nid_path *path,
500 bool enable, bool force)
5d41762a 501{
d69607b3 502 struct via_spec *spec = codec->spec;
3214b966 503 int i;
09a9ad69
TI
504 for (i = 0; i < path->depth; i++) {
505 hda_nid_t src, dst;
506 int idx = path->idx[i];
507 src = path->path[i];
508 if (i < path->depth - 1)
509 dst = path->path[i + 1];
510 else
511 dst = 0;
512 if (enable && path->multi[i])
513 snd_hda_codec_write(codec, dst, 0,
514 AC_VERB_SET_CONNECT_SEL, idx);
3214b966 515 if (!force && (dst == spec->aa_mix_nid))
e5e14681 516 continue;
3214b966
TI
517 if (have_mute(codec, dst, HDA_INPUT))
518 activate_output_mix(codec, path, dst, idx, enable);
09a9ad69
TI
519 if (!force && (src == path->vol_ctl || src == path->mute_ctl))
520 continue;
521 if (have_mute(codec, src, HDA_OUTPUT)) {
522 int val = enable ? AMP_OUT_UNMUTE : AMP_OUT_MUTE;
523 snd_hda_codec_write(codec, src, 0,
524 AC_VERB_SET_AMP_GAIN_MUTE, val);
525 }
526 }
5d41762a
TI
527}
528
529/* set the given pin as output */
530static void init_output_pin(struct hda_codec *codec, hda_nid_t pin,
531 int pin_type)
532{
533 if (!pin)
534 return;
535 snd_hda_codec_write(codec, pin, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
536 pin_type);
537 if (snd_hda_query_pin_caps(codec, pin) & AC_PINCAP_EAPD)
538 snd_hda_codec_write(codec, pin, 0,
d3a11e60 539 AC_VERB_SET_EAPD_BTLENABLE, 0x02);
c577b8a1
JC
540}
541
09a9ad69 542static void via_auto_init_output(struct hda_codec *codec,
a353fbb1 543 struct nid_path *path, int pin_type)
5d41762a 544{
5d41762a 545 unsigned int caps;
d69607b3 546 hda_nid_t pin;
5d41762a 547
09a9ad69 548 if (!path->depth)
5d41762a 549 return;
09a9ad69 550 pin = path->path[path->depth - 1];
5d41762a
TI
551
552 init_output_pin(codec, pin, pin_type);
553 caps = query_amp_caps(codec, pin, HDA_OUTPUT);
554 if (caps & AC_AMPCAP_MUTE) {
555 unsigned int val;
556 val = (caps & AC_AMPCAP_OFFSET) >> AC_AMPCAP_OFFSET_SHIFT;
557 snd_hda_codec_write(codec, pin, 0, AC_VERB_SET_AMP_GAIN_MUTE,
558 AMP_OUT_MUTE | val);
559 }
a353fbb1 560 activate_output_path(codec, path, true, true); /* force on */
5d41762a
TI
561}
562
c577b8a1
JC
563static void via_auto_init_multi_out(struct hda_codec *codec)
564{
565 struct via_spec *spec = codec->spec;
3214b966 566 struct nid_path *path;
c577b8a1
JC
567 int i;
568
3214b966
TI
569 for (i = 0; i < spec->autocfg.line_outs + spec->smart51_nums; i++) {
570 path = &spec->out_path[i];
571 if (!i && spec->aamix_mode && spec->out_mix_path.depth)
572 path = &spec->out_mix_path;
a353fbb1 573 via_auto_init_output(codec, path, PIN_OUT);
3214b966 574 }
c577b8a1
JC
575}
576
020066d1
TI
577/* deactivate the inactive headphone-paths */
578static void deactivate_hp_paths(struct hda_codec *codec)
c577b8a1
JC
579{
580 struct via_spec *spec = codec->spec;
3214b966 581 int shared = spec->hp_indep_shared;
c577b8a1 582
09a9ad69 583 if (spec->hp_independent_mode) {
09a9ad69 584 activate_output_path(codec, &spec->hp_path, false, false);
3214b966
TI
585 activate_output_path(codec, &spec->hp_mix_path, false, false);
586 if (shared)
587 activate_output_path(codec, &spec->out_path[shared],
588 false, false);
020066d1
TI
589 } else if (spec->aamix_mode || !spec->hp_path.depth) {
590 activate_output_path(codec, &spec->hp_indep_path, false, false);
3214b966 591 activate_output_path(codec, &spec->hp_path, false, false);
3214b966 592 } else {
020066d1 593 activate_output_path(codec, &spec->hp_indep_path, false, false);
3214b966 594 activate_output_path(codec, &spec->hp_mix_path, false, false);
09a9ad69 595 }
c577b8a1
JC
596}
597
020066d1
TI
598static void via_auto_init_hp_out(struct hda_codec *codec)
599{
600 struct via_spec *spec = codec->spec;
601
602 if (!spec->hp_path.depth) {
a353fbb1 603 via_auto_init_output(codec, &spec->hp_mix_path, PIN_HP);
020066d1
TI
604 return;
605 }
606 deactivate_hp_paths(codec);
607 if (spec->hp_independent_mode)
a353fbb1 608 via_auto_init_output(codec, &spec->hp_indep_path, PIN_HP);
020066d1 609 else if (spec->aamix_mode)
a353fbb1 610 via_auto_init_output(codec, &spec->hp_mix_path, PIN_HP);
020066d1 611 else
a353fbb1 612 via_auto_init_output(codec, &spec->hp_path, PIN_HP);
020066d1
TI
613}
614
4a918ffe
TI
615static void via_auto_init_speaker_out(struct hda_codec *codec)
616{
617 struct via_spec *spec = codec->spec;
618
3214b966
TI
619 if (!spec->autocfg.speaker_outs)
620 return;
621 if (!spec->speaker_path.depth) {
a353fbb1 622 via_auto_init_output(codec, &spec->speaker_mix_path, PIN_OUT);
3214b966
TI
623 return;
624 }
625 if (!spec->aamix_mode) {
626 activate_output_path(codec, &spec->speaker_mix_path,
627 false, false);
a353fbb1 628 via_auto_init_output(codec, &spec->speaker_path, PIN_OUT);
3214b966
TI
629 } else {
630 activate_output_path(codec, &spec->speaker_path, false, false);
a353fbb1 631 via_auto_init_output(codec, &spec->speaker_mix_path, PIN_OUT);
3214b966 632 }
4a918ffe
TI
633}
634
f4a7828b 635static bool is_smart51_pins(struct hda_codec *codec, hda_nid_t pin);
6e969d91 636static void via_hp_automute(struct hda_codec *codec);
32e0191d 637
c577b8a1
JC
638static void via_auto_init_analog_input(struct hda_codec *codec)
639{
640 struct via_spec *spec = codec->spec;
7b315bb4 641 const struct auto_pin_cfg *cfg = &spec->autocfg;
096a8854 642 hda_nid_t conn[HDA_MAX_CONNECTIONS];
32e0191d 643 unsigned int ctl;
096a8854
TI
644 int i, num_conns;
645
646 /* init ADCs */
647 for (i = 0; i < spec->num_adc_nids; i++) {
648 snd_hda_codec_write(codec, spec->adc_nids[i], 0,
649 AC_VERB_SET_AMP_GAIN_MUTE,
650 AMP_IN_UNMUTE(0));
651 }
c577b8a1 652
096a8854 653 /* init pins */
7b315bb4
TI
654 for (i = 0; i < cfg->num_inputs; i++) {
655 hda_nid_t nid = cfg->inputs[i].pin;
f4a7828b 656 if (spec->smart51_enabled && is_smart51_pins(codec, nid))
32e0191d 657 ctl = PIN_OUT;
30649676 658 else if (cfg->inputs[i].type == AUTO_PIN_MIC)
32e0191d
CL
659 ctl = PIN_VREF50;
660 else
661 ctl = PIN_IN;
c577b8a1 662 snd_hda_codec_write(codec, nid, 0,
32e0191d 663 AC_VERB_SET_PIN_WIDGET_CONTROL, ctl);
c577b8a1 664 }
096a8854
TI
665
666 /* init input-src */
667 for (i = 0; i < spec->num_adc_nids; i++) {
a86a88ea
TI
668 int adc_idx = spec->inputs[spec->cur_mux[i]].adc_idx;
669 if (spec->mux_nids[adc_idx]) {
670 int mux_idx = spec->inputs[spec->cur_mux[i]].mux_idx;
671 snd_hda_codec_write(codec, spec->mux_nids[adc_idx], 0,
672 AC_VERB_SET_CONNECT_SEL,
673 mux_idx);
674 }
675 if (spec->dyn_adc_switch)
676 break; /* only one input-src */
096a8854
TI
677 }
678
679 /* init aa-mixer */
680 if (!spec->aa_mix_nid)
681 return;
682 num_conns = snd_hda_get_connections(codec, spec->aa_mix_nid, conn,
683 ARRAY_SIZE(conn));
684 for (i = 0; i < num_conns; i++) {
685 unsigned int caps = get_wcaps(codec, conn[i]);
686 if (get_wcaps_type(caps) == AC_WID_PIN)
687 snd_hda_codec_write(codec, spec->aa_mix_nid, 0,
688 AC_VERB_SET_AMP_GAIN_MUTE,
689 AMP_IN_MUTE(i));
690 }
c577b8a1 691}
f5271101 692
054d867e
TI
693static void update_power_state(struct hda_codec *codec, hda_nid_t nid,
694 unsigned int parm)
695{
696 if (snd_hda_codec_read(codec, nid, 0,
697 AC_VERB_GET_POWER_STATE, 0) == parm)
698 return;
699 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_POWER_STATE, parm);
700}
701
f5271101
LW
702static void set_pin_power_state(struct hda_codec *codec, hda_nid_t nid,
703 unsigned int *affected_parm)
704{
705 unsigned parm;
706 unsigned def_conf = snd_hda_codec_get_pincfg(codec, nid);
707 unsigned no_presence = (def_conf & AC_DEFCFG_MISC)
708 >> AC_DEFCFG_MISC_SHIFT
709 & AC_DEFCFG_MISC_NO_PRESENCE; /* do not support pin sense */
1564b287 710 struct via_spec *spec = codec->spec;
24088a58
TI
711 unsigned present = 0;
712
713 no_presence |= spec->no_pin_power_ctl;
714 if (!no_presence)
715 present = snd_hda_jack_detect(codec, nid);
f4a7828b 716 if ((spec->smart51_enabled && is_smart51_pins(codec, nid))
1564b287
LW
717 || ((no_presence || present)
718 && get_defcfg_connect(def_conf) != AC_JACK_PORT_NONE)) {
f5271101
LW
719 *affected_parm = AC_PWRST_D0; /* if it's connected */
720 parm = AC_PWRST_D0;
721 } else
722 parm = AC_PWRST_D3;
723
054d867e 724 update_power_state(codec, nid, parm);
f5271101
LW
725}
726
24088a58
TI
727static int via_pin_power_ctl_info(struct snd_kcontrol *kcontrol,
728 struct snd_ctl_elem_info *uinfo)
729{
730 static const char * const texts[] = {
731 "Disabled", "Enabled"
732 };
733
734 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
735 uinfo->count = 1;
736 uinfo->value.enumerated.items = 2;
737 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
738 uinfo->value.enumerated.item = uinfo->value.enumerated.items - 1;
739 strcpy(uinfo->value.enumerated.name,
740 texts[uinfo->value.enumerated.item]);
741 return 0;
742}
743
744static int via_pin_power_ctl_get(struct snd_kcontrol *kcontrol,
745 struct snd_ctl_elem_value *ucontrol)
746{
747 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
748 struct via_spec *spec = codec->spec;
749 ucontrol->value.enumerated.item[0] = !spec->no_pin_power_ctl;
750 return 0;
751}
752
753static int via_pin_power_ctl_put(struct snd_kcontrol *kcontrol,
754 struct snd_ctl_elem_value *ucontrol)
755{
756 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
757 struct via_spec *spec = codec->spec;
758 unsigned int val = !ucontrol->value.enumerated.item[0];
759
760 if (val == spec->no_pin_power_ctl)
761 return 0;
762 spec->no_pin_power_ctl = val;
763 set_widgets_power_state(codec);
e9d010c2 764 analog_low_current_mode(codec);
24088a58
TI
765 return 1;
766}
767
768static const struct snd_kcontrol_new via_pin_power_ctl_enum = {
769 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
770 .name = "Dynamic Power-Control",
771 .info = via_pin_power_ctl_info,
772 .get = via_pin_power_ctl_get,
773 .put = via_pin_power_ctl_put,
774};
775
776
0aa62aef
HW
777static int via_independent_hp_info(struct snd_kcontrol *kcontrol,
778 struct snd_ctl_elem_info *uinfo)
779{
8df2a312
TI
780 static const char * const texts[] = { "OFF", "ON" };
781
782 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
783 uinfo->count = 1;
784 uinfo->value.enumerated.items = 2;
785 if (uinfo->value.enumerated.item >= 2)
786 uinfo->value.enumerated.item = 1;
787 strcpy(uinfo->value.enumerated.name,
788 texts[uinfo->value.enumerated.item]);
789 return 0;
0aa62aef
HW
790}
791
792static int via_independent_hp_get(struct snd_kcontrol *kcontrol,
793 struct snd_ctl_elem_value *ucontrol)
794{
795 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
cdc1784d 796 struct via_spec *spec = codec->spec;
cdc1784d 797
ece8d043 798 ucontrol->value.enumerated.item[0] = spec->hp_independent_mode;
cdc1784d
LW
799 return 0;
800}
801
3b607e3d
TI
802/* adjust spec->multiout setup according to the current flags */
803static void setup_playback_multi_pcm(struct via_spec *spec)
804{
805 const struct auto_pin_cfg *cfg = &spec->autocfg;
806 spec->multiout.num_dacs = cfg->line_outs + spec->smart51_nums;
807 spec->multiout.hp_nid = 0;
808 if (!spec->hp_independent_mode) {
809 if (!spec->hp_indep_shared)
810 spec->multiout.hp_nid = spec->hp_dac_nid;
811 } else {
812 if (spec->hp_indep_shared)
813 spec->multiout.num_dacs = cfg->line_outs - 1;
814 }
815}
816
817/* update DAC setups according to indep-HP switch;
818 * this function is called only when indep-HP is modified
819 */
820static void switch_indep_hp_dacs(struct hda_codec *codec)
821{
822 struct via_spec *spec = codec->spec;
823 int shared = spec->hp_indep_shared;
824 hda_nid_t shared_dac, hp_dac;
825
826 if (!spec->opened_streams)
827 return;
828
829 shared_dac = shared ? spec->multiout.dac_nids[shared] : 0;
830 hp_dac = spec->hp_dac_nid;
831 if (spec->hp_independent_mode) {
832 /* switch to indep-HP mode */
833 if (spec->active_streams & STREAM_MULTI_OUT) {
834 __snd_hda_codec_cleanup_stream(codec, hp_dac, 1);
835 __snd_hda_codec_cleanup_stream(codec, shared_dac, 1);
836 }
837 if (spec->active_streams & STREAM_INDEP_HP)
838 snd_hda_codec_setup_stream(codec, hp_dac,
839 spec->cur_hp_stream_tag, 0,
840 spec->cur_hp_format);
841 } else {
842 /* back to HP or shared-DAC */
843 if (spec->active_streams & STREAM_INDEP_HP)
844 __snd_hda_codec_cleanup_stream(codec, hp_dac, 1);
845 if (spec->active_streams & STREAM_MULTI_OUT) {
846 hda_nid_t dac;
847 int ch;
848 if (shared_dac) { /* reset mutli-ch DAC */
849 dac = shared_dac;
850 ch = shared * 2;
851 } else { /* reset HP DAC */
852 dac = hp_dac;
853 ch = 0;
854 }
855 snd_hda_codec_setup_stream(codec, dac,
856 spec->cur_dac_stream_tag, ch,
857 spec->cur_dac_format);
858 }
859 }
860 setup_playback_multi_pcm(spec);
861}
862
0aa62aef
HW
863static int via_independent_hp_put(struct snd_kcontrol *kcontrol,
864 struct snd_ctl_elem_value *ucontrol)
865{
866 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
867 struct via_spec *spec = codec->spec;
3214b966 868 int cur, shared;
8df2a312 869
3b607e3d 870 mutex_lock(&spec->config_mutex);
25250505 871 cur = !!ucontrol->value.enumerated.item[0];
3b607e3d
TI
872 if (spec->hp_independent_mode == cur) {
873 mutex_unlock(&spec->config_mutex);
25250505 874 return 0;
3b607e3d 875 }
25250505 876 spec->hp_independent_mode = cur;
3214b966 877 shared = spec->hp_indep_shared;
020066d1
TI
878 deactivate_hp_paths(codec);
879 if (cur)
880 activate_output_path(codec, &spec->hp_indep_path, true, false);
881 else {
3214b966
TI
882 if (shared)
883 activate_output_path(codec, &spec->out_path[shared],
25250505 884 true, false);
020066d1
TI
885 if (spec->aamix_mode || !spec->hp_path.depth)
886 activate_output_path(codec, &spec->hp_mix_path,
887 true, false);
888 else
889 activate_output_path(codec, &spec->hp_path,
890 true, false);
8df2a312 891 }
ece8d043 892
3b607e3d
TI
893 switch_indep_hp_dacs(codec);
894 mutex_unlock(&spec->config_mutex);
895
ce0e5a9e 896 /* update jack power state */
3e95b9ab 897 set_widgets_power_state(codec);
6e969d91 898 via_hp_automute(codec);
25250505 899 return 1;
0aa62aef
HW
900}
901
ece8d043
TI
902static const struct snd_kcontrol_new via_hp_mixer = {
903 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
904 .name = "Independent HP",
905 .info = via_independent_hp_info,
906 .get = via_independent_hp_get,
907 .put = via_independent_hp_put,
0aa62aef
HW
908};
909
3d83e577 910static int via_hp_build(struct hda_codec *codec)
5b0cb1d8 911{
3d83e577 912 struct via_spec *spec = codec->spec;
5b0cb1d8
JK
913 struct snd_kcontrol_new *knew;
914 hda_nid_t nid;
5b0cb1d8 915
ece8d043
TI
916 nid = spec->autocfg.hp_pins[0];
917 knew = via_clone_control(spec, &via_hp_mixer);
3d83e577
TI
918 if (knew == NULL)
919 return -ENOMEM;
920
5b0cb1d8 921 knew->subdevice = HDA_SUBDEV_NID_FLAG | nid;
5b0cb1d8 922
5b0cb1d8
JK
923 return 0;
924}
925
1564b287
LW
926static void notify_aa_path_ctls(struct hda_codec *codec)
927{
e3d7a143 928 struct via_spec *spec = codec->spec;
1564b287 929 int i;
e3d7a143
TI
930
931 for (i = 0; i < spec->smart51_nums; i++) {
932 struct snd_kcontrol *ctl;
933 struct snd_ctl_elem_id id;
934 memset(&id, 0, sizeof(id));
935 id.iface = SNDRV_CTL_ELEM_IFACE_MIXER;
936 sprintf(id.name, "%s Playback Volume", spec->smart51_labels[i]);
525566cb
LW
937 ctl = snd_hda_find_mixer_ctl(codec, id.name);
938 if (ctl)
939 snd_ctl_notify(codec->bus->card,
940 SNDRV_CTL_EVENT_MASK_VALUE,
941 &ctl->id);
1564b287
LW
942 }
943}
944
945static void mute_aa_path(struct hda_codec *codec, int mute)
946{
947 struct via_spec *spec = codec->spec;
e3d7a143 948 int val = mute ? HDA_AMP_MUTE : HDA_AMP_UNMUTE;
1564b287 949 int i;
e3d7a143 950
1564b287 951 /* check AA path's mute status */
e3d7a143
TI
952 for (i = 0; i < spec->smart51_nums; i++) {
953 if (spec->smart51_idxs[i] < 0)
954 continue;
955 snd_hda_codec_amp_stereo(codec, spec->aa_mix_nid,
956 HDA_INPUT, spec->smart51_idxs[i],
1564b287
LW
957 HDA_AMP_MUTE, val);
958 }
959}
f4a7828b 960
e3d7a143
TI
961static bool is_smart51_pins(struct hda_codec *codec, hda_nid_t pin)
962{
963 struct via_spec *spec = codec->spec;
964 int i;
965
966 for (i = 0; i < spec->smart51_nums; i++)
967 if (spec->smart51_pins[i] == pin)
968 return true;
969 return false;
970}
971
1564b287
LW
972static int via_smart51_get(struct snd_kcontrol *kcontrol,
973 struct snd_ctl_elem_value *ucontrol)
974{
975 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
976 struct via_spec *spec = codec->spec;
1564b287 977
f2b1c9f0 978 *ucontrol->value.integer.value = spec->smart51_enabled;
1564b287
LW
979 return 0;
980}
981
982static int via_smart51_put(struct snd_kcontrol *kcontrol,
983 struct snd_ctl_elem_value *ucontrol)
984{
985 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
986 struct via_spec *spec = codec->spec;
987 int out_in = *ucontrol->value.integer.value
988 ? AC_PINCTL_OUT_EN : AC_PINCTL_IN_EN;
1564b287
LW
989 int i;
990
e3d7a143
TI
991 for (i = 0; i < spec->smart51_nums; i++) {
992 hda_nid_t nid = spec->smart51_pins[i];
7b315bb4
TI
993 unsigned int parm;
994
7b315bb4
TI
995 parm = snd_hda_codec_read(codec, nid, 0,
996 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
997 parm &= ~(AC_PINCTL_IN_EN | AC_PINCTL_OUT_EN);
998 parm |= out_in;
999 snd_hda_codec_write(codec, nid, 0,
1000 AC_VERB_SET_PIN_WIDGET_CONTROL,
1001 parm);
1002 if (out_in == AC_PINCTL_OUT_EN) {
1003 mute_aa_path(codec, 1);
1004 notify_aa_path_ctls(codec);
1005 }
1564b287
LW
1006 }
1007 spec->smart51_enabled = *ucontrol->value.integer.value;
3e95b9ab 1008 set_widgets_power_state(codec);
1564b287
LW
1009 return 1;
1010}
1011
5f4b36d6
TI
1012static const struct snd_kcontrol_new via_smart51_mixer = {
1013 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1014 .name = "Smart 5.1",
1015 .count = 1,
f2b1c9f0 1016 .info = snd_ctl_boolean_mono_info,
5f4b36d6
TI
1017 .get = via_smart51_get,
1018 .put = via_smart51_put,
1564b287
LW
1019};
1020
f4a7828b 1021static int via_smart51_build(struct hda_codec *codec)
5b0cb1d8 1022{
f4a7828b 1023 struct via_spec *spec = codec->spec;
5b0cb1d8 1024
e3d7a143 1025 if (!spec->smart51_nums)
cb34c207 1026 return 0;
e3d7a143 1027 if (!via_clone_control(spec, &via_smart51_mixer))
5b0cb1d8 1028 return -ENOMEM;
5b0cb1d8
JK
1029 return 0;
1030}
1031
ada509ec
TI
1032/* check AA path's mute status */
1033static bool is_aa_path_mute(struct hda_codec *codec)
f5271101 1034{
f5271101 1035 struct via_spec *spec = codec->spec;
ada509ec
TI
1036 const struct hda_amp_list *p;
1037 int i, ch, v;
1038
1039 for (i = 0; i < spec->num_loopbacks; i++) {
1040 p = &spec->loopback_list[i];
1041 for (ch = 0; ch < 2; ch++) {
1042 v = snd_hda_codec_amp_read(codec, p->nid, ch, p->dir,
1043 p->idx);
1044 if (!(v & HDA_AMP_MUTE) && v > 0)
1045 return false;
f5271101
LW
1046 }
1047 }
ada509ec 1048 return true;
f5271101
LW
1049}
1050
1051/* enter/exit analog low-current mode */
e9d010c2 1052static void __analog_low_current_mode(struct hda_codec *codec, bool force)
f5271101
LW
1053{
1054 struct via_spec *spec = codec->spec;
ada509ec
TI
1055 bool enable;
1056 unsigned int verb, parm;
1057
e9d010c2
TI
1058 if (spec->no_pin_power_ctl)
1059 enable = false;
1060 else
1061 enable = is_aa_path_mute(codec) && !spec->opened_streams;
1062 if (enable == spec->alc_mode && !force)
1063 return;
1064 spec->alc_mode = enable;
f5271101
LW
1065
1066 /* decide low current mode's verb & parameter */
1067 switch (spec->codec_type) {
1068 case VT1708B_8CH:
1069 case VT1708B_4CH:
1070 verb = 0xf70;
1071 parm = enable ? 0x02 : 0x00; /* 0x02: 2/3x, 0x00: 1x */
1072 break;
1073 case VT1708S:
eb7188ca 1074 case VT1718S:
f3db423d 1075 case VT1716S:
f5271101
LW
1076 verb = 0xf73;
1077 parm = enable ? 0x51 : 0xe1; /* 0x51: 4/28x, 0xe1: 1x */
1078 break;
1079 case VT1702:
1080 verb = 0xf73;
1081 parm = enable ? 0x01 : 0x1d; /* 0x01: 4/40x, 0x1d: 1x */
1082 break;
25eaba2f 1083 case VT2002P:
ab6734e7 1084 case VT1812:
11890956 1085 case VT1802:
25eaba2f
LW
1086 verb = 0xf93;
1087 parm = enable ? 0x00 : 0xe0; /* 0x00: 4/40x, 0xe0: 1x */
1088 break;
f5271101
LW
1089 default:
1090 return; /* other codecs are not supported */
1091 }
1092 /* send verb */
1093 snd_hda_codec_write(codec, codec->afg, 0, verb, parm);
1094}
1095
e9d010c2
TI
1096static void analog_low_current_mode(struct hda_codec *codec)
1097{
1098 return __analog_low_current_mode(codec, false);
1099}
1100
c577b8a1
JC
1101/*
1102 * generic initialization of ADC, input mixers and output mixers
1103 */
096a8854 1104static const struct hda_verb vt1708_init_verbs[] = {
aa266fcc
LW
1105 /* power down jack detect function */
1106 {0x1, 0xf81, 0x1},
f7278fd0 1107 { }
c577b8a1
JC
1108};
1109
3b607e3d 1110static void set_stream_open(struct hda_codec *codec, int bit, bool active)
7eb56e84 1111{
ada509ec
TI
1112 struct via_spec *spec = codec->spec;
1113
1114 if (active)
3b607e3d 1115 spec->opened_streams |= bit;
ada509ec 1116 else
3b607e3d 1117 spec->opened_streams &= ~bit;
ada509ec 1118 analog_low_current_mode(codec);
7eb56e84
TI
1119}
1120
ece8d043 1121static int via_playback_multi_pcm_open(struct hda_pcm_stream *hinfo,
c577b8a1
JC
1122 struct hda_codec *codec,
1123 struct snd_pcm_substream *substream)
1124{
1125 struct via_spec *spec = codec->spec;
25250505 1126 const struct auto_pin_cfg *cfg = &spec->autocfg;
ada509ec 1127 int err;
ece8d043 1128
25250505 1129 spec->multiout.num_dacs = cfg->line_outs + spec->smart51_nums;
25250505 1130 spec->multiout.max_channels = spec->multiout.num_dacs * 2;
3b607e3d 1131 set_stream_open(codec, STREAM_MULTI_OUT, true);
ada509ec
TI
1132 err = snd_hda_multi_out_analog_open(codec, &spec->multiout, substream,
1133 hinfo);
1134 if (err < 0) {
3b607e3d 1135 set_stream_open(codec, STREAM_MULTI_OUT, false);
ada509ec
TI
1136 return err;
1137 }
1138 return 0;
c577b8a1
JC
1139}
1140
ece8d043 1141static int via_playback_multi_pcm_close(struct hda_pcm_stream *hinfo,
9af74210
TI
1142 struct hda_codec *codec,
1143 struct snd_pcm_substream *substream)
1144{
3b607e3d 1145 set_stream_open(codec, STREAM_MULTI_OUT, false);
7eb56e84
TI
1146 return 0;
1147}
9af74210 1148
7eb56e84
TI
1149static int via_playback_hp_pcm_open(struct hda_pcm_stream *hinfo,
1150 struct hda_codec *codec,
1151 struct snd_pcm_substream *substream)
1152{
1153 struct via_spec *spec = codec->spec;
7eb56e84 1154
ece8d043 1155 if (snd_BUG_ON(!spec->hp_dac_nid))
7eb56e84 1156 return -EINVAL;
3b607e3d 1157 set_stream_open(codec, STREAM_INDEP_HP, true);
ece8d043
TI
1158 return 0;
1159}
1160
1161static int via_playback_hp_pcm_close(struct hda_pcm_stream *hinfo,
1162 struct hda_codec *codec,
1163 struct snd_pcm_substream *substream)
1164{
3b607e3d 1165 set_stream_open(codec, STREAM_INDEP_HP, false);
9af74210
TI
1166 return 0;
1167}
1168
7eb56e84
TI
1169static int via_playback_multi_pcm_prepare(struct hda_pcm_stream *hinfo,
1170 struct hda_codec *codec,
1171 unsigned int stream_tag,
1172 unsigned int format,
1173 struct snd_pcm_substream *substream)
0aa62aef
HW
1174{
1175 struct via_spec *spec = codec->spec;
ece8d043 1176
3b607e3d
TI
1177 mutex_lock(&spec->config_mutex);
1178 setup_playback_multi_pcm(spec);
ece8d043
TI
1179 snd_hda_multi_out_analog_prepare(codec, &spec->multiout, stream_tag,
1180 format, substream);
3b607e3d
TI
1181 /* remember for dynamic DAC switch with indep-HP */
1182 spec->active_streams |= STREAM_MULTI_OUT;
1183 spec->cur_dac_stream_tag = stream_tag;
1184 spec->cur_dac_format = format;
1185 mutex_unlock(&spec->config_mutex);
187d333e 1186 vt1708_update_hp_work(spec);
7eb56e84 1187 return 0;
0aa62aef
HW
1188}
1189
7eb56e84
TI
1190static int via_playback_hp_pcm_prepare(struct hda_pcm_stream *hinfo,
1191 struct hda_codec *codec,
1192 unsigned int stream_tag,
1193 unsigned int format,
1194 struct snd_pcm_substream *substream)
0aa62aef
HW
1195{
1196 struct via_spec *spec = codec->spec;
0aa62aef 1197
3b607e3d
TI
1198 mutex_lock(&spec->config_mutex);
1199 if (spec->hp_independent_mode)
1200 snd_hda_codec_setup_stream(codec, spec->hp_dac_nid,
1201 stream_tag, 0, format);
1202 spec->active_streams |= STREAM_INDEP_HP;
1203 spec->cur_hp_stream_tag = stream_tag;
1204 spec->cur_hp_format = format;
1205 mutex_unlock(&spec->config_mutex);
187d333e 1206 vt1708_update_hp_work(spec);
0aa62aef
HW
1207 return 0;
1208}
1209
1210static int via_playback_multi_pcm_cleanup(struct hda_pcm_stream *hinfo,
1211 struct hda_codec *codec,
1212 struct snd_pcm_substream *substream)
1213{
1214 struct via_spec *spec = codec->spec;
0aa62aef 1215
3b607e3d 1216 mutex_lock(&spec->config_mutex);
ece8d043 1217 snd_hda_multi_out_analog_cleanup(codec, &spec->multiout);
3b607e3d
TI
1218 spec->active_streams &= ~STREAM_MULTI_OUT;
1219 mutex_unlock(&spec->config_mutex);
187d333e 1220 vt1708_update_hp_work(spec);
7eb56e84
TI
1221 return 0;
1222}
1223
1224static int via_playback_hp_pcm_cleanup(struct hda_pcm_stream *hinfo,
1225 struct hda_codec *codec,
1226 struct snd_pcm_substream *substream)
1227{
1228 struct via_spec *spec = codec->spec;
7eb56e84 1229
3b607e3d
TI
1230 mutex_lock(&spec->config_mutex);
1231 if (spec->hp_independent_mode)
1232 snd_hda_codec_setup_stream(codec, spec->hp_dac_nid, 0, 0, 0);
1233 spec->active_streams &= ~STREAM_INDEP_HP;
1234 mutex_unlock(&spec->config_mutex);
187d333e 1235 vt1708_update_hp_work(spec);
0aa62aef
HW
1236 return 0;
1237}
1238
c577b8a1
JC
1239/*
1240 * Digital out
1241 */
1242static int via_dig_playback_pcm_open(struct hda_pcm_stream *hinfo,
1243 struct hda_codec *codec,
1244 struct snd_pcm_substream *substream)
1245{
1246 struct via_spec *spec = codec->spec;
1247 return snd_hda_multi_out_dig_open(codec, &spec->multiout);
1248}
1249
1250static int via_dig_playback_pcm_close(struct hda_pcm_stream *hinfo,
1251 struct hda_codec *codec,
1252 struct snd_pcm_substream *substream)
1253{
1254 struct via_spec *spec = codec->spec;
1255 return snd_hda_multi_out_dig_close(codec, &spec->multiout);
1256}
1257
5691ec7f 1258static int via_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
98aa34c0
HW
1259 struct hda_codec *codec,
1260 unsigned int stream_tag,
1261 unsigned int format,
1262 struct snd_pcm_substream *substream)
1263{
1264 struct via_spec *spec = codec->spec;
9da29271
TI
1265 return snd_hda_multi_out_dig_prepare(codec, &spec->multiout,
1266 stream_tag, format, substream);
1267}
98aa34c0 1268
9da29271
TI
1269static int via_dig_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
1270 struct hda_codec *codec,
1271 struct snd_pcm_substream *substream)
1272{
1273 struct via_spec *spec = codec->spec;
1274 snd_hda_multi_out_dig_cleanup(codec, &spec->multiout);
98aa34c0
HW
1275 return 0;
1276}
1277
c577b8a1
JC
1278/*
1279 * Analog capture
1280 */
1281static int via_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
1282 struct hda_codec *codec,
1283 unsigned int stream_tag,
1284 unsigned int format,
1285 struct snd_pcm_substream *substream)
1286{
1287 struct via_spec *spec = codec->spec;
1288
1289 snd_hda_codec_setup_stream(codec, spec->adc_nids[substream->number],
1290 stream_tag, 0, format);
1291 return 0;
1292}
1293
1294static int via_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
1295 struct hda_codec *codec,
1296 struct snd_pcm_substream *substream)
1297{
1298 struct via_spec *spec = codec->spec;
888afa15 1299 snd_hda_codec_cleanup_stream(codec, spec->adc_nids[substream->number]);
c577b8a1
JC
1300 return 0;
1301}
1302
a86a88ea
TI
1303/* analog capture with dynamic ADC switching */
1304static int via_dyn_adc_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
1305 struct hda_codec *codec,
1306 unsigned int stream_tag,
1307 unsigned int format,
1308 struct snd_pcm_substream *substream)
1309{
1310 struct via_spec *spec = codec->spec;
1311 int adc_idx = spec->inputs[spec->cur_mux[0]].adc_idx;
1312
3b607e3d 1313 mutex_lock(&spec->config_mutex);
a86a88ea
TI
1314 spec->cur_adc = spec->adc_nids[adc_idx];
1315 spec->cur_adc_stream_tag = stream_tag;
1316 spec->cur_adc_format = format;
1317 snd_hda_codec_setup_stream(codec, spec->cur_adc, stream_tag, 0, format);
3b607e3d 1318 mutex_unlock(&spec->config_mutex);
a86a88ea
TI
1319 return 0;
1320}
1321
1322static int via_dyn_adc_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
1323 struct hda_codec *codec,
1324 struct snd_pcm_substream *substream)
1325{
1326 struct via_spec *spec = codec->spec;
1327
3b607e3d 1328 mutex_lock(&spec->config_mutex);
a86a88ea
TI
1329 snd_hda_codec_cleanup_stream(codec, spec->cur_adc);
1330 spec->cur_adc = 0;
3b607e3d 1331 mutex_unlock(&spec->config_mutex);
a86a88ea
TI
1332 return 0;
1333}
1334
1335/* re-setup the stream if running; called from input-src put */
1336static bool via_dyn_adc_pcm_resetup(struct hda_codec *codec, int cur)
1337{
1338 struct via_spec *spec = codec->spec;
1339 int adc_idx = spec->inputs[cur].adc_idx;
1340 hda_nid_t adc = spec->adc_nids[adc_idx];
3b607e3d 1341 bool ret = false;
a86a88ea 1342
3b607e3d 1343 mutex_lock(&spec->config_mutex);
a86a88ea
TI
1344 if (spec->cur_adc && spec->cur_adc != adc) {
1345 /* stream is running, let's swap the current ADC */
1346 __snd_hda_codec_cleanup_stream(codec, spec->cur_adc, 1);
1347 spec->cur_adc = adc;
1348 snd_hda_codec_setup_stream(codec, adc,
1349 spec->cur_adc_stream_tag, 0,
1350 spec->cur_adc_format);
3b607e3d 1351 ret = true;
a86a88ea 1352 }
3b607e3d
TI
1353 mutex_unlock(&spec->config_mutex);
1354 return ret;
a86a88ea
TI
1355}
1356
9af74210 1357static const struct hda_pcm_stream via_pcm_analog_playback = {
7eb56e84 1358 .substreams = 1,
c577b8a1
JC
1359 .channels_min = 2,
1360 .channels_max = 8,
9af74210 1361 /* NID is set in via_build_pcms */
c577b8a1 1362 .ops = {
ece8d043
TI
1363 .open = via_playback_multi_pcm_open,
1364 .close = via_playback_multi_pcm_close,
0aa62aef
HW
1365 .prepare = via_playback_multi_pcm_prepare,
1366 .cleanup = via_playback_multi_pcm_cleanup
c577b8a1
JC
1367 },
1368};
1369
7eb56e84
TI
1370static const struct hda_pcm_stream via_pcm_hp_playback = {
1371 .substreams = 1,
1372 .channels_min = 2,
1373 .channels_max = 2,
1374 /* NID is set in via_build_pcms */
1375 .ops = {
1376 .open = via_playback_hp_pcm_open,
ece8d043 1377 .close = via_playback_hp_pcm_close,
7eb56e84
TI
1378 .prepare = via_playback_hp_pcm_prepare,
1379 .cleanup = via_playback_hp_pcm_cleanup
1380 },
1381};
1382
90dd48a1 1383static const struct hda_pcm_stream vt1708_pcm_analog_s16_playback = {
7eb56e84 1384 .substreams = 1,
bc9b5623
TI
1385 .channels_min = 2,
1386 .channels_max = 8,
9af74210 1387 /* NID is set in via_build_pcms */
bc9b5623
TI
1388 /* We got noisy outputs on the right channel on VT1708 when
1389 * 24bit samples are used. Until any workaround is found,
1390 * disable the 24bit format, so far.
1391 */
1392 .formats = SNDRV_PCM_FMTBIT_S16_LE,
1393 .ops = {
ece8d043
TI
1394 .open = via_playback_multi_pcm_open,
1395 .close = via_playback_multi_pcm_close,
c873cc25
LW
1396 .prepare = via_playback_multi_pcm_prepare,
1397 .cleanup = via_playback_multi_pcm_cleanup
bc9b5623
TI
1398 },
1399};
1400
9af74210 1401static const struct hda_pcm_stream via_pcm_analog_capture = {
7eb56e84 1402 .substreams = 1, /* will be changed in via_build_pcms() */
c577b8a1
JC
1403 .channels_min = 2,
1404 .channels_max = 2,
9af74210 1405 /* NID is set in via_build_pcms */
c577b8a1
JC
1406 .ops = {
1407 .prepare = via_capture_pcm_prepare,
1408 .cleanup = via_capture_pcm_cleanup
1409 },
1410};
1411
a86a88ea
TI
1412static const struct hda_pcm_stream via_pcm_dyn_adc_analog_capture = {
1413 .substreams = 1,
1414 .channels_min = 2,
1415 .channels_max = 2,
1416 /* NID is set in via_build_pcms */
1417 .ops = {
1418 .prepare = via_dyn_adc_capture_pcm_prepare,
1419 .cleanup = via_dyn_adc_capture_pcm_cleanup,
1420 },
1421};
1422
9af74210 1423static const struct hda_pcm_stream via_pcm_digital_playback = {
c577b8a1
JC
1424 .substreams = 1,
1425 .channels_min = 2,
1426 .channels_max = 2,
1427 /* NID is set in via_build_pcms */
1428 .ops = {
1429 .open = via_dig_playback_pcm_open,
6b97eb45 1430 .close = via_dig_playback_pcm_close,
9da29271
TI
1431 .prepare = via_dig_playback_pcm_prepare,
1432 .cleanup = via_dig_playback_pcm_cleanup
c577b8a1
JC
1433 },
1434};
1435
9af74210 1436static const struct hda_pcm_stream via_pcm_digital_capture = {
c577b8a1
JC
1437 .substreams = 1,
1438 .channels_min = 2,
1439 .channels_max = 2,
1440};
1441
370bafbd
TI
1442/*
1443 * slave controls for virtual master
1444 */
1445static const char * const via_slave_vols[] = {
1446 "Front Playback Volume",
1447 "Surround Playback Volume",
1448 "Center Playback Volume",
1449 "LFE Playback Volume",
1450 "Side Playback Volume",
1451 "Headphone Playback Volume",
1452 "Speaker Playback Volume",
1453 NULL,
1454};
1455
1456static const char * const via_slave_sws[] = {
1457 "Front Playback Switch",
1458 "Surround Playback Switch",
1459 "Center Playback Switch",
1460 "LFE Playback Switch",
1461 "Side Playback Switch",
1462 "Headphone Playback Switch",
1463 "Speaker Playback Switch",
1464 NULL,
1465};
1466
c577b8a1
JC
1467static int via_build_controls(struct hda_codec *codec)
1468{
1469 struct via_spec *spec = codec->spec;
5b0cb1d8 1470 struct snd_kcontrol *kctl;
5b0cb1d8 1471 int err, i;
c577b8a1 1472
b5bcc189 1473 spec->no_pin_power_ctl = 1;
24088a58
TI
1474 if (spec->set_widgets_power_state)
1475 if (!via_clone_control(spec, &via_pin_power_ctl_enum))
1476 return -ENOMEM;
1477
c577b8a1
JC
1478 for (i = 0; i < spec->num_mixers; i++) {
1479 err = snd_hda_add_new_ctls(codec, spec->mixers[i]);
1480 if (err < 0)
1481 return err;
1482 }
1483
1484 if (spec->multiout.dig_out_nid) {
1485 err = snd_hda_create_spdif_out_ctls(codec,
74b654c9 1486 spec->multiout.dig_out_nid,
c577b8a1
JC
1487 spec->multiout.dig_out_nid);
1488 if (err < 0)
1489 return err;
9a08160b
TI
1490 err = snd_hda_create_spdif_share_sw(codec,
1491 &spec->multiout);
1492 if (err < 0)
1493 return err;
1494 spec->multiout.share_spdif = 1;
c577b8a1
JC
1495 }
1496 if (spec->dig_in_nid) {
1497 err = snd_hda_create_spdif_in_ctls(codec, spec->dig_in_nid);
1498 if (err < 0)
1499 return err;
1500 }
17314379 1501
370bafbd
TI
1502 /* if we have no master control, let's create it */
1503 if (!snd_hda_find_mixer_ctl(codec, "Master Playback Volume")) {
1504 unsigned int vmaster_tlv[4];
1505 snd_hda_set_vmaster_tlv(codec, spec->multiout.dac_nids[0],
1506 HDA_OUTPUT, vmaster_tlv);
1507 err = snd_hda_add_vmaster(codec, "Master Playback Volume",
1508 vmaster_tlv, via_slave_vols);
1509 if (err < 0)
1510 return err;
1511 }
1512 if (!snd_hda_find_mixer_ctl(codec, "Master Playback Switch")) {
1513 err = snd_hda_add_vmaster(codec, "Master Playback Switch",
1514 NULL, via_slave_sws);
1515 if (err < 0)
1516 return err;
1517 }
1518
5b0cb1d8
JK
1519 /* assign Capture Source enums to NID */
1520 kctl = snd_hda_find_mixer_ctl(codec, "Input Source");
1521 for (i = 0; kctl && i < kctl->count; i++) {
21949f00 1522 err = snd_hda_add_nid(codec, kctl, i, spec->mux_nids[i]);
5b0cb1d8
JK
1523 if (err < 0)
1524 return err;
1525 }
1526
603c4019 1527 via_free_kctls(codec); /* no longer needed */
01a61e12
TI
1528
1529 err = snd_hda_jack_add_kctls(codec, &spec->autocfg);
1530 if (err < 0)
1531 return err;
1532
c577b8a1
JC
1533 return 0;
1534}
1535
1536static int via_build_pcms(struct hda_codec *codec)
1537{
1538 struct via_spec *spec = codec->spec;
1539 struct hda_pcm *info = spec->pcm_rec;
1540
a5973103 1541 codec->num_pcms = 0;
c577b8a1
JC
1542 codec->pcm_info = info;
1543
a5973103
TI
1544 if (spec->multiout.num_dacs || spec->num_adc_nids) {
1545 snprintf(spec->stream_name_analog,
1546 sizeof(spec->stream_name_analog),
1547 "%s Analog", codec->chip_name);
1548 info->name = spec->stream_name_analog;
9af74210 1549
a5973103
TI
1550 if (spec->multiout.num_dacs) {
1551 if (!spec->stream_analog_playback)
1552 spec->stream_analog_playback =
1553 &via_pcm_analog_playback;
1554 info->stream[SNDRV_PCM_STREAM_PLAYBACK] =
1555 *spec->stream_analog_playback;
1556 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid =
1557 spec->multiout.dac_nids[0];
1558 info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max =
1559 spec->multiout.max_channels;
1560 }
c577b8a1 1561
a5973103
TI
1562 if (!spec->stream_analog_capture) {
1563 if (spec->dyn_adc_switch)
1564 spec->stream_analog_capture =
1565 &via_pcm_dyn_adc_analog_capture;
1566 else
1567 spec->stream_analog_capture =
1568 &via_pcm_analog_capture;
1569 }
1570 if (spec->num_adc_nids) {
1571 info->stream[SNDRV_PCM_STREAM_CAPTURE] =
1572 *spec->stream_analog_capture;
1573 info->stream[SNDRV_PCM_STREAM_CAPTURE].nid =
1574 spec->adc_nids[0];
1575 if (!spec->dyn_adc_switch)
1576 info->stream[SNDRV_PCM_STREAM_CAPTURE].substreams =
1577 spec->num_adc_nids;
1578 }
1579 codec->num_pcms++;
1580 info++;
a86a88ea 1581 }
c577b8a1
JC
1582
1583 if (spec->multiout.dig_out_nid || spec->dig_in_nid) {
82673bc8
TI
1584 snprintf(spec->stream_name_digital,
1585 sizeof(spec->stream_name_digital),
1586 "%s Digital", codec->chip_name);
c577b8a1 1587 info->name = spec->stream_name_digital;
7ba72ba1 1588 info->pcm_type = HDA_PCM_TYPE_SPDIF;
c577b8a1 1589 if (spec->multiout.dig_out_nid) {
9af74210
TI
1590 if (!spec->stream_digital_playback)
1591 spec->stream_digital_playback =
1592 &via_pcm_digital_playback;
c577b8a1 1593 info->stream[SNDRV_PCM_STREAM_PLAYBACK] =
9af74210 1594 *spec->stream_digital_playback;
c577b8a1
JC
1595 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid =
1596 spec->multiout.dig_out_nid;
1597 }
1598 if (spec->dig_in_nid) {
9af74210
TI
1599 if (!spec->stream_digital_capture)
1600 spec->stream_digital_capture =
1601 &via_pcm_digital_capture;
c577b8a1 1602 info->stream[SNDRV_PCM_STREAM_CAPTURE] =
9af74210 1603 *spec->stream_digital_capture;
c577b8a1
JC
1604 info->stream[SNDRV_PCM_STREAM_CAPTURE].nid =
1605 spec->dig_in_nid;
1606 }
a5973103
TI
1607 codec->num_pcms++;
1608 info++;
c577b8a1
JC
1609 }
1610
ece8d043 1611 if (spec->hp_dac_nid) {
7eb56e84
TI
1612 snprintf(spec->stream_name_hp, sizeof(spec->stream_name_hp),
1613 "%s HP", codec->chip_name);
1614 info->name = spec->stream_name_hp;
1615 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = via_pcm_hp_playback;
1616 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid =
ece8d043 1617 spec->hp_dac_nid;
a5973103
TI
1618 codec->num_pcms++;
1619 info++;
7eb56e84 1620 }
c577b8a1
JC
1621 return 0;
1622}
1623
1624static void via_free(struct hda_codec *codec)
1625{
1626 struct via_spec *spec = codec->spec;
c577b8a1
JC
1627
1628 if (!spec)
1629 return;
1630
603c4019 1631 via_free_kctls(codec);
1f2e99fe 1632 vt1708_stop_hp_work(spec);
a86a88ea
TI
1633 kfree(spec->bind_cap_vol);
1634 kfree(spec->bind_cap_sw);
1635 kfree(spec);
c577b8a1
JC
1636}
1637
64be285b
TI
1638/* mute/unmute outputs */
1639static void toggle_output_mutes(struct hda_codec *codec, int num_pins,
1640 hda_nid_t *pins, bool mute)
1641{
1642 int i;
94994734
TI
1643 for (i = 0; i < num_pins; i++) {
1644 unsigned int parm = snd_hda_codec_read(codec, pins[i], 0,
1645 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
1646 if (parm & AC_PINCTL_IN_EN)
1647 continue;
1648 if (mute)
1649 parm &= ~AC_PINCTL_OUT_EN;
1650 else
1651 parm |= AC_PINCTL_OUT_EN;
64be285b 1652 snd_hda_codec_write(codec, pins[i], 0,
94994734
TI
1653 AC_VERB_SET_PIN_WIDGET_CONTROL, parm);
1654 }
64be285b
TI
1655}
1656
4a918ffe
TI
1657/* mute internal speaker if line-out is plugged */
1658static void via_line_automute(struct hda_codec *codec, int present)
69e52a80 1659{
69e52a80
HW
1660 struct via_spec *spec = codec->spec;
1661
4a918ffe
TI
1662 if (!spec->autocfg.speaker_outs)
1663 return;
1664 if (!present)
1665 present = snd_hda_jack_detect(codec,
1666 spec->autocfg.line_out_pins[0]);
1667 toggle_output_mutes(codec, spec->autocfg.speaker_outs,
1668 spec->autocfg.speaker_pins,
1669 present);
69e52a80
HW
1670}
1671
4a918ffe
TI
1672/* mute internal speaker if HP is plugged */
1673static void via_hp_automute(struct hda_codec *codec)
f3db423d 1674{
4a918ffe 1675 int present = 0;
6e969d91 1676 int nums;
f3db423d
LW
1677 struct via_spec *spec = codec->spec;
1678
187d333e
TI
1679 if (!spec->hp_independent_mode && spec->autocfg.hp_pins[0] &&
1680 (spec->codec_type != VT1708 || spec->vt1708_jack_detect))
4a918ffe 1681 present = snd_hda_jack_detect(codec, spec->autocfg.hp_pins[0]);
6e969d91
TI
1682
1683 if (spec->smart51_enabled)
1684 nums = spec->autocfg.line_outs + spec->smart51_nums;
1685 else
1686 nums = spec->autocfg.line_outs;
1687 toggle_output_mutes(codec, nums, spec->autocfg.line_out_pins, present);
1688
4a918ffe 1689 via_line_automute(codec, present);
f3db423d
LW
1690}
1691
69e52a80
HW
1692static void via_gpio_control(struct hda_codec *codec)
1693{
1694 unsigned int gpio_data;
1695 unsigned int vol_counter;
1696 unsigned int vol;
1697 unsigned int master_vol;
1698
1699 struct via_spec *spec = codec->spec;
1700
1701 gpio_data = snd_hda_codec_read(codec, codec->afg, 0,
1702 AC_VERB_GET_GPIO_DATA, 0) & 0x03;
1703
1704 vol_counter = (snd_hda_codec_read(codec, codec->afg, 0,
1705 0xF84, 0) & 0x3F0000) >> 16;
1706
1707 vol = vol_counter & 0x1F;
1708 master_vol = snd_hda_codec_read(codec, 0x1A, 0,
1709 AC_VERB_GET_AMP_GAIN_MUTE,
1710 AC_AMP_GET_INPUT);
1711
1712 if (gpio_data == 0x02) {
1713 /* unmute line out */
3e0693e2
TI
1714 snd_hda_codec_write(codec, spec->autocfg.line_out_pins[0], 0,
1715 AC_VERB_SET_PIN_WIDGET_CONTROL,
1716 PIN_OUT);
69e52a80
HW
1717 if (vol_counter & 0x20) {
1718 /* decrease volume */
1719 if (vol > master_vol)
1720 vol = master_vol;
1721 snd_hda_codec_amp_stereo(codec, 0x1A, HDA_INPUT,
1722 0, HDA_AMP_VOLMASK,
1723 master_vol-vol);
1724 } else {
1725 /* increase volume */
1726 snd_hda_codec_amp_stereo(codec, 0x1A, HDA_INPUT, 0,
1727 HDA_AMP_VOLMASK,
1728 ((master_vol+vol) > 0x2A) ? 0x2A :
1729 (master_vol+vol));
1730 }
1731 } else if (!(gpio_data & 0x02)) {
1732 /* mute line out */
3e0693e2
TI
1733 snd_hda_codec_write(codec, spec->autocfg.line_out_pins[0], 0,
1734 AC_VERB_SET_PIN_WIDGET_CONTROL,
1735 0);
69e52a80
HW
1736 }
1737}
1738
1739/* unsolicited event for jack sensing */
1740static void via_unsol_event(struct hda_codec *codec,
1741 unsigned int res)
1742{
1743 res >>= 26;
3a93897e 1744 res = snd_hda_jack_get_action(codec, res);
ec7e7e42 1745
a34df19a 1746 if (res & VIA_JACK_EVENT)
3e95b9ab 1747 set_widgets_power_state(codec);
ec7e7e42
LW
1748
1749 res &= ~VIA_JACK_EVENT;
1750
21ce0b65 1751 if (res == VIA_HP_EVENT || res == VIA_LINE_EVENT)
ec7e7e42
LW
1752 via_hp_automute(codec);
1753 else if (res == VIA_GPIO_EVENT)
1754 via_gpio_control(codec);
01a61e12 1755 snd_hda_jack_report_sync(codec);
69e52a80
HW
1756}
1757
2a43952a 1758#ifdef CONFIG_PM
1f2e99fe
LW
1759static int via_suspend(struct hda_codec *codec, pm_message_t state)
1760{
1761 struct via_spec *spec = codec->spec;
1762 vt1708_stop_hp_work(spec);
1763 return 0;
1764}
1765#endif
1766
cb53c626
TI
1767#ifdef CONFIG_SND_HDA_POWER_SAVE
1768static int via_check_power_status(struct hda_codec *codec, hda_nid_t nid)
1769{
1770 struct via_spec *spec = codec->spec;
1771 return snd_hda_check_amp_list_power(codec, &spec->loopback, nid);
1772}
1773#endif
1774
c577b8a1
JC
1775/*
1776 */
5d41762a
TI
1777
1778static int via_init(struct hda_codec *codec);
1779
90dd48a1 1780static const struct hda_codec_ops via_patch_ops = {
c577b8a1
JC
1781 .build_controls = via_build_controls,
1782 .build_pcms = via_build_pcms,
1783 .init = via_init,
1784 .free = via_free,
4a918ffe 1785 .unsol_event = via_unsol_event,
2a43952a 1786#ifdef CONFIG_PM
1f2e99fe
LW
1787 .suspend = via_suspend,
1788#endif
cb53c626
TI
1789#ifdef CONFIG_SND_HDA_POWER_SAVE
1790 .check_power_status = via_check_power_status,
1791#endif
c577b8a1
JC
1792};
1793
4a79616d
TI
1794static bool is_empty_dac(struct hda_codec *codec, hda_nid_t dac)
1795{
1796 struct via_spec *spec = codec->spec;
1797 int i;
1798
1799 for (i = 0; i < spec->multiout.num_dacs; i++) {
1800 if (spec->multiout.dac_nids[i] == dac)
1801 return false;
1802 }
ece8d043 1803 if (spec->hp_dac_nid == dac)
4a79616d
TI
1804 return false;
1805 return true;
1806}
1807
8e3679dc 1808static bool __parse_output_path(struct hda_codec *codec, hda_nid_t nid,
3214b966
TI
1809 hda_nid_t target_dac, int with_aa_mix,
1810 struct nid_path *path, int depth)
4a79616d 1811{
3214b966 1812 struct via_spec *spec = codec->spec;
4a79616d
TI
1813 hda_nid_t conn[8];
1814 int i, nums;
1815
3214b966
TI
1816 if (nid == spec->aa_mix_nid) {
1817 if (!with_aa_mix)
1818 return false;
1819 with_aa_mix = 2; /* mark aa-mix is included */
1820 }
1821
4a79616d
TI
1822 nums = snd_hda_get_connections(codec, nid, conn, ARRAY_SIZE(conn));
1823 for (i = 0; i < nums; i++) {
1824 if (get_wcaps_type(get_wcaps(codec, conn[i])) != AC_WID_AUD_OUT)
1825 continue;
3214b966
TI
1826 if (conn[i] == target_dac || is_empty_dac(codec, conn[i])) {
1827 /* aa-mix is requested but not included? */
1828 if (!(spec->aa_mix_nid && with_aa_mix == 1))
1829 goto found;
1830 }
4a79616d 1831 }
8e3679dc 1832 if (depth >= MAX_NID_PATH_DEPTH)
4a79616d
TI
1833 return false;
1834 for (i = 0; i < nums; i++) {
1835 unsigned int type;
1836 type = get_wcaps_type(get_wcaps(codec, conn[i]));
3214b966 1837 if (type == AC_WID_AUD_OUT)
4a79616d 1838 continue;
8e3679dc 1839 if (__parse_output_path(codec, conn[i], target_dac,
3214b966 1840 with_aa_mix, path, depth + 1))
09a9ad69 1841 goto found;
4a79616d
TI
1842 }
1843 return false;
09a9ad69
TI
1844
1845 found:
1846 path->path[path->depth] = conn[i];
1847 path->idx[path->depth] = i;
1848 if (nums > 1 && get_wcaps_type(get_wcaps(codec, nid)) != AC_WID_AUD_MIX)
1849 path->multi[path->depth] = 1;
1850 path->depth++;
1851 return true;
4a79616d
TI
1852}
1853
8e3679dc 1854static bool parse_output_path(struct hda_codec *codec, hda_nid_t nid,
3214b966
TI
1855 hda_nid_t target_dac, int with_aa_mix,
1856 struct nid_path *path)
8e3679dc 1857{
3214b966 1858 if (__parse_output_path(codec, nid, target_dac, with_aa_mix, path, 1)) {
8e3679dc
TI
1859 path->path[path->depth] = nid;
1860 path->depth++;
3214b966
TI
1861 snd_printdd("output-path: depth=%d, %02x/%02x/%02x/%02x/%02x\n",
1862 path->depth, path->path[0], path->path[1],
1863 path->path[2], path->path[3], path->path[4]);
8e3679dc
TI
1864 return true;
1865 }
1866 return false;
1867}
1868
4a79616d 1869static int via_auto_fill_dac_nids(struct hda_codec *codec)
c577b8a1 1870{
4a79616d
TI
1871 struct via_spec *spec = codec->spec;
1872 const struct auto_pin_cfg *cfg = &spec->autocfg;
5c9a5615 1873 int i, dac_num;
c577b8a1
JC
1874 hda_nid_t nid;
1875
4a79616d 1876 spec->multiout.dac_nids = spec->private_dac_nids;
5c9a5615 1877 dac_num = 0;
4a79616d 1878 for (i = 0; i < cfg->line_outs; i++) {
3214b966 1879 hda_nid_t dac = 0;
4a79616d
TI
1880 nid = cfg->line_out_pins[i];
1881 if (!nid)
1882 continue;
3214b966
TI
1883 if (parse_output_path(codec, nid, 0, 0, &spec->out_path[i]))
1884 dac = spec->out_path[i].path[0];
1885 if (!i && parse_output_path(codec, nid, dac, 1,
1886 &spec->out_mix_path))
1887 dac = spec->out_mix_path.path[0];
1888 if (dac) {
1889 spec->private_dac_nids[i] = dac;
5c9a5615
LW
1890 dac_num++;
1891 }
4a79616d 1892 }
3214b966
TI
1893 if (!spec->out_path[0].depth && spec->out_mix_path.depth) {
1894 spec->out_path[0] = spec->out_mix_path;
1895 spec->out_mix_path.depth = 0;
1896 }
5c9a5615 1897 spec->multiout.num_dacs = dac_num;
4a79616d
TI
1898 return 0;
1899}
c577b8a1 1900
4a79616d 1901static int create_ch_ctls(struct hda_codec *codec, const char *pfx,
09a9ad69 1902 int chs, bool check_dac, struct nid_path *path)
4a79616d
TI
1903{
1904 struct via_spec *spec = codec->spec;
1905 char name[32];
09a9ad69
TI
1906 hda_nid_t dac, pin, sel, nid;
1907 int err;
a934d5a9 1908
09a9ad69
TI
1909 dac = check_dac ? path->path[0] : 0;
1910 pin = path->path[path->depth - 1];
1911 sel = path->depth > 1 ? path->path[1] : 0;
377ff31a 1912
8df2a312 1913 if (dac && check_amp_caps(codec, dac, HDA_OUTPUT, AC_AMPCAP_NUM_STEPS))
4a79616d 1914 nid = dac;
8df2a312 1915 else if (check_amp_caps(codec, pin, HDA_OUTPUT, AC_AMPCAP_NUM_STEPS))
4a79616d 1916 nid = pin;
a934d5a9
TI
1917 else if (check_amp_caps(codec, sel, HDA_OUTPUT, AC_AMPCAP_NUM_STEPS))
1918 nid = sel;
4a79616d
TI
1919 else
1920 nid = 0;
1921 if (nid) {
1922 sprintf(name, "%s Playback Volume", pfx);
1923 err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
a00a5fad 1924 HDA_COMPOSE_AMP_VAL(nid, chs, 0, HDA_OUTPUT));
4a79616d
TI
1925 if (err < 0)
1926 return err;
09a9ad69 1927 path->vol_ctl = nid;
c577b8a1
JC
1928 }
1929
8df2a312 1930 if (dac && check_amp_caps(codec, dac, HDA_OUTPUT, AC_AMPCAP_MUTE))
4a79616d 1931 nid = dac;
8df2a312 1932 else if (check_amp_caps(codec, pin, HDA_OUTPUT, AC_AMPCAP_MUTE))
4a79616d 1933 nid = pin;
a934d5a9
TI
1934 else if (check_amp_caps(codec, sel, HDA_OUTPUT, AC_AMPCAP_MUTE))
1935 nid = sel;
4a79616d
TI
1936 else
1937 nid = 0;
1938 if (nid) {
1939 sprintf(name, "%s Playback Switch", pfx);
1940 err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
1941 HDA_COMPOSE_AMP_VAL(nid, chs, 0, HDA_OUTPUT));
1942 if (err < 0)
1943 return err;
09a9ad69 1944 path->mute_ctl = nid;
4a79616d 1945 }
c577b8a1
JC
1946 return 0;
1947}
1948
f4a7828b
TI
1949static void mangle_smart51(struct hda_codec *codec)
1950{
1951 struct via_spec *spec = codec->spec;
1952 struct auto_pin_cfg *cfg = &spec->autocfg;
0f98c24b
TI
1953 struct auto_pin_cfg_item *ins = cfg->inputs;
1954 int i, j, nums, attr;
1955 int pins[AUTO_CFG_MAX_INS];
1956
1957 for (attr = INPUT_PIN_ATTR_REAR; attr >= INPUT_PIN_ATTR_NORMAL; attr--) {
1958 nums = 0;
1959 for (i = 0; i < cfg->num_inputs; i++) {
1960 unsigned int def;
1961 if (ins[i].type > AUTO_PIN_LINE_IN)
1962 continue;
1963 def = snd_hda_codec_get_pincfg(codec, ins[i].pin);
1964 if (snd_hda_get_input_pin_attr(def) != attr)
1965 continue;
1966 for (j = 0; j < nums; j++)
1967 if (ins[pins[j]].type < ins[i].type) {
1968 memmove(pins + j + 1, pins + j,
21d45d2b 1969 (nums - j) * sizeof(int));
0f98c24b
TI
1970 break;
1971 }
1972 pins[j] = i;
e3d7a143 1973 nums++;
0f98c24b
TI
1974 }
1975 if (cfg->line_outs + nums < 3)
f4a7828b 1976 continue;
0f98c24b
TI
1977 for (i = 0; i < nums; i++) {
1978 hda_nid_t pin = ins[pins[i]].pin;
1979 spec->smart51_pins[spec->smart51_nums++] = pin;
1980 cfg->line_out_pins[cfg->line_outs++] = pin;
1981 if (cfg->line_outs == 3)
1982 break;
1983 }
1984 return;
f4a7828b
TI
1985 }
1986}
1987
020066d1
TI
1988static void copy_path_mixer_ctls(struct nid_path *dst, struct nid_path *src)
1989{
1990 dst->vol_ctl = src->vol_ctl;
1991 dst->mute_ctl = src->mute_ctl;
1992}
1993
c577b8a1 1994/* add playback controls from the parsed DAC table */
4a79616d 1995static int via_auto_create_multi_out_ctls(struct hda_codec *codec)
c577b8a1 1996{
4a79616d 1997 struct via_spec *spec = codec->spec;
f4a7828b 1998 struct auto_pin_cfg *cfg = &spec->autocfg;
3214b966 1999 struct nid_path *path;
ea734963
TI
2000 static const char * const chname[4] = {
2001 "Front", "Surround", "C/LFE", "Side"
2002 };
4a79616d 2003 int i, idx, err;
f4a7828b
TI
2004 int old_line_outs;
2005
2006 /* check smart51 */
2007 old_line_outs = cfg->line_outs;
2008 if (cfg->line_outs == 1)
2009 mangle_smart51(codec);
c577b8a1 2010
e3d7a143
TI
2011 err = via_auto_fill_dac_nids(codec);
2012 if (err < 0)
2013 return err;
2014
5c9a5615
LW
2015 if (spec->multiout.num_dacs < 3) {
2016 spec->smart51_nums = 0;
2017 cfg->line_outs = old_line_outs;
2018 }
4a79616d
TI
2019 for (i = 0; i < cfg->line_outs; i++) {
2020 hda_nid_t pin, dac;
2021 pin = cfg->line_out_pins[i];
2022 dac = spec->multiout.dac_nids[i];
2023 if (!pin || !dac)
c577b8a1 2024 continue;
3214b966 2025 path = spec->out_path + i;
0fe0adf8 2026 if (i == HDA_CLFE) {
3214b966 2027 err = create_ch_ctls(codec, "Center", 1, true, path);
c577b8a1
JC
2028 if (err < 0)
2029 return err;
3214b966 2030 err = create_ch_ctls(codec, "LFE", 2, true, path);
c577b8a1
JC
2031 if (err < 0)
2032 return err;
2033 } else {
6aadf41d
TI
2034 const char *pfx = chname[i];
2035 if (cfg->line_out_type == AUTO_PIN_SPEAKER_OUT &&
2036 cfg->line_outs == 1)
2037 pfx = "Speaker";
3214b966 2038 err = create_ch_ctls(codec, pfx, 3, true, path);
c577b8a1
JC
2039 if (err < 0)
2040 return err;
2041 }
020066d1
TI
2042 if (path != spec->out_path + i)
2043 copy_path_mixer_ctls(&spec->out_path[i], path);
2044 if (path == spec->out_path && spec->out_mix_path.depth)
2045 copy_path_mixer_ctls(&spec->out_mix_path, path);
c577b8a1
JC
2046 }
2047
4a79616d
TI
2048 idx = get_connection_index(codec, spec->aa_mix_nid,
2049 spec->multiout.dac_nids[0]);
2050 if (idx >= 0) {
2051 /* add control to mixer */
3214b966
TI
2052 const char *name;
2053 name = spec->out_mix_path.depth ?
2054 "PCM Loopback Playback Volume" : "PCM Playback Volume";
2055 err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
4a79616d
TI
2056 HDA_COMPOSE_AMP_VAL(spec->aa_mix_nid, 3,
2057 idx, HDA_INPUT));
2058 if (err < 0)
2059 return err;
3214b966
TI
2060 name = spec->out_mix_path.depth ?
2061 "PCM Loopback Playback Switch" : "PCM Playback Switch";
2062 err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
4a79616d
TI
2063 HDA_COMPOSE_AMP_VAL(spec->aa_mix_nid, 3,
2064 idx, HDA_INPUT));
2065 if (err < 0)
2066 return err;
2067 }
2068
f4a7828b
TI
2069 cfg->line_outs = old_line_outs;
2070
c577b8a1
JC
2071 return 0;
2072}
2073
4a79616d 2074static int via_auto_create_hp_ctls(struct hda_codec *codec, hda_nid_t pin)
c577b8a1 2075{
4a79616d 2076 struct via_spec *spec = codec->spec;
09a9ad69 2077 struct nid_path *path;
18bd2c44 2078 bool check_dac;
3214b966 2079 int i, err;
c577b8a1
JC
2080
2081 if (!pin)
2082 return 0;
2083
3214b966
TI
2084 if (!parse_output_path(codec, pin, 0, 0, &spec->hp_indep_path)) {
2085 for (i = HDA_SIDE; i >= HDA_CLFE; i--) {
2086 if (i < spec->multiout.num_dacs &&
2087 parse_output_path(codec, pin,
2088 spec->multiout.dac_nids[i], 0,
2089 &spec->hp_indep_path)) {
2090 spec->hp_indep_shared = i;
2091 break;
2092 }
2093 }
25250505 2094 }
3214b966
TI
2095 if (spec->hp_indep_path.depth) {
2096 spec->hp_dac_nid = spec->hp_indep_path.path[0];
2097 if (!spec->hp_indep_shared)
2098 spec->hp_path = spec->hp_indep_path;
2099 }
2100 /* optionally check front-path w/o AA-mix */
2101 if (!spec->hp_path.depth)
2102 parse_output_path(codec, pin,
2103 spec->multiout.dac_nids[HDA_FRONT], 0,
2104 &spec->hp_path);
c577b8a1 2105
ece8d043 2106 if (!parse_output_path(codec, pin, spec->multiout.dac_nids[HDA_FRONT],
3214b966 2107 1, &spec->hp_mix_path) && !spec->hp_path.depth)
ece8d043
TI
2108 return 0;
2109
3214b966 2110 if (spec->hp_path.depth) {
09a9ad69 2111 path = &spec->hp_path;
18bd2c44
TI
2112 check_dac = true;
2113 } else {
3214b966 2114 path = &spec->hp_mix_path;
18bd2c44
TI
2115 check_dac = false;
2116 }
2117 err = create_ch_ctls(codec, "Headphone", 3, check_dac, path);
c577b8a1
JC
2118 if (err < 0)
2119 return err;
020066d1
TI
2120 if (check_dac)
2121 copy_path_mixer_ctls(&spec->hp_mix_path, path);
2122 else
2123 copy_path_mixer_ctls(&spec->hp_path, path);
2124 if (spec->hp_indep_path.depth)
2125 copy_path_mixer_ctls(&spec->hp_indep_path, path);
c577b8a1
JC
2126 return 0;
2127}
2128
4a918ffe
TI
2129static int via_auto_create_speaker_ctls(struct hda_codec *codec)
2130{
2131 struct via_spec *spec = codec->spec;
3214b966
TI
2132 struct nid_path *path;
2133 bool check_dac;
81c0a78b 2134 hda_nid_t pin, dac = 0;
3214b966 2135 int err;
4a918ffe
TI
2136
2137 pin = spec->autocfg.speaker_pins[0];
2138 if (!spec->autocfg.speaker_outs || !pin)
2139 return 0;
2140
3214b966 2141 if (parse_output_path(codec, pin, 0, 0, &spec->speaker_path))
8e3679dc 2142 dac = spec->speaker_path.path[0];
3214b966
TI
2143 if (!dac)
2144 parse_output_path(codec, pin,
2145 spec->multiout.dac_nids[HDA_FRONT], 0,
2146 &spec->speaker_path);
2147 if (!parse_output_path(codec, pin, spec->multiout.dac_nids[HDA_FRONT],
2148 1, &spec->speaker_mix_path) && !dac)
2149 return 0;
2150
2151 /* no AA-path for front? */
2152 if (!spec->out_mix_path.depth && spec->speaker_mix_path.depth)
2153 dac = 0;
2154
2155 spec->speaker_dac_nid = dac;
2156 spec->multiout.extra_out_nid[0] = dac;
2157 if (dac) {
2158 path = &spec->speaker_path;
2159 check_dac = true;
2160 } else {
2161 path = &spec->speaker_mix_path;
2162 check_dac = false;
2163 }
2164 err = create_ch_ctls(codec, "Speaker", 3, check_dac, path);
2165 if (err < 0)
2166 return err;
020066d1
TI
2167 if (check_dac)
2168 copy_path_mixer_ctls(&spec->speaker_mix_path, path);
2169 else
2170 copy_path_mixer_ctls(&spec->speaker_path, path);
3214b966
TI
2171 return 0;
2172}
2173
2174#define via_aamix_ctl_info via_pin_power_ctl_info
4a918ffe 2175
3214b966
TI
2176static int via_aamix_ctl_get(struct snd_kcontrol *kcontrol,
2177 struct snd_ctl_elem_value *ucontrol)
2178{
2179 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2180 struct via_spec *spec = codec->spec;
2181 ucontrol->value.enumerated.item[0] = spec->aamix_mode;
2182 return 0;
2183}
2184
2185static void update_aamix_paths(struct hda_codec *codec, int do_mix,
2186 struct nid_path *nomix, struct nid_path *mix)
2187{
2188 if (do_mix) {
2189 activate_output_path(codec, nomix, false, false);
2190 activate_output_path(codec, mix, true, false);
2191 } else {
2192 activate_output_path(codec, mix, false, false);
2193 activate_output_path(codec, nomix, true, false);
2194 }
2195}
2196
2197static int via_aamix_ctl_put(struct snd_kcontrol *kcontrol,
2198 struct snd_ctl_elem_value *ucontrol)
2199{
2200 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2201 struct via_spec *spec = codec->spec;
2202 unsigned int val = ucontrol->value.enumerated.item[0];
2203
2204 if (val == spec->aamix_mode)
2205 return 0;
2206 spec->aamix_mode = val;
2207 /* update front path */
2208 update_aamix_paths(codec, val, &spec->out_path[0], &spec->out_mix_path);
2209 /* update HP path */
2210 if (!spec->hp_independent_mode) {
2211 update_aamix_paths(codec, val, &spec->hp_path,
2212 &spec->hp_mix_path);
2213 }
2214 /* update speaker path */
2215 update_aamix_paths(codec, val, &spec->speaker_path,
2216 &spec->speaker_mix_path);
2217 return 1;
2218}
2219
2220static const struct snd_kcontrol_new via_aamix_ctl_enum = {
2221 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2222 .name = "Loopback Mixing",
2223 .info = via_aamix_ctl_info,
2224 .get = via_aamix_ctl_get,
2225 .put = via_aamix_ctl_put,
2226};
2227
2228static int via_auto_create_loopback_switch(struct hda_codec *codec)
2229{
2230 struct via_spec *spec = codec->spec;
2231
4808d12d
TI
2232 if (!spec->aa_mix_nid)
2233 return 0; /* no loopback switching available */
2234 if (!(spec->out_mix_path.depth || spec->hp_mix_path.depth ||
2235 spec->speaker_path.depth))
3214b966
TI
2236 return 0; /* no loopback switching available */
2237 if (!via_clone_control(spec, &via_aamix_ctl_enum))
2238 return -ENOMEM;
4a918ffe
TI
2239 return 0;
2240}
2241
a766d0d7
TI
2242/* look for ADCs */
2243static int via_fill_adcs(struct hda_codec *codec)
2244{
2245 struct via_spec *spec = codec->spec;
2246 hda_nid_t nid = codec->start_nid;
2247 int i;
2248
2249 for (i = 0; i < codec->num_nodes; i++, nid++) {
2250 unsigned int wcaps = get_wcaps(codec, nid);
2251 if (get_wcaps_type(wcaps) != AC_WID_AUD_IN)
2252 continue;
2253 if (wcaps & AC_WCAP_DIGITAL)
2254 continue;
2255 if (!(wcaps & AC_WCAP_CONN_LIST))
2256 continue;
2257 if (spec->num_adc_nids >= ARRAY_SIZE(spec->adc_nids))
2258 return -ENOMEM;
2259 spec->adc_nids[spec->num_adc_nids++] = nid;
2260 }
2261 return 0;
2262}
2263
a86a88ea
TI
2264/* input-src control */
2265static int via_mux_enum_info(struct snd_kcontrol *kcontrol,
2266 struct snd_ctl_elem_info *uinfo)
2267{
2268 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2269 struct via_spec *spec = codec->spec;
2270
2271 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
2272 uinfo->count = 1;
2273 uinfo->value.enumerated.items = spec->num_inputs;
2274 if (uinfo->value.enumerated.item >= spec->num_inputs)
2275 uinfo->value.enumerated.item = spec->num_inputs - 1;
2276 strcpy(uinfo->value.enumerated.name,
2277 spec->inputs[uinfo->value.enumerated.item].label);
2278 return 0;
2279}
2280
2281static int via_mux_enum_get(struct snd_kcontrol *kcontrol,
2282 struct snd_ctl_elem_value *ucontrol)
2283{
2284 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2285 struct via_spec *spec = codec->spec;
2286 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
2287
2288 ucontrol->value.enumerated.item[0] = spec->cur_mux[idx];
2289 return 0;
2290}
2291
2292static int via_mux_enum_put(struct snd_kcontrol *kcontrol,
2293 struct snd_ctl_elem_value *ucontrol)
2294{
2295 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2296 struct via_spec *spec = codec->spec;
2297 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
2298 hda_nid_t mux;
2299 int cur;
2300
2301 cur = ucontrol->value.enumerated.item[0];
2302 if (cur < 0 || cur >= spec->num_inputs)
2303 return -EINVAL;
2304 if (spec->cur_mux[idx] == cur)
2305 return 0;
2306 spec->cur_mux[idx] = cur;
2307 if (spec->dyn_adc_switch) {
2308 int adc_idx = spec->inputs[cur].adc_idx;
2309 mux = spec->mux_nids[adc_idx];
2310 via_dyn_adc_pcm_resetup(codec, cur);
2311 } else {
2312 mux = spec->mux_nids[idx];
2313 if (snd_BUG_ON(!mux))
2314 return -EINVAL;
2315 }
2316
2317 if (mux) {
2318 /* switch to D0 beofre change index */
054d867e 2319 update_power_state(codec, mux, AC_PWRST_D0);
a86a88ea
TI
2320 snd_hda_codec_write(codec, mux, 0,
2321 AC_VERB_SET_CONNECT_SEL,
2322 spec->inputs[cur].mux_idx);
2323 }
2324
2325 /* update jack power state */
2326 set_widgets_power_state(codec);
2327 return 0;
2328}
a766d0d7 2329
d7a99cce
TI
2330static const struct snd_kcontrol_new via_input_src_ctl = {
2331 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2332 /* The multiple "Capture Source" controls confuse alsamixer
2333 * So call somewhat different..
2334 */
2335 /* .name = "Capture Source", */
2336 .name = "Input Source",
2337 .info = via_mux_enum_info,
2338 .get = via_mux_enum_get,
2339 .put = via_mux_enum_put,
2340};
2341
a86a88ea
TI
2342static int create_input_src_ctls(struct hda_codec *codec, int count)
2343{
2344 struct via_spec *spec = codec->spec;
2345 struct snd_kcontrol_new *knew;
2346
2347 if (spec->num_inputs <= 1 || !count)
2348 return 0; /* no need for single src */
2349
2350 knew = via_clone_control(spec, &via_input_src_ctl);
2351 if (!knew)
2352 return -ENOMEM;
2353 knew->count = count;
2354 return 0;
2355}
2356
2357/* add the powersave loopback-list entry */
13af8e77
TI
2358static void add_loopback_list(struct via_spec *spec, hda_nid_t mix, int idx)
2359{
2360 struct hda_amp_list *list;
2361
2362 if (spec->num_loopbacks >= ARRAY_SIZE(spec->loopback_list) - 1)
2363 return;
2364 list = spec->loopback_list + spec->num_loopbacks;
2365 list->nid = mix;
2366 list->dir = HDA_INPUT;
2367 list->idx = idx;
2368 spec->num_loopbacks++;
2369 spec->loopback.amplist = spec->loopback_list;
2370}
13af8e77 2371
a86a88ea 2372static bool is_reachable_nid(struct hda_codec *codec, hda_nid_t src,
8d087c76 2373 hda_nid_t dst)
a86a88ea 2374{
8d087c76 2375 return snd_hda_get_conn_index(codec, src, dst, 1) >= 0;
a86a88ea
TI
2376}
2377
2378/* add the input-route to the given pin */
2379static bool add_input_route(struct hda_codec *codec, hda_nid_t pin)
c577b8a1 2380{
10a20af7 2381 struct via_spec *spec = codec->spec;
a86a88ea
TI
2382 int c, idx;
2383
2384 spec->inputs[spec->num_inputs].adc_idx = -1;
2385 spec->inputs[spec->num_inputs].pin = pin;
2386 for (c = 0; c < spec->num_adc_nids; c++) {
2387 if (spec->mux_nids[c]) {
2388 idx = get_connection_index(codec, spec->mux_nids[c],
2389 pin);
2390 if (idx < 0)
2391 continue;
2392 spec->inputs[spec->num_inputs].mux_idx = idx;
2393 } else {
8d087c76 2394 if (!is_reachable_nid(codec, spec->adc_nids[c], pin))
a86a88ea
TI
2395 continue;
2396 }
2397 spec->inputs[spec->num_inputs].adc_idx = c;
2398 /* Can primary ADC satisfy all inputs? */
2399 if (!spec->dyn_adc_switch &&
2400 spec->num_inputs > 0 && spec->inputs[0].adc_idx != c) {
2401 snd_printd(KERN_INFO
2402 "via: dynamic ADC switching enabled\n");
2403 spec->dyn_adc_switch = 1;
2404 }
2405 return true;
2406 }
2407 return false;
2408}
2409
2410static int get_mux_nids(struct hda_codec *codec);
2411
2412/* parse input-routes; fill ADCs, MUXs and input-src entries */
2413static int parse_analog_inputs(struct hda_codec *codec)
2414{
2415 struct via_spec *spec = codec->spec;
2416 const struct auto_pin_cfg *cfg = &spec->autocfg;
2417 int i, err;
a766d0d7
TI
2418
2419 err = via_fill_adcs(codec);
2420 if (err < 0)
2421 return err;
2422 err = get_mux_nids(codec);
2423 if (err < 0)
2424 return err;
c577b8a1 2425
a86a88ea
TI
2426 /* fill all input-routes */
2427 for (i = 0; i < cfg->num_inputs; i++) {
2428 if (add_input_route(codec, cfg->inputs[i].pin))
2429 spec->inputs[spec->num_inputs++].label =
2430 hda_get_autocfg_input_label(codec, cfg, i);
f3268512 2431 }
c577b8a1 2432
a86a88ea
TI
2433 /* check for internal loopback recording */
2434 if (spec->aa_mix_nid &&
2435 add_input_route(codec, spec->aa_mix_nid))
2436 spec->inputs[spec->num_inputs++].label = "Stereo Mixer";
2437
2438 return 0;
2439}
2440
2441/* create analog-loopback volume/switch controls */
2442static int create_loopback_ctls(struct hda_codec *codec)
2443{
2444 struct via_spec *spec = codec->spec;
2445 const struct auto_pin_cfg *cfg = &spec->autocfg;
2446 const char *prev_label = NULL;
2447 int type_idx = 0;
2448 int i, j, err, idx;
2449
2450 if (!spec->aa_mix_nid)
2451 return 0;
2452
7b315bb4 2453 for (i = 0; i < cfg->num_inputs; i++) {
a86a88ea
TI
2454 hda_nid_t pin = cfg->inputs[i].pin;
2455 const char *label = hda_get_autocfg_input_label(codec, cfg, i);
2456
1e11cae1 2457 if (prev_label && !strcmp(label, prev_label))
7b315bb4
TI
2458 type_idx++;
2459 else
2460 type_idx = 0;
1e11cae1 2461 prev_label = label;
a86a88ea
TI
2462 idx = get_connection_index(codec, spec->aa_mix_nid, pin);
2463 if (idx >= 0) {
16922281 2464 err = via_new_analog_input(spec, label, type_idx,
a86a88ea 2465 idx, spec->aa_mix_nid);
13af8e77
TI
2466 if (err < 0)
2467 return err;
a86a88ea 2468 add_loopback_list(spec, spec->aa_mix_nid, idx);
13af8e77 2469 }
e3d7a143
TI
2470
2471 /* remember the label for smart51 control */
2472 for (j = 0; j < spec->smart51_nums; j++) {
a86a88ea 2473 if (spec->smart51_pins[j] == pin) {
e3d7a143
TI
2474 spec->smart51_idxs[j] = idx;
2475 spec->smart51_labels[j] = label;
2476 break;
2477 }
2478 }
c577b8a1 2479 }
a86a88ea
TI
2480 return 0;
2481}
2482
2483/* create mic-boost controls (if present) */
2484static int create_mic_boost_ctls(struct hda_codec *codec)
2485{
2486 struct via_spec *spec = codec->spec;
2487 const struct auto_pin_cfg *cfg = &spec->autocfg;
2488 int i, err;
2489
2490 for (i = 0; i < cfg->num_inputs; i++) {
2491 hda_nid_t pin = cfg->inputs[i].pin;
2492 unsigned int caps;
2493 const char *label;
2494 char name[32];
2495
2496 if (cfg->inputs[i].type != AUTO_PIN_MIC)
2497 continue;
2498 caps = query_amp_caps(codec, pin, HDA_INPUT);
2499 if (caps == -1 || !(caps & AC_AMPCAP_NUM_STEPS))
2500 continue;
2501 label = hda_get_autocfg_input_label(codec, cfg, i);
2502 snprintf(name, sizeof(name), "%s Boost Volume", label);
2503 err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
2504 HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_INPUT));
2505 if (err < 0)
2506 return err;
2507 }
2508 return 0;
2509}
2510
2511/* create capture and input-src controls for multiple streams */
2512static int create_multi_adc_ctls(struct hda_codec *codec)
2513{
2514 struct via_spec *spec = codec->spec;
2515 int i, err;
d7a99cce
TI
2516
2517 /* create capture mixer elements */
2518 for (i = 0; i < spec->num_adc_nids; i++) {
2519 hda_nid_t adc = spec->adc_nids[i];
2520 err = __via_add_control(spec, VIA_CTL_WIDGET_VOL,
2521 "Capture Volume", i,
2522 HDA_COMPOSE_AMP_VAL(adc, 3, 0,
2523 HDA_INPUT));
2524 if (err < 0)
2525 return err;
2526 err = __via_add_control(spec, VIA_CTL_WIDGET_MUTE,
2527 "Capture Switch", i,
2528 HDA_COMPOSE_AMP_VAL(adc, 3, 0,
2529 HDA_INPUT));
2530 if (err < 0)
2531 return err;
2532 }
2533
2534 /* input-source control */
2535 for (i = 0; i < spec->num_adc_nids; i++)
2536 if (!spec->mux_nids[i])
2537 break;
a86a88ea
TI
2538 err = create_input_src_ctls(codec, i);
2539 if (err < 0)
2540 return err;
2541 return 0;
2542}
d7a99cce 2543
a86a88ea
TI
2544/* bind capture volume/switch */
2545static struct snd_kcontrol_new via_bind_cap_vol_ctl =
2546 HDA_BIND_VOL("Capture Volume", 0);
2547static struct snd_kcontrol_new via_bind_cap_sw_ctl =
2548 HDA_BIND_SW("Capture Switch", 0);
d7a99cce 2549
a86a88ea
TI
2550static int init_bind_ctl(struct via_spec *spec, struct hda_bind_ctls **ctl_ret,
2551 struct hda_ctl_ops *ops)
2552{
2553 struct hda_bind_ctls *ctl;
2554 int i;
d7a99cce 2555
a86a88ea
TI
2556 ctl = kzalloc(sizeof(*ctl) + sizeof(long) * 4, GFP_KERNEL);
2557 if (!ctl)
2558 return -ENOMEM;
2559 ctl->ops = ops;
2560 for (i = 0; i < spec->num_adc_nids; i++)
2561 ctl->values[i] =
2562 HDA_COMPOSE_AMP_VAL(spec->adc_nids[i], 3, 0, HDA_INPUT);
2563 *ctl_ret = ctl;
2564 return 0;
2565}
2566
2567/* create capture and input-src controls for dynamic ADC-switch case */
2568static int create_dyn_adc_ctls(struct hda_codec *codec)
2569{
2570 struct via_spec *spec = codec->spec;
2571 struct snd_kcontrol_new *knew;
2572 int err;
2573
2574 /* set up the bind capture ctls */
2575 err = init_bind_ctl(spec, &spec->bind_cap_vol, &snd_hda_bind_vol);
2576 if (err < 0)
2577 return err;
2578 err = init_bind_ctl(spec, &spec->bind_cap_sw, &snd_hda_bind_sw);
2579 if (err < 0)
2580 return err;
2581
2582 /* create capture mixer elements */
2583 knew = via_clone_control(spec, &via_bind_cap_vol_ctl);
2584 if (!knew)
2585 return -ENOMEM;
2586 knew->private_value = (long)spec->bind_cap_vol;
2587
2588 knew = via_clone_control(spec, &via_bind_cap_sw_ctl);
2589 if (!knew)
2590 return -ENOMEM;
2591 knew->private_value = (long)spec->bind_cap_sw;
2592
2593 /* input-source control */
2594 err = create_input_src_ctls(codec, 1);
2595 if (err < 0)
2596 return err;
2597 return 0;
2598}
2599
2600/* parse and create capture-related stuff */
2601static int via_auto_create_analog_input_ctls(struct hda_codec *codec)
2602{
2603 struct via_spec *spec = codec->spec;
2604 int err;
2605
2606 err = parse_analog_inputs(codec);
2607 if (err < 0)
2608 return err;
2609 if (spec->dyn_adc_switch)
2610 err = create_dyn_adc_ctls(codec);
2611 else
2612 err = create_multi_adc_ctls(codec);
2613 if (err < 0)
2614 return err;
2615 err = create_loopback_ctls(codec);
2616 if (err < 0)
2617 return err;
2618 err = create_mic_boost_ctls(codec);
2619 if (err < 0)
2620 return err;
c577b8a1
JC
2621 return 0;
2622}
2623
76d9b0dd
HW
2624static void vt1708_set_pinconfig_connect(struct hda_codec *codec, hda_nid_t nid)
2625{
2626 unsigned int def_conf;
2627 unsigned char seqassoc;
2628
2f334f92 2629 def_conf = snd_hda_codec_get_pincfg(codec, nid);
76d9b0dd
HW
2630 seqassoc = (unsigned char) get_defcfg_association(def_conf);
2631 seqassoc = (seqassoc << 4) | get_defcfg_sequence(def_conf);
82ef9e45
LW
2632 if (get_defcfg_connect(def_conf) == AC_JACK_PORT_NONE
2633 && (seqassoc == 0xf0 || seqassoc == 0xff)) {
2634 def_conf = def_conf & (~(AC_JACK_PORT_BOTH << 30));
2635 snd_hda_codec_set_pincfg(codec, nid, def_conf);
76d9b0dd
HW
2636 }
2637
2638 return;
2639}
2640
e06e5a29 2641static int vt1708_jack_detect_get(struct snd_kcontrol *kcontrol,
1f2e99fe
LW
2642 struct snd_ctl_elem_value *ucontrol)
2643{
2644 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2645 struct via_spec *spec = codec->spec;
2646
2647 if (spec->codec_type != VT1708)
2648 return 0;
e06e5a29 2649 ucontrol->value.integer.value[0] = spec->vt1708_jack_detect;
1f2e99fe
LW
2650 return 0;
2651}
2652
e06e5a29 2653static int vt1708_jack_detect_put(struct snd_kcontrol *kcontrol,
1f2e99fe
LW
2654 struct snd_ctl_elem_value *ucontrol)
2655{
2656 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2657 struct via_spec *spec = codec->spec;
187d333e 2658 int val;
1f2e99fe
LW
2659
2660 if (spec->codec_type != VT1708)
2661 return 0;
187d333e
TI
2662 val = !!ucontrol->value.integer.value[0];
2663 if (spec->vt1708_jack_detect == val)
2664 return 0;
2665 spec->vt1708_jack_detect = val;
2666 if (spec->vt1708_jack_detect &&
2667 snd_hda_get_bool_hint(codec, "analog_loopback_hp_detect") != 1) {
1f2e99fe
LW
2668 mute_aa_path(codec, 1);
2669 notify_aa_path_ctls(codec);
2670 }
187d333e
TI
2671 via_hp_automute(codec);
2672 vt1708_update_hp_work(spec);
2673 return 1;
1f2e99fe
LW
2674}
2675
e06e5a29
TI
2676static const struct snd_kcontrol_new vt1708_jack_detect_ctl = {
2677 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2678 .name = "Jack Detect",
2679 .count = 1,
2680 .info = snd_ctl_boolean_mono_info,
2681 .get = vt1708_jack_detect_get,
2682 .put = vt1708_jack_detect_put,
1f2e99fe
LW
2683};
2684
12daef65
TI
2685static void fill_dig_outs(struct hda_codec *codec);
2686static void fill_dig_in(struct hda_codec *codec);
2687
2688static int via_parse_auto_config(struct hda_codec *codec)
c577b8a1
JC
2689{
2690 struct via_spec *spec = codec->spec;
2691 int err;
2692
2693 err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
c577b8a1
JC
2694 if (err < 0)
2695 return err;
2696 if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
7f0df88c 2697 return -EINVAL;
c577b8a1 2698
4a79616d 2699 err = via_auto_create_multi_out_ctls(codec);
c577b8a1
JC
2700 if (err < 0)
2701 return err;
4a79616d 2702 err = via_auto_create_hp_ctls(codec, spec->autocfg.hp_pins[0]);
4a918ffe
TI
2703 if (err < 0)
2704 return err;
2705 err = via_auto_create_speaker_ctls(codec);
3214b966
TI
2706 if (err < 0)
2707 return err;
2708 err = via_auto_create_loopback_switch(codec);
c577b8a1
JC
2709 if (err < 0)
2710 return err;
a86a88ea 2711 err = via_auto_create_analog_input_ctls(codec);
1f2e99fe
LW
2712 if (err < 0)
2713 return err;
c577b8a1
JC
2714
2715 spec->multiout.max_channels = spec->multiout.num_dacs * 2;
2716
12daef65
TI
2717 fill_dig_outs(codec);
2718 fill_dig_in(codec);
c577b8a1 2719
603c4019
TI
2720 if (spec->kctls.list)
2721 spec->mixers[spec->num_mixers++] = spec->kctls.list;
c577b8a1 2722
c577b8a1 2723
3214b966 2724 if (spec->hp_dac_nid && spec->hp_mix_path.depth) {
ece8d043
TI
2725 err = via_hp_build(codec);
2726 if (err < 0)
2727 return err;
2728 }
c577b8a1 2729
f4a7828b
TI
2730 err = via_smart51_build(codec);
2731 if (err < 0)
2732 return err;
2733
5d41762a
TI
2734 /* assign slave outs */
2735 if (spec->slave_dig_outs[0])
2736 codec->slave_dig_outs = spec->slave_dig_outs;
2737
c577b8a1
JC
2738 return 1;
2739}
2740
5d41762a
TI
2741static void via_auto_init_dig_outs(struct hda_codec *codec)
2742{
2743 struct via_spec *spec = codec->spec;
2744 if (spec->multiout.dig_out_nid)
2745 init_output_pin(codec, spec->autocfg.dig_out_pins[0], PIN_OUT);
2746 if (spec->slave_dig_outs[0])
2747 init_output_pin(codec, spec->autocfg.dig_out_pins[1], PIN_OUT);
2748}
2749
2750static void via_auto_init_dig_in(struct hda_codec *codec)
c577b8a1 2751{
25eaba2f 2752 struct via_spec *spec = codec->spec;
5d41762a
TI
2753 if (!spec->dig_in_nid)
2754 return;
2755 snd_hda_codec_write(codec, spec->autocfg.dig_in_pin, 0,
2756 AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN);
2757}
2758
4a918ffe
TI
2759/* initialize the unsolicited events */
2760static void via_auto_init_unsol_event(struct hda_codec *codec)
2761{
2762 struct via_spec *spec = codec->spec;
2763 struct auto_pin_cfg *cfg = &spec->autocfg;
2764 unsigned int ev;
2765 int i;
2766
2767 if (cfg->hp_pins[0] && is_jack_detectable(codec, cfg->hp_pins[0]))
1835a0f9
TI
2768 snd_hda_jack_detect_enable(codec, cfg->hp_pins[0],
2769 VIA_HP_EVENT | VIA_JACK_EVENT);
4a918ffe
TI
2770
2771 if (cfg->speaker_pins[0])
2772 ev = VIA_LINE_EVENT;
2773 else
2774 ev = 0;
2775 for (i = 0; i < cfg->line_outs; i++) {
2776 if (cfg->line_out_pins[i] &&
2777 is_jack_detectable(codec, cfg->line_out_pins[i]))
1835a0f9
TI
2778 snd_hda_jack_detect_enable(codec, cfg->line_out_pins[i],
2779 ev | VIA_JACK_EVENT);
4a918ffe
TI
2780 }
2781
2782 for (i = 0; i < cfg->num_inputs; i++) {
2783 if (is_jack_detectable(codec, cfg->inputs[i].pin))
1835a0f9
TI
2784 snd_hda_jack_detect_enable(codec, cfg->inputs[i].pin,
2785 VIA_JACK_EVENT);
4a918ffe
TI
2786 }
2787}
2788
5d41762a
TI
2789static int via_init(struct hda_codec *codec)
2790{
2791 struct via_spec *spec = codec->spec;
2792 int i;
2793
2794 for (i = 0; i < spec->num_iverbs; i++)
2795 snd_hda_sequence_write(codec, spec->init_verbs[i]);
25eaba2f 2796
e9d010c2
TI
2797 /* init power states */
2798 set_widgets_power_state(codec);
2799 __analog_low_current_mode(codec, true);
2800
c577b8a1
JC
2801 via_auto_init_multi_out(codec);
2802 via_auto_init_hp_out(codec);
4a918ffe 2803 via_auto_init_speaker_out(codec);
c577b8a1 2804 via_auto_init_analog_input(codec);
5d41762a
TI
2805 via_auto_init_dig_outs(codec);
2806 via_auto_init_dig_in(codec);
11890956 2807
4a918ffe
TI
2808 via_auto_init_unsol_event(codec);
2809
2810 via_hp_automute(codec);
187d333e 2811 vt1708_update_hp_work(spec);
01a61e12 2812 snd_hda_jack_report_sync(codec);
25eaba2f 2813
c577b8a1
JC
2814 return 0;
2815}
2816
1f2e99fe
LW
2817static void vt1708_update_hp_jack_state(struct work_struct *work)
2818{
2819 struct via_spec *spec = container_of(work, struct via_spec,
2820 vt1708_hp_work.work);
2821 if (spec->codec_type != VT1708)
2822 return;
1835a0f9 2823 snd_hda_jack_set_dirty_all(spec->codec);
1f2e99fe
LW
2824 /* if jack state toggled */
2825 if (spec->vt1708_hp_present
d56757ab 2826 != snd_hda_jack_detect(spec->codec, spec->autocfg.hp_pins[0])) {
1f2e99fe
LW
2827 spec->vt1708_hp_present ^= 1;
2828 via_hp_automute(spec->codec);
2829 }
187d333e
TI
2830 if (spec->vt1708_jack_detect)
2831 schedule_delayed_work(&spec->vt1708_hp_work,
2832 msecs_to_jiffies(100));
1f2e99fe
LW
2833}
2834
337b9d02
TI
2835static int get_mux_nids(struct hda_codec *codec)
2836{
2837 struct via_spec *spec = codec->spec;
2838 hda_nid_t nid, conn[8];
2839 unsigned int type;
2840 int i, n;
2841
2842 for (i = 0; i < spec->num_adc_nids; i++) {
2843 nid = spec->adc_nids[i];
2844 while (nid) {
a22d543a 2845 type = get_wcaps_type(get_wcaps(codec, nid));
1c55d521
TI
2846 if (type == AC_WID_PIN)
2847 break;
337b9d02
TI
2848 n = snd_hda_get_connections(codec, nid, conn,
2849 ARRAY_SIZE(conn));
2850 if (n <= 0)
2851 break;
2852 if (n > 1) {
2853 spec->mux_nids[i] = nid;
2854 break;
2855 }
2856 nid = conn[0];
2857 }
2858 }
1c55d521 2859 return 0;
337b9d02
TI
2860}
2861
c577b8a1
JC
2862static int patch_vt1708(struct hda_codec *codec)
2863{
2864 struct via_spec *spec;
2865 int err;
2866
2867 /* create a codec specific record */
5b0cb1d8 2868 spec = via_new_spec(codec);
c577b8a1
JC
2869 if (spec == NULL)
2870 return -ENOMEM;
2871
620e2b28
TI
2872 spec->aa_mix_nid = 0x17;
2873
12daef65
TI
2874 /* Add HP and CD pin config connect bit re-config action */
2875 vt1708_set_pinconfig_connect(codec, VT1708_HP_PIN_NID);
2876 vt1708_set_pinconfig_connect(codec, VT1708_CD_PIN_NID);
2877
c577b8a1 2878 /* automatic parse from the BIOS config */
12daef65 2879 err = via_parse_auto_config(codec);
c577b8a1
JC
2880 if (err < 0) {
2881 via_free(codec);
2882 return err;
c577b8a1
JC
2883 }
2884
12daef65
TI
2885 /* add jack detect on/off control */
2886 if (!via_clone_control(spec, &vt1708_jack_detect_ctl))
2887 return -ENOMEM;
2888
bc9b5623
TI
2889 /* disable 32bit format on VT1708 */
2890 if (codec->vendor_id == 0x11061708)
2891 spec->stream_analog_playback = &vt1708_pcm_analog_s16_playback;
c577b8a1 2892
e322a36d
LW
2893 spec->init_verbs[spec->num_iverbs++] = vt1708_init_verbs;
2894
c577b8a1
JC
2895 codec->patch_ops = via_patch_ops;
2896
1f2e99fe 2897 INIT_DELAYED_WORK(&spec->vt1708_hp_work, vt1708_update_hp_jack_state);
c577b8a1
JC
2898 return 0;
2899}
2900
ddd304d8 2901static int patch_vt1709(struct hda_codec *codec)
c577b8a1
JC
2902{
2903 struct via_spec *spec;
2904 int err;
2905
2906 /* create a codec specific record */
5b0cb1d8 2907 spec = via_new_spec(codec);
c577b8a1
JC
2908 if (spec == NULL)
2909 return -ENOMEM;
2910
620e2b28
TI
2911 spec->aa_mix_nid = 0x18;
2912
12daef65 2913 err = via_parse_auto_config(codec);
c577b8a1
JC
2914 if (err < 0) {
2915 via_free(codec);
2916 return err;
c577b8a1
JC
2917 }
2918
c577b8a1
JC
2919 codec->patch_ops = via_patch_ops;
2920
f7278fd0
JC
2921 return 0;
2922}
2923
3e95b9ab
LW
2924static void set_widgets_power_state_vt1708B(struct hda_codec *codec)
2925{
2926 struct via_spec *spec = codec->spec;
2927 int imux_is_smixer;
2928 unsigned int parm;
2929 int is_8ch = 0;
bc92df7f
LW
2930 if ((spec->codec_type != VT1708B_4CH) &&
2931 (codec->vendor_id != 0x11064397))
3e95b9ab
LW
2932 is_8ch = 1;
2933
2934 /* SW0 (17h) = stereo mixer */
2935 imux_is_smixer =
2936 (snd_hda_codec_read(codec, 0x17, 0, AC_VERB_GET_CONNECT_SEL, 0x00)
2937 == ((spec->codec_type == VT1708S) ? 5 : 0));
2938 /* inputs */
2939 /* PW 1/2/5 (1ah/1bh/1eh) */
2940 parm = AC_PWRST_D3;
2941 set_pin_power_state(codec, 0x1a, &parm);
2942 set_pin_power_state(codec, 0x1b, &parm);
2943 set_pin_power_state(codec, 0x1e, &parm);
2944 if (imux_is_smixer)
2945 parm = AC_PWRST_D0;
2946 /* SW0 (17h), AIW 0/1 (13h/14h) */
054d867e
TI
2947 update_power_state(codec, 0x17, parm);
2948 update_power_state(codec, 0x13, parm);
2949 update_power_state(codec, 0x14, parm);
3e95b9ab
LW
2950
2951 /* outputs */
2952 /* PW0 (19h), SW1 (18h), AOW1 (11h) */
2953 parm = AC_PWRST_D3;
2954 set_pin_power_state(codec, 0x19, &parm);
2955 if (spec->smart51_enabled)
2956 set_pin_power_state(codec, 0x1b, &parm);
054d867e
TI
2957 update_power_state(codec, 0x18, parm);
2958 update_power_state(codec, 0x11, parm);
3e95b9ab
LW
2959
2960 /* PW6 (22h), SW2 (26h), AOW2 (24h) */
2961 if (is_8ch) {
2962 parm = AC_PWRST_D3;
2963 set_pin_power_state(codec, 0x22, &parm);
2964 if (spec->smart51_enabled)
2965 set_pin_power_state(codec, 0x1a, &parm);
054d867e
TI
2966 update_power_state(codec, 0x26, parm);
2967 update_power_state(codec, 0x24, parm);
bc92df7f
LW
2968 } else if (codec->vendor_id == 0x11064397) {
2969 /* PW7(23h), SW2(27h), AOW2(25h) */
2970 parm = AC_PWRST_D3;
2971 set_pin_power_state(codec, 0x23, &parm);
2972 if (spec->smart51_enabled)
2973 set_pin_power_state(codec, 0x1a, &parm);
054d867e
TI
2974 update_power_state(codec, 0x27, parm);
2975 update_power_state(codec, 0x25, parm);
3e95b9ab
LW
2976 }
2977
2978 /* PW 3/4/7 (1ch/1dh/23h) */
2979 parm = AC_PWRST_D3;
2980 /* force to D0 for internal Speaker */
2981 set_pin_power_state(codec, 0x1c, &parm);
2982 set_pin_power_state(codec, 0x1d, &parm);
2983 if (is_8ch)
2984 set_pin_power_state(codec, 0x23, &parm);
2985
2986 /* MW0 (16h), Sw3 (27h), AOW 0/3 (10h/25h) */
054d867e
TI
2987 update_power_state(codec, 0x16, imux_is_smixer ? AC_PWRST_D0 : parm);
2988 update_power_state(codec, 0x10, parm);
3e95b9ab 2989 if (is_8ch) {
054d867e
TI
2990 update_power_state(codec, 0x25, parm);
2991 update_power_state(codec, 0x27, parm);
bc92df7f 2992 } else if (codec->vendor_id == 0x11064397 && spec->hp_independent_mode)
054d867e 2993 update_power_state(codec, 0x25, parm);
3e95b9ab
LW
2994}
2995
518bf3ba 2996static int patch_vt1708S(struct hda_codec *codec);
ddd304d8 2997static int patch_vt1708B(struct hda_codec *codec)
f7278fd0
JC
2998{
2999 struct via_spec *spec;
3000 int err;
3001
518bf3ba
LW
3002 if (get_codec_type(codec) == VT1708BCE)
3003 return patch_vt1708S(codec);
ddd304d8 3004
f7278fd0 3005 /* create a codec specific record */
5b0cb1d8 3006 spec = via_new_spec(codec);
f7278fd0
JC
3007 if (spec == NULL)
3008 return -ENOMEM;
3009
620e2b28
TI
3010 spec->aa_mix_nid = 0x16;
3011
f7278fd0 3012 /* automatic parse from the BIOS config */
12daef65 3013 err = via_parse_auto_config(codec);
f7278fd0
JC
3014 if (err < 0) {
3015 via_free(codec);
3016 return err;
f7278fd0
JC
3017 }
3018
f7278fd0
JC
3019 codec->patch_ops = via_patch_ops;
3020
3e95b9ab
LW
3021 spec->set_widgets_power_state = set_widgets_power_state_vt1708B;
3022
f7278fd0
JC
3023 return 0;
3024}
3025
d949cac1 3026/* Patch for VT1708S */
096a8854 3027static const struct hda_verb vt1708S_init_verbs[] = {
d7426329
HW
3028 /* Enable Mic Boost Volume backdoor */
3029 {0x1, 0xf98, 0x1},
bc7e7e5c
LW
3030 /* don't bybass mixer */
3031 {0x1, 0xf88, 0xc0},
d949cac1
HW
3032 { }
3033};
3034
4a79616d
TI
3035/* fill out digital output widgets; one for master and one for slave outputs */
3036static void fill_dig_outs(struct hda_codec *codec)
d949cac1 3037{
4a79616d 3038 struct via_spec *spec = codec->spec;
d949cac1 3039 int i;
d949cac1 3040
4a79616d
TI
3041 for (i = 0; i < spec->autocfg.dig_outs; i++) {
3042 hda_nid_t nid;
3043 int conn;
9da29271
TI
3044
3045 nid = spec->autocfg.dig_out_pins[i];
3046 if (!nid)
3047 continue;
3048 conn = snd_hda_get_connections(codec, nid, &nid, 1);
3049 if (conn < 1)
3050 continue;
3051 if (!spec->multiout.dig_out_nid)
3052 spec->multiout.dig_out_nid = nid;
3053 else {
3054 spec->slave_dig_outs[0] = nid;
3055 break; /* at most two dig outs */
3056 }
3057 }
3058}
3059
12daef65 3060static void fill_dig_in(struct hda_codec *codec)
d949cac1
HW
3061{
3062 struct via_spec *spec = codec->spec;
12daef65
TI
3063 hda_nid_t dig_nid;
3064 int i, err;
d949cac1 3065
12daef65
TI
3066 if (!spec->autocfg.dig_in_pin)
3067 return;
f4a7828b 3068
12daef65
TI
3069 dig_nid = codec->start_nid;
3070 for (i = 0; i < codec->num_nodes; i++, dig_nid++) {
3071 unsigned int wcaps = get_wcaps(codec, dig_nid);
3072 if (get_wcaps_type(wcaps) != AC_WID_AUD_IN)
3073 continue;
3074 if (!(wcaps & AC_WCAP_DIGITAL))
3075 continue;
3076 if (!(wcaps & AC_WCAP_CONN_LIST))
3077 continue;
3078 err = get_connection_index(codec, dig_nid,
3079 spec->autocfg.dig_in_pin);
3080 if (err >= 0) {
3081 spec->dig_in_nid = dig_nid;
3082 break;
3083 }
3084 }
d949cac1
HW
3085}
3086
6369bcfc
LW
3087static void override_mic_boost(struct hda_codec *codec, hda_nid_t pin,
3088 int offset, int num_steps, int step_size)
3089{
3090 snd_hda_override_amp_caps(codec, pin, HDA_INPUT,
3091 (offset << AC_AMPCAP_OFFSET_SHIFT) |
3092 (num_steps << AC_AMPCAP_NUM_STEPS_SHIFT) |
3093 (step_size << AC_AMPCAP_STEP_SIZE_SHIFT) |
3094 (0 << AC_AMPCAP_MUTE_SHIFT));
3095}
3096
d949cac1
HW
3097static int patch_vt1708S(struct hda_codec *codec)
3098{
3099 struct via_spec *spec;
3100 int err;
3101
3102 /* create a codec specific record */
5b0cb1d8 3103 spec = via_new_spec(codec);
d949cac1
HW
3104 if (spec == NULL)
3105 return -ENOMEM;
3106
620e2b28 3107 spec->aa_mix_nid = 0x16;
d7a99cce
TI
3108 override_mic_boost(codec, 0x1a, 0, 3, 40);
3109 override_mic_boost(codec, 0x1e, 0, 3, 40);
620e2b28 3110
d949cac1 3111 /* automatic parse from the BIOS config */
12daef65 3112 err = via_parse_auto_config(codec);
d949cac1
HW
3113 if (err < 0) {
3114 via_free(codec);
3115 return err;
d949cac1
HW
3116 }
3117
096a8854 3118 spec->init_verbs[spec->num_iverbs++] = vt1708S_init_verbs;
d949cac1 3119
d949cac1
HW
3120 codec->patch_ops = via_patch_ops;
3121
518bf3ba
LW
3122 /* correct names for VT1708BCE */
3123 if (get_codec_type(codec) == VT1708BCE) {
3124 kfree(codec->chip_name);
3125 codec->chip_name = kstrdup("VT1708BCE", GFP_KERNEL);
3126 snprintf(codec->bus->card->mixername,
3127 sizeof(codec->bus->card->mixername),
3128 "%s %s", codec->vendor_name, codec->chip_name);
970f630f 3129 }
bc92df7f
LW
3130 /* correct names for VT1705 */
3131 if (codec->vendor_id == 0x11064397) {
3132 kfree(codec->chip_name);
3133 codec->chip_name = kstrdup("VT1705", GFP_KERNEL);
3134 snprintf(codec->bus->card->mixername,
3135 sizeof(codec->bus->card->mixername),
3136 "%s %s", codec->vendor_name, codec->chip_name);
3137 }
3e95b9ab 3138 spec->set_widgets_power_state = set_widgets_power_state_vt1708B;
d949cac1
HW
3139 return 0;
3140}
3141
3142/* Patch for VT1702 */
3143
096a8854 3144static const struct hda_verb vt1702_init_verbs[] = {
bc7e7e5c
LW
3145 /* mixer enable */
3146 {0x1, 0xF88, 0x3},
3147 /* GPIO 0~2 */
3148 {0x1, 0xF82, 0x3F},
d949cac1
HW
3149 { }
3150};
3151
3e95b9ab
LW
3152static void set_widgets_power_state_vt1702(struct hda_codec *codec)
3153{
3154 int imux_is_smixer =
3155 snd_hda_codec_read(codec, 0x13, 0, AC_VERB_GET_CONNECT_SEL, 0x00) == 3;
3156 unsigned int parm;
3157 /* inputs */
3158 /* PW 1/2/5 (14h/15h/18h) */
3159 parm = AC_PWRST_D3;
3160 set_pin_power_state(codec, 0x14, &parm);
3161 set_pin_power_state(codec, 0x15, &parm);
3162 set_pin_power_state(codec, 0x18, &parm);
3163 if (imux_is_smixer)
3164 parm = AC_PWRST_D0; /* SW0 (13h) = stereo mixer (idx 3) */
3165 /* SW0 (13h), AIW 0/1/2 (12h/1fh/20h) */
054d867e
TI
3166 update_power_state(codec, 0x13, parm);
3167 update_power_state(codec, 0x12, parm);
3168 update_power_state(codec, 0x1f, parm);
3169 update_power_state(codec, 0x20, parm);
3e95b9ab
LW
3170
3171 /* outputs */
3172 /* PW 3/4 (16h/17h) */
3173 parm = AC_PWRST_D3;
3174 set_pin_power_state(codec, 0x17, &parm);
3175 set_pin_power_state(codec, 0x16, &parm);
3176 /* MW0 (1ah), AOW 0/1 (10h/1dh) */
054d867e
TI
3177 update_power_state(codec, 0x1a, imux_is_smixer ? AC_PWRST_D0 : parm);
3178 update_power_state(codec, 0x10, parm);
3179 update_power_state(codec, 0x1d, parm);
3e95b9ab
LW
3180}
3181
d949cac1
HW
3182static int patch_vt1702(struct hda_codec *codec)
3183{
3184 struct via_spec *spec;
3185 int err;
d949cac1
HW
3186
3187 /* create a codec specific record */
5b0cb1d8 3188 spec = via_new_spec(codec);
d949cac1
HW
3189 if (spec == NULL)
3190 return -ENOMEM;
3191
620e2b28
TI
3192 spec->aa_mix_nid = 0x1a;
3193
12daef65
TI
3194 /* limit AA path volume to 0 dB */
3195 snd_hda_override_amp_caps(codec, 0x1A, HDA_INPUT,
3196 (0x17 << AC_AMPCAP_OFFSET_SHIFT) |
3197 (0x17 << AC_AMPCAP_NUM_STEPS_SHIFT) |
3198 (0x5 << AC_AMPCAP_STEP_SIZE_SHIFT) |
3199 (1 << AC_AMPCAP_MUTE_SHIFT));
3200
d949cac1 3201 /* automatic parse from the BIOS config */
12daef65 3202 err = via_parse_auto_config(codec);
d949cac1
HW
3203 if (err < 0) {
3204 via_free(codec);
3205 return err;
d949cac1
HW
3206 }
3207
096a8854 3208 spec->init_verbs[spec->num_iverbs++] = vt1702_init_verbs;
d949cac1 3209
d949cac1
HW
3210 codec->patch_ops = via_patch_ops;
3211
3e95b9ab 3212 spec->set_widgets_power_state = set_widgets_power_state_vt1702;
d949cac1
HW
3213 return 0;
3214}
3215
eb7188ca
LW
3216/* Patch for VT1718S */
3217
096a8854 3218static const struct hda_verb vt1718S_init_verbs[] = {
4ab2d53a
LW
3219 /* Enable MW0 adjust Gain 5 */
3220 {0x1, 0xfb2, 0x10},
eb7188ca
LW
3221 /* Enable Boost Volume backdoor */
3222 {0x1, 0xf88, 0x8},
5d41762a 3223
eb7188ca
LW
3224 { }
3225};
3226
3e95b9ab
LW
3227static void set_widgets_power_state_vt1718S(struct hda_codec *codec)
3228{
3229 struct via_spec *spec = codec->spec;
3230 int imux_is_smixer;
3231 unsigned int parm;
3232 /* MUX6 (1eh) = stereo mixer */
3233 imux_is_smixer =
3234 snd_hda_codec_read(codec, 0x1e, 0, AC_VERB_GET_CONNECT_SEL, 0x00) == 5;
3235 /* inputs */
3236 /* PW 5/6/7 (29h/2ah/2bh) */
3237 parm = AC_PWRST_D3;
3238 set_pin_power_state(codec, 0x29, &parm);
3239 set_pin_power_state(codec, 0x2a, &parm);
3240 set_pin_power_state(codec, 0x2b, &parm);
3241 if (imux_is_smixer)
3242 parm = AC_PWRST_D0;
3243 /* MUX6/7 (1eh/1fh), AIW 0/1 (10h/11h) */
054d867e
TI
3244 update_power_state(codec, 0x1e, parm);
3245 update_power_state(codec, 0x1f, parm);
3246 update_power_state(codec, 0x10, parm);
3247 update_power_state(codec, 0x11, parm);
3e95b9ab
LW
3248
3249 /* outputs */
3250 /* PW3 (27h), MW2 (1ah), AOW3 (bh) */
3251 parm = AC_PWRST_D3;
3252 set_pin_power_state(codec, 0x27, &parm);
054d867e
TI
3253 update_power_state(codec, 0x1a, parm);
3254 update_power_state(codec, 0xb, parm);
3e95b9ab
LW
3255
3256 /* PW2 (26h), AOW2 (ah) */
3257 parm = AC_PWRST_D3;
3258 set_pin_power_state(codec, 0x26, &parm);
3259 if (spec->smart51_enabled)
3260 set_pin_power_state(codec, 0x2b, &parm);
054d867e 3261 update_power_state(codec, 0xa, parm);
3e95b9ab
LW
3262
3263 /* PW0 (24h), AOW0 (8h) */
3264 parm = AC_PWRST_D3;
3265 set_pin_power_state(codec, 0x24, &parm);
3266 if (!spec->hp_independent_mode) /* check for redirected HP */
3267 set_pin_power_state(codec, 0x28, &parm);
054d867e 3268 update_power_state(codec, 0x8, parm);
3e95b9ab 3269 /* MW9 (21h), Mw2 (1ah), AOW0 (8h) */
054d867e 3270 update_power_state(codec, 0x21, imux_is_smixer ? AC_PWRST_D0 : parm);
3e95b9ab
LW
3271
3272 /* PW1 (25h), AOW1 (9h) */
3273 parm = AC_PWRST_D3;
3274 set_pin_power_state(codec, 0x25, &parm);
3275 if (spec->smart51_enabled)
3276 set_pin_power_state(codec, 0x2a, &parm);
054d867e 3277 update_power_state(codec, 0x9, parm);
3e95b9ab
LW
3278
3279 if (spec->hp_independent_mode) {
3280 /* PW4 (28h), MW3 (1bh), MUX1(34h), AOW4 (ch) */
3281 parm = AC_PWRST_D3;
3282 set_pin_power_state(codec, 0x28, &parm);
054d867e
TI
3283 update_power_state(codec, 0x1b, parm);
3284 update_power_state(codec, 0x34, parm);
3285 update_power_state(codec, 0xc, parm);
3e95b9ab
LW
3286 }
3287}
3288
30b45033
TI
3289/* Add a connection to the primary DAC from AA-mixer for some codecs
3290 * This isn't listed from the raw info, but the chip has a secret connection.
3291 */
3292static int add_secret_dac_path(struct hda_codec *codec)
3293{
3294 struct via_spec *spec = codec->spec;
3295 int i, nums;
3296 hda_nid_t conn[8];
3297 hda_nid_t nid;
3298
3299 if (!spec->aa_mix_nid)
3300 return 0;
3301 nums = snd_hda_get_connections(codec, spec->aa_mix_nid, conn,
3302 ARRAY_SIZE(conn) - 1);
3303 for (i = 0; i < nums; i++) {
3304 if (get_wcaps_type(get_wcaps(codec, conn[i])) == AC_WID_AUD_OUT)
3305 return 0;
3306 }
3307
3308 /* find the primary DAC and add to the connection list */
3309 nid = codec->start_nid;
3310 for (i = 0; i < codec->num_nodes; i++, nid++) {
3311 unsigned int caps = get_wcaps(codec, nid);
3312 if (get_wcaps_type(caps) == AC_WID_AUD_OUT &&
3313 !(caps & AC_WCAP_DIGITAL)) {
3314 conn[nums++] = nid;
3315 return snd_hda_override_conn_list(codec,
3316 spec->aa_mix_nid,
3317 nums, conn);
3318 }
3319 }
3320 return 0;
3321}
3322
3323
eb7188ca
LW
3324static int patch_vt1718S(struct hda_codec *codec)
3325{
3326 struct via_spec *spec;
3327 int err;
3328
3329 /* create a codec specific record */
5b0cb1d8 3330 spec = via_new_spec(codec);
eb7188ca
LW
3331 if (spec == NULL)
3332 return -ENOMEM;
3333
620e2b28 3334 spec->aa_mix_nid = 0x21;
d7a99cce
TI
3335 override_mic_boost(codec, 0x2b, 0, 3, 40);
3336 override_mic_boost(codec, 0x29, 0, 3, 40);
30b45033 3337 add_secret_dac_path(codec);
620e2b28 3338
eb7188ca 3339 /* automatic parse from the BIOS config */
12daef65 3340 err = via_parse_auto_config(codec);
eb7188ca
LW
3341 if (err < 0) {
3342 via_free(codec);
3343 return err;
eb7188ca
LW
3344 }
3345
096a8854 3346 spec->init_verbs[spec->num_iverbs++] = vt1718S_init_verbs;
eb7188ca 3347
eb7188ca
LW
3348 codec->patch_ops = via_patch_ops;
3349
3e95b9ab
LW
3350 spec->set_widgets_power_state = set_widgets_power_state_vt1718S;
3351
eb7188ca
LW
3352 return 0;
3353}
f3db423d
LW
3354
3355/* Patch for VT1716S */
3356
3357static int vt1716s_dmic_info(struct snd_kcontrol *kcontrol,
3358 struct snd_ctl_elem_info *uinfo)
3359{
3360 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN;
3361 uinfo->count = 1;
3362 uinfo->value.integer.min = 0;
3363 uinfo->value.integer.max = 1;
3364 return 0;
3365}
3366
3367static int vt1716s_dmic_get(struct snd_kcontrol *kcontrol,
3368 struct snd_ctl_elem_value *ucontrol)
3369{
3370 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
3371 int index = 0;
3372
3373 index = snd_hda_codec_read(codec, 0x26, 0,
3374 AC_VERB_GET_CONNECT_SEL, 0);
3375 if (index != -1)
3376 *ucontrol->value.integer.value = index;
3377
3378 return 0;
3379}
3380
3381static int vt1716s_dmic_put(struct snd_kcontrol *kcontrol,
3382 struct snd_ctl_elem_value *ucontrol)
3383{
3384 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
3385 struct via_spec *spec = codec->spec;
3386 int index = *ucontrol->value.integer.value;
3387
3388 snd_hda_codec_write(codec, 0x26, 0,
3389 AC_VERB_SET_CONNECT_SEL, index);
3390 spec->dmic_enabled = index;
3e95b9ab 3391 set_widgets_power_state(codec);
f3db423d
LW
3392 return 1;
3393}
3394
90dd48a1 3395static const struct snd_kcontrol_new vt1716s_dmic_mixer[] = {
f3db423d
LW
3396 HDA_CODEC_VOLUME("Digital Mic Capture Volume", 0x22, 0x0, HDA_INPUT),
3397 {
3398 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3399 .name = "Digital Mic Capture Switch",
5b0cb1d8 3400 .subdevice = HDA_SUBDEV_NID_FLAG | 0x26,
f3db423d
LW
3401 .count = 1,
3402 .info = vt1716s_dmic_info,
3403 .get = vt1716s_dmic_get,
3404 .put = vt1716s_dmic_put,
3405 },
3406 {} /* end */
3407};
3408
3409
3410/* mono-out mixer elements */
90dd48a1 3411static const struct snd_kcontrol_new vt1716S_mono_out_mixer[] = {
f3db423d
LW
3412 HDA_CODEC_MUTE("Mono Playback Switch", 0x2a, 0x0, HDA_OUTPUT),
3413 { } /* end */
3414};
3415
096a8854 3416static const struct hda_verb vt1716S_init_verbs[] = {
f3db423d
LW
3417 /* Enable Boost Volume backdoor */
3418 {0x1, 0xf8a, 0x80},
3419 /* don't bybass mixer */
3420 {0x1, 0xf88, 0xc0},
3421 /* Enable mono output */
3422 {0x1, 0xf90, 0x08},
3423 { }
3424};
3425
3e95b9ab
LW
3426static void set_widgets_power_state_vt1716S(struct hda_codec *codec)
3427{
3428 struct via_spec *spec = codec->spec;
3429 int imux_is_smixer;
3430 unsigned int parm;
3431 unsigned int mono_out, present;
3432 /* SW0 (17h) = stereo mixer */
3433 imux_is_smixer =
3434 (snd_hda_codec_read(codec, 0x17, 0,
3435 AC_VERB_GET_CONNECT_SEL, 0x00) == 5);
3436 /* inputs */
3437 /* PW 1/2/5 (1ah/1bh/1eh) */
3438 parm = AC_PWRST_D3;
3439 set_pin_power_state(codec, 0x1a, &parm);
3440 set_pin_power_state(codec, 0x1b, &parm);
3441 set_pin_power_state(codec, 0x1e, &parm);
3442 if (imux_is_smixer)
3443 parm = AC_PWRST_D0;
3444 /* SW0 (17h), AIW0(13h) */
054d867e
TI
3445 update_power_state(codec, 0x17, parm);
3446 update_power_state(codec, 0x13, parm);
3e95b9ab
LW
3447
3448 parm = AC_PWRST_D3;
3449 set_pin_power_state(codec, 0x1e, &parm);
3450 /* PW11 (22h) */
3451 if (spec->dmic_enabled)
3452 set_pin_power_state(codec, 0x22, &parm);
3453 else
054d867e 3454 update_power_state(codec, 0x22, AC_PWRST_D3);
3e95b9ab
LW
3455
3456 /* SW2(26h), AIW1(14h) */
054d867e
TI
3457 update_power_state(codec, 0x26, parm);
3458 update_power_state(codec, 0x14, parm);
3e95b9ab
LW
3459
3460 /* outputs */
3461 /* PW0 (19h), SW1 (18h), AOW1 (11h) */
3462 parm = AC_PWRST_D3;
3463 set_pin_power_state(codec, 0x19, &parm);
3464 /* Smart 5.1 PW2(1bh) */
3465 if (spec->smart51_enabled)
3466 set_pin_power_state(codec, 0x1b, &parm);
054d867e
TI
3467 update_power_state(codec, 0x18, parm);
3468 update_power_state(codec, 0x11, parm);
3e95b9ab
LW
3469
3470 /* PW7 (23h), SW3 (27h), AOW3 (25h) */
3471 parm = AC_PWRST_D3;
3472 set_pin_power_state(codec, 0x23, &parm);
3473 /* Smart 5.1 PW1(1ah) */
3474 if (spec->smart51_enabled)
3475 set_pin_power_state(codec, 0x1a, &parm);
054d867e 3476 update_power_state(codec, 0x27, parm);
3e95b9ab
LW
3477
3478 /* Smart 5.1 PW5(1eh) */
3479 if (spec->smart51_enabled)
3480 set_pin_power_state(codec, 0x1e, &parm);
054d867e 3481 update_power_state(codec, 0x25, parm);
3e95b9ab
LW
3482
3483 /* Mono out */
3484 /* SW4(28h)->MW1(29h)-> PW12 (2ah)*/
3485 present = snd_hda_jack_detect(codec, 0x1c);
3486
3487 if (present)
3488 mono_out = 0;
3489 else {
3490 present = snd_hda_jack_detect(codec, 0x1d);
3491 if (!spec->hp_independent_mode && present)
3492 mono_out = 0;
3493 else
3494 mono_out = 1;
3495 }
3496 parm = mono_out ? AC_PWRST_D0 : AC_PWRST_D3;
054d867e
TI
3497 update_power_state(codec, 0x28, parm);
3498 update_power_state(codec, 0x29, parm);
3499 update_power_state(codec, 0x2a, parm);
3e95b9ab
LW
3500
3501 /* PW 3/4 (1ch/1dh) */
3502 parm = AC_PWRST_D3;
3503 set_pin_power_state(codec, 0x1c, &parm);
3504 set_pin_power_state(codec, 0x1d, &parm);
3505 /* HP Independent Mode, power on AOW3 */
3506 if (spec->hp_independent_mode)
054d867e 3507 update_power_state(codec, 0x25, parm);
3e95b9ab
LW
3508
3509 /* force to D0 for internal Speaker */
3510 /* MW0 (16h), AOW0 (10h) */
054d867e
TI
3511 update_power_state(codec, 0x16, imux_is_smixer ? AC_PWRST_D0 : parm);
3512 update_power_state(codec, 0x10, mono_out ? AC_PWRST_D0 : parm);
3e95b9ab
LW
3513}
3514
f3db423d
LW
3515static int patch_vt1716S(struct hda_codec *codec)
3516{
3517 struct via_spec *spec;
3518 int err;
3519
3520 /* create a codec specific record */
5b0cb1d8 3521 spec = via_new_spec(codec);
f3db423d
LW
3522 if (spec == NULL)
3523 return -ENOMEM;
3524
620e2b28 3525 spec->aa_mix_nid = 0x16;
d7a99cce
TI
3526 override_mic_boost(codec, 0x1a, 0, 3, 40);
3527 override_mic_boost(codec, 0x1e, 0, 3, 40);
620e2b28 3528
f3db423d 3529 /* automatic parse from the BIOS config */
12daef65 3530 err = via_parse_auto_config(codec);
f3db423d
LW
3531 if (err < 0) {
3532 via_free(codec);
3533 return err;
f3db423d
LW
3534 }
3535
096a8854 3536 spec->init_verbs[spec->num_iverbs++] = vt1716S_init_verbs;
f3db423d 3537
f3db423d
LW
3538 spec->mixers[spec->num_mixers] = vt1716s_dmic_mixer;
3539 spec->num_mixers++;
3540
3541 spec->mixers[spec->num_mixers++] = vt1716S_mono_out_mixer;
3542
3543 codec->patch_ops = via_patch_ops;
3544
3e95b9ab 3545 spec->set_widgets_power_state = set_widgets_power_state_vt1716S;
f3db423d
LW
3546 return 0;
3547}
25eaba2f
LW
3548
3549/* for vt2002P */
3550
096a8854 3551static const struct hda_verb vt2002P_init_verbs[] = {
eadb9a80
LW
3552 /* Class-D speaker related verbs */
3553 {0x1, 0xfe0, 0x4},
3554 {0x1, 0xfe9, 0x80},
3555 {0x1, 0xfe2, 0x22},
25eaba2f
LW
3556 /* Enable Boost Volume backdoor */
3557 {0x1, 0xfb9, 0x24},
25eaba2f
LW
3558 /* Enable AOW0 to MW9 */
3559 {0x1, 0xfb8, 0x88},
3560 { }
3561};
4a918ffe 3562
096a8854 3563static const struct hda_verb vt1802_init_verbs[] = {
11890956
LW
3564 /* Enable Boost Volume backdoor */
3565 {0x1, 0xfb9, 0x24},
11890956
LW
3566 /* Enable AOW0 to MW9 */
3567 {0x1, 0xfb8, 0x88},
3568 { }
3569};
25eaba2f 3570
3e95b9ab
LW
3571static void set_widgets_power_state_vt2002P(struct hda_codec *codec)
3572{
3573 struct via_spec *spec = codec->spec;
3574 int imux_is_smixer;
3575 unsigned int parm;
3576 unsigned int present;
3577 /* MUX9 (1eh) = stereo mixer */
3578 imux_is_smixer =
3579 snd_hda_codec_read(codec, 0x1e, 0, AC_VERB_GET_CONNECT_SEL, 0x00) == 3;
3580 /* inputs */
3581 /* PW 5/6/7 (29h/2ah/2bh) */
3582 parm = AC_PWRST_D3;
3583 set_pin_power_state(codec, 0x29, &parm);
3584 set_pin_power_state(codec, 0x2a, &parm);
3585 set_pin_power_state(codec, 0x2b, &parm);
3586 parm = AC_PWRST_D0;
3587 /* MUX9/10 (1eh/1fh), AIW 0/1 (10h/11h) */
054d867e
TI
3588 update_power_state(codec, 0x1e, parm);
3589 update_power_state(codec, 0x1f, parm);
3590 update_power_state(codec, 0x10, parm);
3591 update_power_state(codec, 0x11, parm);
3e95b9ab
LW
3592
3593 /* outputs */
3594 /* AOW0 (8h)*/
054d867e 3595 update_power_state(codec, 0x8, parm);
3e95b9ab 3596
11890956
LW
3597 if (spec->codec_type == VT1802) {
3598 /* PW4 (28h), MW4 (18h), MUX4(38h) */
3599 parm = AC_PWRST_D3;
3600 set_pin_power_state(codec, 0x28, &parm);
054d867e
TI
3601 update_power_state(codec, 0x18, parm);
3602 update_power_state(codec, 0x38, parm);
11890956
LW
3603 } else {
3604 /* PW4 (26h), MW4 (1ch), MUX4(37h) */
3605 parm = AC_PWRST_D3;
3606 set_pin_power_state(codec, 0x26, &parm);
054d867e
TI
3607 update_power_state(codec, 0x1c, parm);
3608 update_power_state(codec, 0x37, parm);
11890956 3609 }
3e95b9ab 3610
11890956
LW
3611 if (spec->codec_type == VT1802) {
3612 /* PW1 (25h), MW1 (15h), MUX1(35h), AOW1 (9h) */
3613 parm = AC_PWRST_D3;
3614 set_pin_power_state(codec, 0x25, &parm);
054d867e
TI
3615 update_power_state(codec, 0x15, parm);
3616 update_power_state(codec, 0x35, parm);
11890956
LW
3617 } else {
3618 /* PW1 (25h), MW1 (19h), MUX1(35h), AOW1 (9h) */
3619 parm = AC_PWRST_D3;
3620 set_pin_power_state(codec, 0x25, &parm);
054d867e
TI
3621 update_power_state(codec, 0x19, parm);
3622 update_power_state(codec, 0x35, parm);
11890956 3623 }
3e95b9ab
LW
3624
3625 if (spec->hp_independent_mode)
054d867e 3626 update_power_state(codec, 0x9, AC_PWRST_D0);
3e95b9ab
LW
3627
3628 /* Class-D */
3629 /* PW0 (24h), MW0(18h/14h), MUX0(34h) */
3630 present = snd_hda_jack_detect(codec, 0x25);
3631
3632 parm = AC_PWRST_D3;
3633 set_pin_power_state(codec, 0x24, &parm);
3634 parm = present ? AC_PWRST_D3 : AC_PWRST_D0;
11890956 3635 if (spec->codec_type == VT1802)
054d867e 3636 update_power_state(codec, 0x14, parm);
11890956 3637 else
054d867e
TI
3638 update_power_state(codec, 0x18, parm);
3639 update_power_state(codec, 0x34, parm);
3e95b9ab
LW
3640
3641 /* Mono Out */
3642 present = snd_hda_jack_detect(codec, 0x26);
3643
3644 parm = present ? AC_PWRST_D3 : AC_PWRST_D0;
11890956
LW
3645 if (spec->codec_type == VT1802) {
3646 /* PW15 (33h), MW8(1ch), MUX8(3ch) */
054d867e
TI
3647 update_power_state(codec, 0x33, parm);
3648 update_power_state(codec, 0x1c, parm);
3649 update_power_state(codec, 0x3c, parm);
11890956
LW
3650 } else {
3651 /* PW15 (31h), MW8(17h), MUX8(3bh) */
054d867e
TI
3652 update_power_state(codec, 0x31, parm);
3653 update_power_state(codec, 0x17, parm);
3654 update_power_state(codec, 0x3b, parm);
11890956 3655 }
3e95b9ab
LW
3656 /* MW9 (21h) */
3657 if (imux_is_smixer || !is_aa_path_mute(codec))
054d867e 3658 update_power_state(codec, 0x21, AC_PWRST_D0);
3e95b9ab 3659 else
054d867e 3660 update_power_state(codec, 0x21, AC_PWRST_D3);
3e95b9ab 3661}
25eaba2f
LW
3662
3663/* patch for vt2002P */
3664static int patch_vt2002P(struct hda_codec *codec)
3665{
3666 struct via_spec *spec;
3667 int err;
3668
3669 /* create a codec specific record */
5b0cb1d8 3670 spec = via_new_spec(codec);
25eaba2f
LW
3671 if (spec == NULL)
3672 return -ENOMEM;
3673
620e2b28 3674 spec->aa_mix_nid = 0x21;
d7a99cce
TI
3675 override_mic_boost(codec, 0x2b, 0, 3, 40);
3676 override_mic_boost(codec, 0x29, 0, 3, 40);
30b45033 3677 add_secret_dac_path(codec);
620e2b28 3678
25eaba2f 3679 /* automatic parse from the BIOS config */
12daef65 3680 err = via_parse_auto_config(codec);
25eaba2f
LW
3681 if (err < 0) {
3682 via_free(codec);
3683 return err;
25eaba2f
LW
3684 }
3685
11890956 3686 if (spec->codec_type == VT1802)
4a918ffe 3687 spec->init_verbs[spec->num_iverbs++] = vt1802_init_verbs;
11890956 3688 else
4a918ffe 3689 spec->init_verbs[spec->num_iverbs++] = vt2002P_init_verbs;
11890956 3690
25eaba2f
LW
3691 codec->patch_ops = via_patch_ops;
3692
3e95b9ab 3693 spec->set_widgets_power_state = set_widgets_power_state_vt2002P;
25eaba2f
LW
3694 return 0;
3695}
ab6734e7
LW
3696
3697/* for vt1812 */
3698
096a8854 3699static const struct hda_verb vt1812_init_verbs[] = {
ab6734e7
LW
3700 /* Enable Boost Volume backdoor */
3701 {0x1, 0xfb9, 0x24},
ab6734e7
LW
3702 /* Enable AOW0 to MW9 */
3703 {0x1, 0xfb8, 0xa8},
3704 { }
3705};
3706
3e95b9ab
LW
3707static void set_widgets_power_state_vt1812(struct hda_codec *codec)
3708{
3709 struct via_spec *spec = codec->spec;
3e95b9ab
LW
3710 unsigned int parm;
3711 unsigned int present;
3e95b9ab
LW
3712 /* inputs */
3713 /* PW 5/6/7 (29h/2ah/2bh) */
3714 parm = AC_PWRST_D3;
3715 set_pin_power_state(codec, 0x29, &parm);
3716 set_pin_power_state(codec, 0x2a, &parm);
3717 set_pin_power_state(codec, 0x2b, &parm);
3718 parm = AC_PWRST_D0;
3719 /* MUX10/11 (1eh/1fh), AIW 0/1 (10h/11h) */
054d867e
TI
3720 update_power_state(codec, 0x1e, parm);
3721 update_power_state(codec, 0x1f, parm);
3722 update_power_state(codec, 0x10, parm);
3723 update_power_state(codec, 0x11, parm);
3e95b9ab
LW
3724
3725 /* outputs */
3726 /* AOW0 (8h)*/
054d867e 3727 update_power_state(codec, 0x8, AC_PWRST_D0);
3e95b9ab
LW
3728
3729 /* PW4 (28h), MW4 (18h), MUX4(38h) */
3730 parm = AC_PWRST_D3;
3731 set_pin_power_state(codec, 0x28, &parm);
054d867e
TI
3732 update_power_state(codec, 0x18, parm);
3733 update_power_state(codec, 0x38, parm);
3e95b9ab
LW
3734
3735 /* PW1 (25h), MW1 (15h), MUX1(35h), AOW1 (9h) */
3736 parm = AC_PWRST_D3;
3737 set_pin_power_state(codec, 0x25, &parm);
054d867e
TI
3738 update_power_state(codec, 0x15, parm);
3739 update_power_state(codec, 0x35, parm);
3e95b9ab 3740 if (spec->hp_independent_mode)
054d867e 3741 update_power_state(codec, 0x9, AC_PWRST_D0);
3e95b9ab
LW
3742
3743 /* Internal Speaker */
3744 /* PW0 (24h), MW0(14h), MUX0(34h) */
3745 present = snd_hda_jack_detect(codec, 0x25);
3746
3747 parm = AC_PWRST_D3;
3748 set_pin_power_state(codec, 0x24, &parm);
3749 if (present) {
054d867e
TI
3750 update_power_state(codec, 0x14, AC_PWRST_D3);
3751 update_power_state(codec, 0x34, AC_PWRST_D3);
3e95b9ab 3752 } else {
054d867e
TI
3753 update_power_state(codec, 0x14, AC_PWRST_D0);
3754 update_power_state(codec, 0x34, AC_PWRST_D0);
3e95b9ab
LW
3755 }
3756
3757
3758 /* Mono Out */
3759 /* PW13 (31h), MW13(1ch), MUX13(3ch), MW14(3eh) */
3760 present = snd_hda_jack_detect(codec, 0x28);
3761
3762 parm = AC_PWRST_D3;
3763 set_pin_power_state(codec, 0x31, &parm);
3764 if (present) {
054d867e
TI
3765 update_power_state(codec, 0x1c, AC_PWRST_D3);
3766 update_power_state(codec, 0x3c, AC_PWRST_D3);
3767 update_power_state(codec, 0x3e, AC_PWRST_D3);
3e95b9ab 3768 } else {
054d867e
TI
3769 update_power_state(codec, 0x1c, AC_PWRST_D0);
3770 update_power_state(codec, 0x3c, AC_PWRST_D0);
3771 update_power_state(codec, 0x3e, AC_PWRST_D0);
3e95b9ab
LW
3772 }
3773
3774 /* PW15 (33h), MW15 (1dh), MUX15(3dh) */
3775 parm = AC_PWRST_D3;
3776 set_pin_power_state(codec, 0x33, &parm);
054d867e
TI
3777 update_power_state(codec, 0x1d, parm);
3778 update_power_state(codec, 0x3d, parm);
3e95b9ab
LW
3779
3780}
ab6734e7
LW
3781
3782/* patch for vt1812 */
3783static int patch_vt1812(struct hda_codec *codec)
3784{
3785 struct via_spec *spec;
3786 int err;
3787
3788 /* create a codec specific record */
5b0cb1d8 3789 spec = via_new_spec(codec);
ab6734e7
LW
3790 if (spec == NULL)
3791 return -ENOMEM;
3792
620e2b28 3793 spec->aa_mix_nid = 0x21;
d7a99cce
TI
3794 override_mic_boost(codec, 0x2b, 0, 3, 40);
3795 override_mic_boost(codec, 0x29, 0, 3, 40);
30b45033 3796 add_secret_dac_path(codec);
620e2b28 3797
ab6734e7 3798 /* automatic parse from the BIOS config */
12daef65 3799 err = via_parse_auto_config(codec);
ab6734e7
LW
3800 if (err < 0) {
3801 via_free(codec);
3802 return err;
ab6734e7
LW
3803 }
3804
096a8854 3805 spec->init_verbs[spec->num_iverbs++] = vt1812_init_verbs;
ab6734e7 3806
ab6734e7
LW
3807 codec->patch_ops = via_patch_ops;
3808
3e95b9ab 3809 spec->set_widgets_power_state = set_widgets_power_state_vt1812;
ab6734e7
LW
3810 return 0;
3811}
3812
c577b8a1
JC
3813/*
3814 * patch entries
3815 */
90dd48a1 3816static const struct hda_codec_preset snd_hda_preset_via[] = {
3218c178
TI
3817 { .id = 0x11061708, .name = "VT1708", .patch = patch_vt1708},
3818 { .id = 0x11061709, .name = "VT1708", .patch = patch_vt1708},
3819 { .id = 0x1106170a, .name = "VT1708", .patch = patch_vt1708},
3820 { .id = 0x1106170b, .name = "VT1708", .patch = patch_vt1708},
3821 { .id = 0x1106e710, .name = "VT1709 10-Ch",
ddd304d8 3822 .patch = patch_vt1709},
3218c178 3823 { .id = 0x1106e711, .name = "VT1709 10-Ch",
ddd304d8 3824 .patch = patch_vt1709},
3218c178 3825 { .id = 0x1106e712, .name = "VT1709 10-Ch",
ddd304d8 3826 .patch = patch_vt1709},
3218c178 3827 { .id = 0x1106e713, .name = "VT1709 10-Ch",
ddd304d8 3828 .patch = patch_vt1709},
3218c178 3829 { .id = 0x1106e714, .name = "VT1709 6-Ch",
ddd304d8 3830 .patch = patch_vt1709},
3218c178 3831 { .id = 0x1106e715, .name = "VT1709 6-Ch",
ddd304d8 3832 .patch = patch_vt1709},
3218c178 3833 { .id = 0x1106e716, .name = "VT1709 6-Ch",
ddd304d8 3834 .patch = patch_vt1709},
3218c178 3835 { .id = 0x1106e717, .name = "VT1709 6-Ch",
ddd304d8 3836 .patch = patch_vt1709},
3218c178 3837 { .id = 0x1106e720, .name = "VT1708B 8-Ch",
ddd304d8 3838 .patch = patch_vt1708B},
3218c178 3839 { .id = 0x1106e721, .name = "VT1708B 8-Ch",
ddd304d8 3840 .patch = patch_vt1708B},
3218c178 3841 { .id = 0x1106e722, .name = "VT1708B 8-Ch",
ddd304d8 3842 .patch = patch_vt1708B},
3218c178 3843 { .id = 0x1106e723, .name = "VT1708B 8-Ch",
ddd304d8 3844 .patch = patch_vt1708B},
3218c178 3845 { .id = 0x1106e724, .name = "VT1708B 4-Ch",
ddd304d8 3846 .patch = patch_vt1708B},
3218c178 3847 { .id = 0x1106e725, .name = "VT1708B 4-Ch",
ddd304d8 3848 .patch = patch_vt1708B},
3218c178 3849 { .id = 0x1106e726, .name = "VT1708B 4-Ch",
ddd304d8 3850 .patch = patch_vt1708B},
3218c178 3851 { .id = 0x1106e727, .name = "VT1708B 4-Ch",
ddd304d8 3852 .patch = patch_vt1708B},
3218c178 3853 { .id = 0x11060397, .name = "VT1708S",
d949cac1 3854 .patch = patch_vt1708S},
3218c178 3855 { .id = 0x11061397, .name = "VT1708S",
d949cac1 3856 .patch = patch_vt1708S},
3218c178 3857 { .id = 0x11062397, .name = "VT1708S",
d949cac1 3858 .patch = patch_vt1708S},
3218c178 3859 { .id = 0x11063397, .name = "VT1708S",
d949cac1 3860 .patch = patch_vt1708S},
bc92df7f 3861 { .id = 0x11064397, .name = "VT1705",
d949cac1 3862 .patch = patch_vt1708S},
3218c178 3863 { .id = 0x11065397, .name = "VT1708S",
d949cac1 3864 .patch = patch_vt1708S},
3218c178 3865 { .id = 0x11066397, .name = "VT1708S",
d949cac1 3866 .patch = patch_vt1708S},
3218c178 3867 { .id = 0x11067397, .name = "VT1708S",
d949cac1 3868 .patch = patch_vt1708S},
3218c178 3869 { .id = 0x11060398, .name = "VT1702",
d949cac1 3870 .patch = patch_vt1702},
3218c178 3871 { .id = 0x11061398, .name = "VT1702",
d949cac1 3872 .patch = patch_vt1702},
3218c178 3873 { .id = 0x11062398, .name = "VT1702",
d949cac1 3874 .patch = patch_vt1702},
3218c178 3875 { .id = 0x11063398, .name = "VT1702",
d949cac1 3876 .patch = patch_vt1702},
3218c178 3877 { .id = 0x11064398, .name = "VT1702",
d949cac1 3878 .patch = patch_vt1702},
3218c178 3879 { .id = 0x11065398, .name = "VT1702",
d949cac1 3880 .patch = patch_vt1702},
3218c178 3881 { .id = 0x11066398, .name = "VT1702",
d949cac1 3882 .patch = patch_vt1702},
3218c178 3883 { .id = 0x11067398, .name = "VT1702",
d949cac1 3884 .patch = patch_vt1702},
eb7188ca
LW
3885 { .id = 0x11060428, .name = "VT1718S",
3886 .patch = patch_vt1718S},
3887 { .id = 0x11064428, .name = "VT1718S",
3888 .patch = patch_vt1718S},
bb3c6bfc
LW
3889 { .id = 0x11060441, .name = "VT2020",
3890 .patch = patch_vt1718S},
3891 { .id = 0x11064441, .name = "VT1828S",
3892 .patch = patch_vt1718S},
f3db423d
LW
3893 { .id = 0x11060433, .name = "VT1716S",
3894 .patch = patch_vt1716S},
3895 { .id = 0x1106a721, .name = "VT1716S",
3896 .patch = patch_vt1716S},
25eaba2f
LW
3897 { .id = 0x11060438, .name = "VT2002P", .patch = patch_vt2002P},
3898 { .id = 0x11064438, .name = "VT2002P", .patch = patch_vt2002P},
ab6734e7 3899 { .id = 0x11060448, .name = "VT1812", .patch = patch_vt1812},
36dd5c4a
LW
3900 { .id = 0x11060440, .name = "VT1818S",
3901 .patch = patch_vt1708S},
11890956
LW
3902 { .id = 0x11060446, .name = "VT1802",
3903 .patch = patch_vt2002P},
3904 { .id = 0x11068446, .name = "VT1802",
3905 .patch = patch_vt2002P},
c577b8a1
JC
3906 {} /* terminator */
3907};
1289e9e8
TI
3908
3909MODULE_ALIAS("snd-hda-codec-id:1106*");
3910
3911static struct hda_codec_preset_list via_list = {
3912 .preset = snd_hda_preset_via,
3913 .owner = THIS_MODULE,
3914};
3915
3916MODULE_LICENSE("GPL");
3917MODULE_DESCRIPTION("VIA HD-audio codec");
3918
3919static int __init patch_via_init(void)
3920{
3921 return snd_hda_add_codec_preset(&via_list);
3922}
3923
3924static void __exit patch_via_exit(void)
3925{
3926 snd_hda_delete_codec_preset(&via_list);
3927}
3928
3929module_init(patch_via_init)
3930module_exit(patch_via_exit)