ALSA: hda - More fixes on Gateway entries
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / sound / pci / hda / patch_sigmatel.c
CommitLineData
2f2f4251
M
1/*
2 * Universal Interface for Intel High Definition Audio Codec
3 *
4 * HD audio interface patch for SigmaTel STAC92xx
5 *
6 * Copyright (c) 2005 Embedded Alley Solutions, Inc.
403d1944 7 * Matt Porter <mporter@embeddedalley.com>
2f2f4251
M
8 *
9 * Based on patch_cmedia.c and patch_realtek.c
10 * Copyright (c) 2004 Takashi Iwai <tiwai@suse.de>
11 *
12 * This driver is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * This driver is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 */
26
2f2f4251
M
27#include <linux/init.h>
28#include <linux/delay.h>
29#include <linux/slab.h>
30#include <linux/pci.h>
31#include <sound/core.h>
c7d4b2fa 32#include <sound/asoundef.h>
45a6ac16 33#include <sound/jack.h>
2f2f4251
M
34#include "hda_codec.h"
35#include "hda_local.h"
1cd2224c 36#include "hda_beep.h"
2f2f4251 37
c6e4c666
TI
38enum {
39 STAC_VREF_EVENT = 1,
40 STAC_INSERT_EVENT,
41 STAC_PWR_EVENT,
42 STAC_HP_EVENT,
43};
4e55096e 44
f5fcc13c
TI
45enum {
46 STAC_REF,
bf277785 47 STAC_9200_OQO,
dfe495d0
TI
48 STAC_9200_DELL_D21,
49 STAC_9200_DELL_D22,
50 STAC_9200_DELL_D23,
51 STAC_9200_DELL_M21,
52 STAC_9200_DELL_M22,
53 STAC_9200_DELL_M23,
54 STAC_9200_DELL_M24,
55 STAC_9200_DELL_M25,
56 STAC_9200_DELL_M26,
57 STAC_9200_DELL_M27,
58eec423
MCC
58 STAC_9200_M4,
59 STAC_9200_M4_2,
117f257d 60 STAC_9200_PANASONIC,
f5fcc13c
TI
61 STAC_9200_MODELS
62};
63
64enum {
65 STAC_9205_REF,
dfe495d0 66 STAC_9205_DELL_M42,
ae0a8ed8
TD
67 STAC_9205_DELL_M43,
68 STAC_9205_DELL_M44,
f5fcc13c
TI
69 STAC_9205_MODELS
70};
71
e1f0d669
MR
72enum {
73 STAC_92HD73XX_REF,
661cd8fb
TI
74 STAC_DELL_M6_AMIC,
75 STAC_DELL_M6_DMIC,
76 STAC_DELL_M6_BOTH,
6b3ab21e 77 STAC_DELL_EQ,
e1f0d669
MR
78 STAC_92HD73XX_MODELS
79};
80
d0513fc6
MR
81enum {
82 STAC_92HD83XXX_REF,
83 STAC_92HD83XXX_MODELS
84};
85
e035b841
MR
86enum {
87 STAC_92HD71BXX_REF,
a7662640
MR
88 STAC_DELL_M4_1,
89 STAC_DELL_M4_2,
3a7abfd2 90 STAC_DELL_M4_3,
6a14f585 91 STAC_HP_M4,
e035b841
MR
92 STAC_92HD71BXX_MODELS
93};
94
8e21c34c
TD
95enum {
96 STAC_925x_REF,
9cb36c2a
MCC
97 STAC_M1,
98 STAC_M1_2,
99 STAC_M2,
8e21c34c 100 STAC_M2_2,
9cb36c2a
MCC
101 STAC_M3,
102 STAC_M5,
103 STAC_M6,
8e21c34c
TD
104 STAC_925x_MODELS
105};
106
f5fcc13c
TI
107enum {
108 STAC_D945_REF,
109 STAC_D945GTP3,
110 STAC_D945GTP5,
5d5d3bc3
IZ
111 STAC_INTEL_MAC_V1,
112 STAC_INTEL_MAC_V2,
113 STAC_INTEL_MAC_V3,
114 STAC_INTEL_MAC_V4,
115 STAC_INTEL_MAC_V5,
536319af
NB
116 STAC_INTEL_MAC_AUTO, /* This model is selected if no module parameter
117 * is given, one of the above models will be
118 * chosen according to the subsystem id. */
dfe495d0 119 /* for backward compatibility */
f5fcc13c 120 STAC_MACMINI,
3fc24d85 121 STAC_MACBOOK,
6f0778d8
NB
122 STAC_MACBOOK_PRO_V1,
123 STAC_MACBOOK_PRO_V2,
f16928fb 124 STAC_IMAC_INTEL,
0dae0f83 125 STAC_IMAC_INTEL_20,
8c650087 126 STAC_ECS_202,
dfe495d0
TI
127 STAC_922X_DELL_D81,
128 STAC_922X_DELL_D82,
129 STAC_922X_DELL_M81,
130 STAC_922X_DELL_M82,
f5fcc13c
TI
131 STAC_922X_MODELS
132};
133
134enum {
135 STAC_D965_REF,
136 STAC_D965_3ST,
137 STAC_D965_5ST,
4ff076e5 138 STAC_DELL_3ST,
8e9068b1 139 STAC_DELL_BIOS,
f5fcc13c
TI
140 STAC_927X_MODELS
141};
403d1944 142
74aeaabc
MR
143struct sigmatel_event {
144 hda_nid_t nid;
c6e4c666
TI
145 unsigned char type;
146 unsigned char tag;
74aeaabc
MR
147 int data;
148};
149
150struct sigmatel_jack {
151 hda_nid_t nid;
152 int type;
153 struct snd_jack *jack;
154};
155
2f2f4251 156struct sigmatel_spec {
c8b6bf9b 157 struct snd_kcontrol_new *mixers[4];
c7d4b2fa
M
158 unsigned int num_mixers;
159
403d1944 160 int board_config;
c0cea0d0 161 unsigned int eapd_switch: 1;
c7d4b2fa 162 unsigned int surr_switch: 1;
403d1944
MP
163 unsigned int line_switch: 1;
164 unsigned int mic_switch: 1;
3cc08dc6 165 unsigned int alt_switch: 1;
82bc955f 166 unsigned int hp_detect: 1;
00ef50c2 167 unsigned int spdif_mute: 1;
c7d4b2fa 168
4fe5195c 169 /* gpio lines */
0fc9dec4 170 unsigned int eapd_mask;
4fe5195c
MR
171 unsigned int gpio_mask;
172 unsigned int gpio_dir;
173 unsigned int gpio_data;
174 unsigned int gpio_mute;
175
8daaaa97
MR
176 /* stream */
177 unsigned int stream_delay;
178
4fe5195c 179 /* analog loopback */
e1f0d669
MR
180 unsigned char aloopback_mask;
181 unsigned char aloopback_shift;
8259980e 182
a64135a2
MR
183 /* power management */
184 unsigned int num_pwrs;
d0513fc6 185 unsigned int *pwr_mapping;
a64135a2 186 hda_nid_t *pwr_nids;
b76c850f 187 hda_nid_t *dac_list;
a64135a2 188
74aeaabc
MR
189 /* jack detection */
190 struct snd_array jacks;
191
192 /* events */
193 struct snd_array events;
194
2f2f4251 195 /* playback */
b22b4821 196 struct hda_input_mux *mono_mux;
89385035 197 struct hda_input_mux *amp_mux;
b22b4821 198 unsigned int cur_mmux;
2f2f4251 199 struct hda_multi_out multiout;
3cc08dc6 200 hda_nid_t dac_nids[5];
2f2f4251
M
201
202 /* capture */
203 hda_nid_t *adc_nids;
2f2f4251 204 unsigned int num_adcs;
dabbed6f
M
205 hda_nid_t *mux_nids;
206 unsigned int num_muxes;
8b65727b
MP
207 hda_nid_t *dmic_nids;
208 unsigned int num_dmics;
e1f0d669 209 hda_nid_t *dmux_nids;
1697055e 210 unsigned int num_dmuxes;
d9737751
MR
211 hda_nid_t *smux_nids;
212 unsigned int num_smuxes;
65973632 213 const char **spdif_labels;
d9737751 214
dabbed6f 215 hda_nid_t dig_in_nid;
b22b4821 216 hda_nid_t mono_nid;
1cd2224c
MR
217 hda_nid_t anabeep_nid;
218 hda_nid_t digbeep_nid;
2f2f4251 219
2f2f4251
M
220 /* pin widgets */
221 hda_nid_t *pin_nids;
222 unsigned int num_pins;
2f2f4251 223 unsigned int *pin_configs;
2f2f4251
M
224
225 /* codec specific stuff */
226 struct hda_verb *init;
c8b6bf9b 227 struct snd_kcontrol_new *mixer;
2f2f4251
M
228
229 /* capture source */
8b65727b 230 struct hda_input_mux *dinput_mux;
e1f0d669 231 unsigned int cur_dmux[2];
c7d4b2fa 232 struct hda_input_mux *input_mux;
3cc08dc6 233 unsigned int cur_mux[3];
d9737751
MR
234 struct hda_input_mux *sinput_mux;
235 unsigned int cur_smux[2];
2a9c7816
MR
236 unsigned int cur_amux;
237 hda_nid_t *amp_nids;
238 unsigned int num_amps;
8daaaa97 239 unsigned int powerdown_adcs;
2f2f4251 240
403d1944
MP
241 /* i/o switches */
242 unsigned int io_switch[2];
0fb87bb4 243 unsigned int clfe_swap;
d7a89436 244 unsigned int hp_switch; /* NID of HP as line-out */
5f10c4a9 245 unsigned int aloopback;
2f2f4251 246
c7d4b2fa
M
247 struct hda_pcm pcm_rec[2]; /* PCM information */
248
249 /* dynamic controls and input_mux */
250 struct auto_pin_cfg autocfg;
603c4019 251 struct snd_array kctls;
8b65727b 252 struct hda_input_mux private_dimux;
c7d4b2fa 253 struct hda_input_mux private_imux;
d9737751 254 struct hda_input_mux private_smux;
89385035 255 struct hda_input_mux private_amp_mux;
b22b4821 256 struct hda_input_mux private_mono_mux;
2f2f4251
M
257};
258
259static hda_nid_t stac9200_adc_nids[1] = {
260 0x03,
261};
262
263static hda_nid_t stac9200_mux_nids[1] = {
264 0x0c,
265};
266
267static hda_nid_t stac9200_dac_nids[1] = {
268 0x02,
269};
270
a64135a2
MR
271static hda_nid_t stac92hd73xx_pwr_nids[8] = {
272 0x0a, 0x0b, 0x0c, 0xd, 0x0e,
273 0x0f, 0x10, 0x11
274};
275
0ffa9807
MR
276static hda_nid_t stac92hd73xx_slave_dig_outs[2] = {
277 0x26, 0,
278};
279
e1f0d669
MR
280static hda_nid_t stac92hd73xx_adc_nids[2] = {
281 0x1a, 0x1b
282};
283
2a9c7816
MR
284#define DELL_M6_AMP 2
285static hda_nid_t stac92hd73xx_amp_nids[3] = {
286 0x0b, 0x0c, 0x0e
89385035
MR
287};
288
e1f0d669
MR
289#define STAC92HD73XX_NUM_DMICS 2
290static hda_nid_t stac92hd73xx_dmic_nids[STAC92HD73XX_NUM_DMICS + 1] = {
291 0x13, 0x14, 0
292};
293
294#define STAC92HD73_DAC_COUNT 5
295static hda_nid_t stac92hd73xx_dac_nids[STAC92HD73_DAC_COUNT] = {
296 0x15, 0x16, 0x17, 0x18, 0x19,
297};
298
299static hda_nid_t stac92hd73xx_mux_nids[4] = {
300 0x28, 0x29, 0x2a, 0x2b,
301};
302
303static hda_nid_t stac92hd73xx_dmux_nids[2] = {
304 0x20, 0x21,
305};
306
d9737751
MR
307static hda_nid_t stac92hd73xx_smux_nids[2] = {
308 0x22, 0x23,
309};
310
d0513fc6
MR
311#define STAC92HD83XXX_NUM_DMICS 2
312static hda_nid_t stac92hd83xxx_dmic_nids[STAC92HD83XXX_NUM_DMICS + 1] = {
313 0x11, 0x12, 0
314};
315
316#define STAC92HD81_DAC_COUNT 2
317#define STAC92HD83_DAC_COUNT 3
318static hda_nid_t stac92hd83xxx_dac_nids[STAC92HD73_DAC_COUNT] = {
319 0x13, 0x14, 0x22,
320};
321
322static hda_nid_t stac92hd83xxx_dmux_nids[2] = {
323 0x17, 0x18,
324};
325
326static hda_nid_t stac92hd83xxx_adc_nids[2] = {
327 0x15, 0x16,
328};
329
330static hda_nid_t stac92hd83xxx_pwr_nids[4] = {
331 0xa, 0xb, 0xd, 0xe,
332};
333
0ffa9807
MR
334static hda_nid_t stac92hd83xxx_slave_dig_outs[2] = {
335 0x1e, 0,
336};
337
d0513fc6
MR
338static unsigned int stac92hd83xxx_pwr_mapping[4] = {
339 0x03, 0x0c, 0x10, 0x40,
340};
341
a64135a2
MR
342static hda_nid_t stac92hd71bxx_pwr_nids[3] = {
343 0x0a, 0x0d, 0x0f
344};
345
e035b841
MR
346static hda_nid_t stac92hd71bxx_adc_nids[2] = {
347 0x12, 0x13,
348};
349
350static hda_nid_t stac92hd71bxx_mux_nids[2] = {
351 0x1a, 0x1b
352};
353
4b33c767
MR
354static hda_nid_t stac92hd71bxx_dmux_nids[2] = {
355 0x1c, 0x1d,
e1f0d669
MR
356};
357
d9737751
MR
358static hda_nid_t stac92hd71bxx_smux_nids[2] = {
359 0x24, 0x25,
360};
361
aea7bb0a 362static hda_nid_t stac92hd71bxx_dac_nids[1] = {
e035b841
MR
363 0x10, /*0x11, */
364};
365
366#define STAC92HD71BXX_NUM_DMICS 2
367static hda_nid_t stac92hd71bxx_dmic_nids[STAC92HD71BXX_NUM_DMICS + 1] = {
368 0x18, 0x19, 0
369};
370
0ffa9807
MR
371static hda_nid_t stac92hd71bxx_slave_dig_outs[2] = {
372 0x22, 0
373};
374
8e21c34c
TD
375static hda_nid_t stac925x_adc_nids[1] = {
376 0x03,
377};
378
379static hda_nid_t stac925x_mux_nids[1] = {
380 0x0f,
381};
382
383static hda_nid_t stac925x_dac_nids[1] = {
384 0x02,
385};
386
f6e9852a
TI
387#define STAC925X_NUM_DMICS 1
388static hda_nid_t stac925x_dmic_nids[STAC925X_NUM_DMICS + 1] = {
389 0x15, 0
2c11f955
TD
390};
391
1697055e
TI
392static hda_nid_t stac925x_dmux_nids[1] = {
393 0x14,
394};
395
2f2f4251
M
396static hda_nid_t stac922x_adc_nids[2] = {
397 0x06, 0x07,
398};
399
400static hda_nid_t stac922x_mux_nids[2] = {
401 0x12, 0x13,
402};
403
3cc08dc6
MP
404static hda_nid_t stac927x_adc_nids[3] = {
405 0x07, 0x08, 0x09
406};
407
408static hda_nid_t stac927x_mux_nids[3] = {
409 0x15, 0x16, 0x17
410};
411
d9737751
MR
412static hda_nid_t stac927x_smux_nids[1] = {
413 0x21,
414};
415
b76c850f
MR
416static hda_nid_t stac927x_dac_nids[6] = {
417 0x02, 0x03, 0x04, 0x05, 0x06, 0
418};
419
e1f0d669
MR
420static hda_nid_t stac927x_dmux_nids[1] = {
421 0x1b,
422};
423
7f16859a
MR
424#define STAC927X_NUM_DMICS 2
425static hda_nid_t stac927x_dmic_nids[STAC927X_NUM_DMICS + 1] = {
426 0x13, 0x14, 0
427};
428
65973632
MR
429static const char *stac927x_spdif_labels[5] = {
430 "Digital Playback", "ADAT", "Analog Mux 1",
431 "Analog Mux 2", "Analog Mux 3"
432};
433
f3302a59
MP
434static hda_nid_t stac9205_adc_nids[2] = {
435 0x12, 0x13
436};
437
438static hda_nid_t stac9205_mux_nids[2] = {
439 0x19, 0x1a
440};
441
e1f0d669 442static hda_nid_t stac9205_dmux_nids[1] = {
1697055e 443 0x1d,
e1f0d669
MR
444};
445
d9737751
MR
446static hda_nid_t stac9205_smux_nids[1] = {
447 0x21,
448};
449
f6e9852a
TI
450#define STAC9205_NUM_DMICS 2
451static hda_nid_t stac9205_dmic_nids[STAC9205_NUM_DMICS + 1] = {
452 0x17, 0x18, 0
8b65727b
MP
453};
454
c7d4b2fa 455static hda_nid_t stac9200_pin_nids[8] = {
93ed1503
TD
456 0x08, 0x09, 0x0d, 0x0e,
457 0x0f, 0x10, 0x11, 0x12,
2f2f4251
M
458};
459
8e21c34c
TD
460static hda_nid_t stac925x_pin_nids[8] = {
461 0x07, 0x08, 0x0a, 0x0b,
462 0x0c, 0x0d, 0x10, 0x11,
463};
464
2f2f4251
M
465static hda_nid_t stac922x_pin_nids[10] = {
466 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
467 0x0f, 0x10, 0x11, 0x15, 0x1b,
468};
469
a7662640 470static hda_nid_t stac92hd73xx_pin_nids[13] = {
e1f0d669
MR
471 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
472 0x0f, 0x10, 0x11, 0x12, 0x13,
d9737751 473 0x14, 0x22, 0x23
e1f0d669
MR
474};
475
d0513fc6
MR
476static hda_nid_t stac92hd83xxx_pin_nids[14] = {
477 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
478 0x0f, 0x10, 0x11, 0x12, 0x13,
479 0x1d, 0x1e, 0x1f, 0x20
480};
0ffa9807 481static hda_nid_t stac92hd71bxx_pin_nids[11] = {
e035b841
MR
482 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
483 0x0f, 0x14, 0x18, 0x19, 0x1e,
0ffa9807 484 0x1f,
e035b841
MR
485};
486
3cc08dc6
MP
487static hda_nid_t stac927x_pin_nids[14] = {
488 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
489 0x0f, 0x10, 0x11, 0x12, 0x13,
490 0x14, 0x21, 0x22, 0x23,
491};
492
f3302a59
MP
493static hda_nid_t stac9205_pin_nids[12] = {
494 0x0a, 0x0b, 0x0c, 0x0d, 0x0e,
495 0x0f, 0x14, 0x16, 0x17, 0x18,
496 0x21, 0x22,
f3302a59
MP
497};
498
89385035
MR
499#define stac92xx_amp_volume_info snd_hda_mixer_amp_volume_info
500
501static int stac92xx_amp_volume_get(struct snd_kcontrol *kcontrol,
502 struct snd_ctl_elem_value *ucontrol)
503{
504 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
505 struct sigmatel_spec *spec = codec->spec;
506 hda_nid_t nid = spec->amp_nids[spec->cur_amux];
507
508 kcontrol->private_value ^= get_amp_nid(kcontrol);
509 kcontrol->private_value |= nid;
510
511 return snd_hda_mixer_amp_volume_get(kcontrol, ucontrol);
512}
513
514static int stac92xx_amp_volume_put(struct snd_kcontrol *kcontrol,
515 struct snd_ctl_elem_value *ucontrol)
516{
517 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
518 struct sigmatel_spec *spec = codec->spec;
519 hda_nid_t nid = spec->amp_nids[spec->cur_amux];
520
521 kcontrol->private_value ^= get_amp_nid(kcontrol);
522 kcontrol->private_value |= nid;
523
524 return snd_hda_mixer_amp_volume_put(kcontrol, ucontrol);
525}
526
8b65727b
MP
527static int stac92xx_dmux_enum_info(struct snd_kcontrol *kcontrol,
528 struct snd_ctl_elem_info *uinfo)
529{
530 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
531 struct sigmatel_spec *spec = codec->spec;
532 return snd_hda_input_mux_info(spec->dinput_mux, uinfo);
533}
534
535static int stac92xx_dmux_enum_get(struct snd_kcontrol *kcontrol,
536 struct snd_ctl_elem_value *ucontrol)
537{
538 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
539 struct sigmatel_spec *spec = codec->spec;
e1f0d669 540 unsigned int dmux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
8b65727b 541
e1f0d669 542 ucontrol->value.enumerated.item[0] = spec->cur_dmux[dmux_idx];
8b65727b
MP
543 return 0;
544}
545
546static int stac92xx_dmux_enum_put(struct snd_kcontrol *kcontrol,
547 struct snd_ctl_elem_value *ucontrol)
548{
549 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
550 struct sigmatel_spec *spec = codec->spec;
e1f0d669 551 unsigned int dmux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
8b65727b
MP
552
553 return snd_hda_input_mux_put(codec, spec->dinput_mux, ucontrol,
e1f0d669 554 spec->dmux_nids[dmux_idx], &spec->cur_dmux[dmux_idx]);
8b65727b
MP
555}
556
d9737751
MR
557static int stac92xx_smux_enum_info(struct snd_kcontrol *kcontrol,
558 struct snd_ctl_elem_info *uinfo)
559{
560 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
561 struct sigmatel_spec *spec = codec->spec;
562 return snd_hda_input_mux_info(spec->sinput_mux, uinfo);
563}
564
565static int stac92xx_smux_enum_get(struct snd_kcontrol *kcontrol,
566 struct snd_ctl_elem_value *ucontrol)
567{
568 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
569 struct sigmatel_spec *spec = codec->spec;
570 unsigned int smux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
571
572 ucontrol->value.enumerated.item[0] = spec->cur_smux[smux_idx];
573 return 0;
574}
575
576static int stac92xx_smux_enum_put(struct snd_kcontrol *kcontrol,
577 struct snd_ctl_elem_value *ucontrol)
578{
579 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
580 struct sigmatel_spec *spec = codec->spec;
00ef50c2 581 struct hda_input_mux *smux = &spec->private_smux;
d9737751 582 unsigned int smux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
00ef50c2
MR
583 int err, val;
584 hda_nid_t nid;
d9737751 585
00ef50c2 586 err = snd_hda_input_mux_put(codec, spec->sinput_mux, ucontrol,
d9737751 587 spec->smux_nids[smux_idx], &spec->cur_smux[smux_idx]);
00ef50c2
MR
588 if (err < 0)
589 return err;
590
591 if (spec->spdif_mute) {
592 if (smux_idx == 0)
593 nid = spec->multiout.dig_out_nid;
594 else
595 nid = codec->slave_dig_outs[smux_idx - 1];
596 if (spec->cur_smux[smux_idx] == smux->num_items - 1)
597 val = AMP_OUT_MUTE;
00ef50c2 598 else
c1e99bd9 599 val = AMP_OUT_UNMUTE;
00ef50c2
MR
600 /* un/mute SPDIF out */
601 snd_hda_codec_write_cache(codec, nid, 0,
602 AC_VERB_SET_AMP_GAIN_MUTE, val);
603 }
604 return 0;
d9737751
MR
605}
606
c8b6bf9b 607static int stac92xx_mux_enum_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
2f2f4251
M
608{
609 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
610 struct sigmatel_spec *spec = codec->spec;
c7d4b2fa 611 return snd_hda_input_mux_info(spec->input_mux, uinfo);
2f2f4251
M
612}
613
c8b6bf9b 614static int stac92xx_mux_enum_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
2f2f4251
M
615{
616 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
617 struct sigmatel_spec *spec = codec->spec;
618 unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
619
620 ucontrol->value.enumerated.item[0] = spec->cur_mux[adc_idx];
621 return 0;
622}
623
c8b6bf9b 624static int stac92xx_mux_enum_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
2f2f4251
M
625{
626 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
627 struct sigmatel_spec *spec = codec->spec;
628 unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
629
c7d4b2fa 630 return snd_hda_input_mux_put(codec, spec->input_mux, ucontrol,
2f2f4251
M
631 spec->mux_nids[adc_idx], &spec->cur_mux[adc_idx]);
632}
633
b22b4821
MR
634static int stac92xx_mono_mux_enum_info(struct snd_kcontrol *kcontrol,
635 struct snd_ctl_elem_info *uinfo)
636{
637 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
638 struct sigmatel_spec *spec = codec->spec;
639 return snd_hda_input_mux_info(spec->mono_mux, uinfo);
640}
641
642static int stac92xx_mono_mux_enum_get(struct snd_kcontrol *kcontrol,
643 struct snd_ctl_elem_value *ucontrol)
644{
645 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
646 struct sigmatel_spec *spec = codec->spec;
647
648 ucontrol->value.enumerated.item[0] = spec->cur_mmux;
649 return 0;
650}
651
652static int stac92xx_mono_mux_enum_put(struct snd_kcontrol *kcontrol,
653 struct snd_ctl_elem_value *ucontrol)
654{
655 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
656 struct sigmatel_spec *spec = codec->spec;
657
658 return snd_hda_input_mux_put(codec, spec->mono_mux, ucontrol,
659 spec->mono_nid, &spec->cur_mmux);
660}
661
89385035
MR
662static int stac92xx_amp_mux_enum_info(struct snd_kcontrol *kcontrol,
663 struct snd_ctl_elem_info *uinfo)
664{
665 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
666 struct sigmatel_spec *spec = codec->spec;
667 return snd_hda_input_mux_info(spec->amp_mux, uinfo);
668}
669
670static int stac92xx_amp_mux_enum_get(struct snd_kcontrol *kcontrol,
671 struct snd_ctl_elem_value *ucontrol)
672{
673 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
674 struct sigmatel_spec *spec = codec->spec;
675
676 ucontrol->value.enumerated.item[0] = spec->cur_amux;
677 return 0;
678}
679
680static int stac92xx_amp_mux_enum_put(struct snd_kcontrol *kcontrol,
681 struct snd_ctl_elem_value *ucontrol)
682{
683 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
684 struct sigmatel_spec *spec = codec->spec;
685 struct snd_kcontrol *ctl =
686 snd_hda_find_mixer_ctl(codec, "Amp Capture Volume");
687 if (!ctl)
688 return -EINVAL;
689
690 snd_ctl_notify(codec->bus->card, SNDRV_CTL_EVENT_MASK_VALUE |
691 SNDRV_CTL_EVENT_MASK_INFO, &ctl->id);
692
693 return snd_hda_input_mux_put(codec, spec->amp_mux, ucontrol,
694 0, &spec->cur_amux);
695}
696
5f10c4a9
ML
697#define stac92xx_aloopback_info snd_ctl_boolean_mono_info
698
699static int stac92xx_aloopback_get(struct snd_kcontrol *kcontrol,
700 struct snd_ctl_elem_value *ucontrol)
701{
702 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
e1f0d669 703 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
5f10c4a9
ML
704 struct sigmatel_spec *spec = codec->spec;
705
e1f0d669
MR
706 ucontrol->value.integer.value[0] = !!(spec->aloopback &
707 (spec->aloopback_mask << idx));
5f10c4a9
ML
708 return 0;
709}
710
711static int stac92xx_aloopback_put(struct snd_kcontrol *kcontrol,
712 struct snd_ctl_elem_value *ucontrol)
713{
714 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
715 struct sigmatel_spec *spec = codec->spec;
e1f0d669 716 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
5f10c4a9 717 unsigned int dac_mode;
e1f0d669 718 unsigned int val, idx_val;
5f10c4a9 719
e1f0d669
MR
720 idx_val = spec->aloopback_mask << idx;
721 if (ucontrol->value.integer.value[0])
722 val = spec->aloopback | idx_val;
723 else
724 val = spec->aloopback & ~idx_val;
68ea7b2f 725 if (spec->aloopback == val)
5f10c4a9
ML
726 return 0;
727
68ea7b2f 728 spec->aloopback = val;
5f10c4a9 729
e1f0d669
MR
730 /* Only return the bits defined by the shift value of the
731 * first two bytes of the mask
732 */
5f10c4a9 733 dac_mode = snd_hda_codec_read(codec, codec->afg, 0,
e1f0d669
MR
734 kcontrol->private_value & 0xFFFF, 0x0);
735 dac_mode >>= spec->aloopback_shift;
5f10c4a9 736
e1f0d669 737 if (spec->aloopback & idx_val) {
5f10c4a9 738 snd_hda_power_up(codec);
e1f0d669 739 dac_mode |= idx_val;
5f10c4a9
ML
740 } else {
741 snd_hda_power_down(codec);
e1f0d669 742 dac_mode &= ~idx_val;
5f10c4a9
ML
743 }
744
745 snd_hda_codec_write_cache(codec, codec->afg, 0,
746 kcontrol->private_value >> 16, dac_mode);
747
748 return 1;
749}
750
c7d4b2fa 751static struct hda_verb stac9200_core_init[] = {
2f2f4251 752 /* set dac0mux for dac converter */
c7d4b2fa 753 { 0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
2f2f4251
M
754 {}
755};
756
1194b5b7
TI
757static struct hda_verb stac9200_eapd_init[] = {
758 /* set dac0mux for dac converter */
759 {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
760 {0x08, AC_VERB_SET_EAPD_BTLENABLE, 0x02},
761 {}
762};
763
e1f0d669
MR
764static struct hda_verb stac92hd73xx_6ch_core_init[] = {
765 /* set master volume and direct control */
766 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
767 /* setup audio connections */
768 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x00},
769 { 0x10, AC_VERB_SET_CONNECT_SEL, 0x01},
770 { 0x11, AC_VERB_SET_CONNECT_SEL, 0x02},
771 /* setup adcs to point to mixer */
772 { 0x20, AC_VERB_SET_CONNECT_SEL, 0x0b},
773 { 0x21, AC_VERB_SET_CONNECT_SEL, 0x0b},
e1f0d669
MR
774 { 0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
775 { 0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
776 { 0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
777 /* setup import muxs */
778 { 0x28, AC_VERB_SET_CONNECT_SEL, 0x01},
779 { 0x29, AC_VERB_SET_CONNECT_SEL, 0x01},
780 { 0x2a, AC_VERB_SET_CONNECT_SEL, 0x01},
781 { 0x2b, AC_VERB_SET_CONNECT_SEL, 0x00},
782 {}
783};
784
d654a660
MR
785static struct hda_verb dell_eq_core_init[] = {
786 /* set master volume to max value without distortion
787 * and direct control */
788 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xec},
789 /* setup audio connections */
790 { 0x0d, AC_VERB_SET_CONNECT_SEL, 0x00},
f7cf0a7c
MR
791 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x02},
792 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x01},
d654a660
MR
793 /* setup adcs to point to mixer */
794 { 0x20, AC_VERB_SET_CONNECT_SEL, 0x0b},
795 { 0x21, AC_VERB_SET_CONNECT_SEL, 0x0b},
796 /* setup import muxs */
797 { 0x28, AC_VERB_SET_CONNECT_SEL, 0x01},
798 { 0x29, AC_VERB_SET_CONNECT_SEL, 0x01},
799 { 0x2a, AC_VERB_SET_CONNECT_SEL, 0x01},
800 { 0x2b, AC_VERB_SET_CONNECT_SEL, 0x00},
801 {}
802};
803
52fe0f9d 804static struct hda_verb dell_m6_core_init[] = {
6b3ab21e 805 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
52fe0f9d 806 /* setup audio connections */
7747ecce
MR
807 { 0x0d, AC_VERB_SET_CONNECT_SEL, 0x00},
808 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x01},
52fe0f9d
MR
809 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x02},
810 /* setup adcs to point to mixer */
811 { 0x20, AC_VERB_SET_CONNECT_SEL, 0x0b},
812 { 0x21, AC_VERB_SET_CONNECT_SEL, 0x0b},
813 /* setup import muxs */
814 { 0x28, AC_VERB_SET_CONNECT_SEL, 0x01},
815 { 0x29, AC_VERB_SET_CONNECT_SEL, 0x01},
816 { 0x2a, AC_VERB_SET_CONNECT_SEL, 0x01},
817 { 0x2b, AC_VERB_SET_CONNECT_SEL, 0x00},
818 {}
819};
820
e1f0d669
MR
821static struct hda_verb stac92hd73xx_8ch_core_init[] = {
822 /* set master volume and direct control */
823 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
824 /* setup audio connections */
825 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x00},
826 { 0x10, AC_VERB_SET_CONNECT_SEL, 0x01},
827 { 0x11, AC_VERB_SET_CONNECT_SEL, 0x02},
828 /* connect hp ports to dac3 */
829 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x03},
830 { 0x0d, AC_VERB_SET_CONNECT_SEL, 0x03},
831 /* setup adcs to point to mixer */
832 { 0x20, AC_VERB_SET_CONNECT_SEL, 0x0b},
833 { 0x21, AC_VERB_SET_CONNECT_SEL, 0x0b},
e1f0d669
MR
834 { 0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
835 { 0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
836 { 0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
837 /* setup import muxs */
838 { 0x28, AC_VERB_SET_CONNECT_SEL, 0x01},
839 { 0x29, AC_VERB_SET_CONNECT_SEL, 0x01},
840 { 0x2a, AC_VERB_SET_CONNECT_SEL, 0x01},
841 { 0x2b, AC_VERB_SET_CONNECT_SEL, 0x03},
842 {}
843};
844
845static struct hda_verb stac92hd73xx_10ch_core_init[] = {
846 /* set master volume and direct control */
847 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
848 /* setup audio connections */
849 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x00 },
850 { 0x10, AC_VERB_SET_CONNECT_SEL, 0x01 },
851 { 0x11, AC_VERB_SET_CONNECT_SEL, 0x02 },
852 /* dac3 is connected to import3 mux */
853 { 0x18, AC_VERB_SET_AMP_GAIN_MUTE, 0xb07f},
854 /* connect hp ports to dac4 */
855 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x04},
856 { 0x0d, AC_VERB_SET_CONNECT_SEL, 0x04},
857 /* setup adcs to point to mixer */
858 { 0x20, AC_VERB_SET_CONNECT_SEL, 0x0b},
859 { 0x21, AC_VERB_SET_CONNECT_SEL, 0x0b},
e1f0d669
MR
860 { 0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
861 { 0x10, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
862 { 0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT},
863 /* setup import muxs */
864 { 0x28, AC_VERB_SET_CONNECT_SEL, 0x01},
865 { 0x29, AC_VERB_SET_CONNECT_SEL, 0x01},
866 { 0x2a, AC_VERB_SET_CONNECT_SEL, 0x01},
867 { 0x2b, AC_VERB_SET_CONNECT_SEL, 0x03},
868 {}
869};
870
d0513fc6
MR
871static struct hda_verb stac92hd83xxx_core_init[] = {
872 /* start of config #1 */
873 { 0xe, AC_VERB_SET_CONNECT_SEL, 0x3},
874
875 /* start of config #2 */
876 { 0xa, AC_VERB_SET_CONNECT_SEL, 0x0},
877 { 0xb, AC_VERB_SET_CONNECT_SEL, 0x0},
878 { 0xd, AC_VERB_SET_CONNECT_SEL, 0x1},
879
880 /* power state controls amps */
881 { 0x01, AC_VERB_SET_EAPD, 1 << 2},
882};
883
e035b841 884static struct hda_verb stac92hd71bxx_core_init[] = {
541eee87
MR
885 /* set master volume and direct control */
886 { 0x28, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
887 /* connect headphone jack to dac1 */
888 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x01},
541eee87
MR
889 /* unmute right and left channels for nodes 0x0a, 0xd, 0x0f */
890 { 0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
891 { 0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
892 { 0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
541eee87
MR
893};
894
4b33c767 895#define HD_DISABLE_PORTF 2
541eee87 896static struct hda_verb stac92hd71bxx_analog_core_init[] = {
aafc4412
MR
897 /* start of config #1 */
898
899 /* connect port 0f to audio mixer */
900 { 0x0f, AC_VERB_SET_CONNECT_SEL, 0x2},
aafc4412
MR
901 /* unmute right and left channels for node 0x0f */
902 { 0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
903 /* start of config #2 */
904
e035b841
MR
905 /* set master volume and direct control */
906 { 0x28, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
907 /* connect headphone jack to dac1 */
908 { 0x0a, AC_VERB_SET_CONNECT_SEL, 0x01},
aafc4412 909 /* unmute right and left channels for nodes 0x0a, 0xd */
e035b841
MR
910 { 0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
911 { 0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
e035b841
MR
912 {}
913};
914
8e21c34c
TD
915static struct hda_verb stac925x_core_init[] = {
916 /* set dac0mux for dac converter */
917 { 0x06, AC_VERB_SET_CONNECT_SEL, 0x00},
918 {}
919};
920
c7d4b2fa 921static struct hda_verb stac922x_core_init[] = {
2f2f4251 922 /* set master volume and direct control */
c7d4b2fa 923 { 0x16, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
2f2f4251
M
924 {}
925};
926
93ed1503 927static struct hda_verb d965_core_init[] = {
19039bd0 928 /* set master volume and direct control */
93ed1503 929 { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
19039bd0
TI
930 /* unmute node 0x1b */
931 { 0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
932 /* select node 0x03 as DAC */
933 { 0x0b, AC_VERB_SET_CONNECT_SEL, 0x01},
934 {}
935};
936
3cc08dc6
MP
937static struct hda_verb stac927x_core_init[] = {
938 /* set master volume and direct control */
939 { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
1cd2224c
MR
940 /* enable analog pc beep path */
941 { 0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5},
3cc08dc6
MP
942 {}
943};
944
f3302a59
MP
945static struct hda_verb stac9205_core_init[] = {
946 /* set master volume and direct control */
947 { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
d0513fc6
MR
948 /* enable analog pc beep path */
949 { 0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5},
f3302a59
MP
950 {}
951};
952
b22b4821
MR
953#define STAC_MONO_MUX \
954 { \
955 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
956 .name = "Mono Mux", \
957 .count = 1, \
958 .info = stac92xx_mono_mux_enum_info, \
959 .get = stac92xx_mono_mux_enum_get, \
960 .put = stac92xx_mono_mux_enum_put, \
961 }
962
89385035
MR
963#define STAC_AMP_MUX \
964 { \
965 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
966 .name = "Amp Selector Capture Switch", \
967 .count = 1, \
968 .info = stac92xx_amp_mux_enum_info, \
969 .get = stac92xx_amp_mux_enum_get, \
970 .put = stac92xx_amp_mux_enum_put, \
971 }
972
973#define STAC_AMP_VOL(xname, nid, chs, idx, dir) \
974 { \
975 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
976 .name = xname, \
977 .index = 0, \
978 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \
979 SNDRV_CTL_ELEM_ACCESS_TLV_READ | \
980 SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK, \
981 .info = stac92xx_amp_volume_info, \
982 .get = stac92xx_amp_volume_get, \
983 .put = stac92xx_amp_volume_put, \
984 .tlv = { .c = snd_hda_mixer_amp_tlv }, \
985 .private_value = HDA_COMPOSE_AMP_VAL(nid, chs, idx, dir) \
986 }
987
9e05b7a3 988#define STAC_INPUT_SOURCE(cnt) \
ca7c5a8b
ML
989 { \
990 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
991 .name = "Input Source", \
9e05b7a3 992 .count = cnt, \
ca7c5a8b
ML
993 .info = stac92xx_mux_enum_info, \
994 .get = stac92xx_mux_enum_get, \
995 .put = stac92xx_mux_enum_put, \
996 }
997
e1f0d669 998#define STAC_ANALOG_LOOPBACK(verb_read, verb_write, cnt) \
5f10c4a9
ML
999 { \
1000 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
1001 .name = "Analog Loopback", \
e1f0d669 1002 .count = cnt, \
5f10c4a9
ML
1003 .info = stac92xx_aloopback_info, \
1004 .get = stac92xx_aloopback_get, \
1005 .put = stac92xx_aloopback_put, \
1006 .private_value = verb_read | (verb_write << 16), \
1007 }
1008
c8b6bf9b 1009static struct snd_kcontrol_new stac9200_mixer[] = {
2f2f4251
M
1010 HDA_CODEC_VOLUME("Master Playback Volume", 0xb, 0, HDA_OUTPUT),
1011 HDA_CODEC_MUTE("Master Playback Switch", 0xb, 0, HDA_OUTPUT),
9e05b7a3 1012 STAC_INPUT_SOURCE(1),
2f2f4251
M
1013 HDA_CODEC_VOLUME("Capture Volume", 0x0a, 0, HDA_OUTPUT),
1014 HDA_CODEC_MUTE("Capture Switch", 0x0a, 0, HDA_OUTPUT),
2f2f4251
M
1015 { } /* end */
1016};
1017
2a9c7816 1018#define DELL_M6_MIXER 6
e1f0d669 1019static struct snd_kcontrol_new stac92hd73xx_6ch_mixer[] = {
2a9c7816 1020 /* start of config #1 */
e1f0d669
MR
1021 HDA_CODEC_VOLUME("Front Mic Mixer Capture Volume", 0x1d, 0, HDA_INPUT),
1022 HDA_CODEC_MUTE("Front Mic Mixer Capture Switch", 0x1d, 0, HDA_INPUT),
1023
e1f0d669
MR
1024 HDA_CODEC_VOLUME("Line In Mixer Capture Volume", 0x1d, 0x2, HDA_INPUT),
1025 HDA_CODEC_MUTE("Line In Mixer Capture Switch", 0x1d, 0x2, HDA_INPUT),
1026
2a9c7816
MR
1027 HDA_CODEC_VOLUME("CD Mixer Capture Volume", 0x1d, 0x4, HDA_INPUT),
1028 HDA_CODEC_MUTE("CD Mixer Capture Switch", 0x1d, 0x4, HDA_INPUT),
1029
1030 /* start of config #2 */
1031 HDA_CODEC_VOLUME("Mic Mixer Capture Volume", 0x1d, 0x1, HDA_INPUT),
1032 HDA_CODEC_MUTE("Mic Mixer Capture Switch", 0x1d, 0x1, HDA_INPUT),
1033
e1f0d669
MR
1034 HDA_CODEC_VOLUME("DAC Mixer Capture Volume", 0x1d, 0x3, HDA_INPUT),
1035 HDA_CODEC_MUTE("DAC Mixer Capture Switch", 0x1d, 0x3, HDA_INPUT),
1036
2a9c7816
MR
1037 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 3),
1038
1039 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x20, 0x0, HDA_OUTPUT),
1040 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x20, 0x0, HDA_OUTPUT),
1041
1042 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x21, 0x0, HDA_OUTPUT),
1043 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x21, 0x0, HDA_OUTPUT),
1044
e1f0d669
MR
1045 { } /* end */
1046};
1047
1048static struct snd_kcontrol_new stac92hd73xx_8ch_mixer[] = {
e1f0d669
MR
1049 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 4),
1050
e1f0d669
MR
1051 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x20, 0x0, HDA_OUTPUT),
1052 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x20, 0x0, HDA_OUTPUT),
1053
1054 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x21, 0x0, HDA_OUTPUT),
1055 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x21, 0x0, HDA_OUTPUT),
1056
1057 HDA_CODEC_VOLUME("Front Mic Mixer Capture Volume", 0x1d, 0, HDA_INPUT),
1058 HDA_CODEC_MUTE("Front Mic Mixer Capture Switch", 0x1d, 0, HDA_INPUT),
1059
1060 HDA_CODEC_VOLUME("Mic Mixer Capture Volume", 0x1d, 0x1, HDA_INPUT),
1061 HDA_CODEC_MUTE("Mic Mixer Capture Switch", 0x1d, 0x1, HDA_INPUT),
1062
1063 HDA_CODEC_VOLUME("Line In Mixer Capture Volume", 0x1d, 0x2, HDA_INPUT),
1064 HDA_CODEC_MUTE("Line In Mixer Capture Switch", 0x1d, 0x2, HDA_INPUT),
1065
1066 HDA_CODEC_VOLUME("DAC Mixer Capture Volume", 0x1d, 0x3, HDA_INPUT),
1067 HDA_CODEC_MUTE("DAC Mixer Capture Switch", 0x1d, 0x3, HDA_INPUT),
1068
1069 HDA_CODEC_VOLUME("CD Mixer Capture Volume", 0x1d, 0x4, HDA_INPUT),
1070 HDA_CODEC_MUTE("CD Mixer Capture Switch", 0x1d, 0x4, HDA_INPUT),
1071 { } /* end */
1072};
1073
1074static struct snd_kcontrol_new stac92hd73xx_10ch_mixer[] = {
e1f0d669
MR
1075 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 5),
1076
e1f0d669
MR
1077 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x20, 0x0, HDA_OUTPUT),
1078 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x20, 0x0, HDA_OUTPUT),
1079
1080 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x21, 0x0, HDA_OUTPUT),
1081 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x21, 0x0, HDA_OUTPUT),
1082
1083 HDA_CODEC_VOLUME("Front Mic Mixer Capture Volume", 0x1d, 0, HDA_INPUT),
1084 HDA_CODEC_MUTE("Front Mic Mixer Capture Switch", 0x1d, 0, HDA_INPUT),
1085
1086 HDA_CODEC_VOLUME("Mic Mixer Capture Volume", 0x1d, 0x1, HDA_INPUT),
1087 HDA_CODEC_MUTE("Mic Mixer Capture Switch", 0x1d, 0x1, HDA_INPUT),
1088
1089 HDA_CODEC_VOLUME("Line In Mixer Capture Volume", 0x1d, 0x2, HDA_INPUT),
1090 HDA_CODEC_MUTE("Line In Mixer Capture Switch", 0x1d, 0x2, HDA_INPUT),
1091
1092 HDA_CODEC_VOLUME("DAC Mixer Capture Volume", 0x1d, 0x3, HDA_INPUT),
1093 HDA_CODEC_MUTE("DAC Mixer Capture Switch", 0x1d, 0x3, HDA_INPUT),
1094
1095 HDA_CODEC_VOLUME("CD Mixer Capture Volume", 0x1d, 0x4, HDA_INPUT),
1096 HDA_CODEC_MUTE("CD Mixer Capture Switch", 0x1d, 0x4, HDA_INPUT),
1097 { } /* end */
1098};
1099
d0513fc6
MR
1100
1101static struct snd_kcontrol_new stac92hd83xxx_mixer[] = {
1102 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x17, 0x0, HDA_OUTPUT),
1103 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x17, 0x0, HDA_OUTPUT),
1104
1105 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x18, 0x0, HDA_OUTPUT),
1106 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x18, 0x0, HDA_OUTPUT),
1107
1108 HDA_CODEC_VOLUME("DAC0 Capture Volume", 0x1b, 0, HDA_INPUT),
1109 HDA_CODEC_MUTE("DAC0 Capture Switch", 0x1b, 0, HDA_INPUT),
1110
1111 HDA_CODEC_VOLUME("DAC1 Capture Volume", 0x1b, 0x1, HDA_INPUT),
1112 HDA_CODEC_MUTE("DAC1 Capture Switch", 0x1b, 0x1, HDA_INPUT),
1113
1114 HDA_CODEC_VOLUME("Front Mic Capture Volume", 0x1b, 0x2, HDA_INPUT),
1115 HDA_CODEC_MUTE("Front Mic Capture Switch", 0x1b, 0x2, HDA_INPUT),
1116
1117 HDA_CODEC_VOLUME("Line In Capture Volume", 0x1b, 0x3, HDA_INPUT),
1118 HDA_CODEC_MUTE("Line In Capture Switch", 0x1b, 0x3, HDA_INPUT),
1119
1120 /*
1121 HDA_CODEC_VOLUME("Mic Capture Volume", 0x1b, 0x4, HDA_INPUT),
1122 HDA_CODEC_MUTE("Mic Capture Switch", 0x1b 0x4, HDA_INPUT),
1123 */
1124 { } /* end */
1125};
1126
541eee87 1127static struct snd_kcontrol_new stac92hd71bxx_analog_mixer[] = {
e035b841 1128 STAC_INPUT_SOURCE(2),
4b33c767 1129 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A0, 2),
e035b841 1130
9b35947f
MR
1131 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x1c, 0x0, HDA_OUTPUT),
1132 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x1c, 0x0, HDA_OUTPUT),
9b35947f
MR
1133
1134 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x1d, 0x0, HDA_OUTPUT),
1135 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x1d, 0x0, HDA_OUTPUT),
1cd2224c
MR
1136 /* analog pc-beep replaced with digital beep support */
1137 /*
f7c5dda2
MR
1138 HDA_CODEC_VOLUME("PC Beep Volume", 0x17, 0x2, HDA_INPUT),
1139 HDA_CODEC_MUTE("PC Beep Switch", 0x17, 0x2, HDA_INPUT),
1cd2224c 1140 */
f7c5dda2 1141
687cb98e
MR
1142 HDA_CODEC_MUTE("Import0 Mux Capture Switch", 0x17, 0x0, HDA_INPUT),
1143 HDA_CODEC_VOLUME("Import0 Mux Capture Volume", 0x17, 0x0, HDA_INPUT),
4b33c767 1144
687cb98e
MR
1145 HDA_CODEC_MUTE("Import1 Mux Capture Switch", 0x17, 0x1, HDA_INPUT),
1146 HDA_CODEC_VOLUME("Import1 Mux Capture Volume", 0x17, 0x1, HDA_INPUT),
4b33c767
MR
1147
1148 HDA_CODEC_MUTE("DAC0 Capture Switch", 0x17, 0x3, HDA_INPUT),
1149 HDA_CODEC_VOLUME("DAC0 Capture Volume", 0x17, 0x3, HDA_INPUT),
1150
1151 HDA_CODEC_MUTE("DAC1 Capture Switch", 0x17, 0x4, HDA_INPUT),
1152 HDA_CODEC_VOLUME("DAC1 Capture Volume", 0x17, 0x4, HDA_INPUT),
e035b841
MR
1153 { } /* end */
1154};
1155
541eee87 1156static struct snd_kcontrol_new stac92hd71bxx_mixer[] = {
541eee87
MR
1157 STAC_INPUT_SOURCE(2),
1158 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A0, 2),
1159
541eee87
MR
1160 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x1c, 0x0, HDA_OUTPUT),
1161 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x1c, 0x0, HDA_OUTPUT),
541eee87
MR
1162
1163 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x1d, 0x0, HDA_OUTPUT),
1164 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x1d, 0x0, HDA_OUTPUT),
541eee87
MR
1165 { } /* end */
1166};
1167
8e21c34c 1168static struct snd_kcontrol_new stac925x_mixer[] = {
9e05b7a3 1169 STAC_INPUT_SOURCE(1),
8e21c34c 1170 HDA_CODEC_VOLUME("Capture Volume", 0x09, 0, HDA_OUTPUT),
587755f1 1171 HDA_CODEC_MUTE("Capture Switch", 0x14, 0, HDA_OUTPUT),
8e21c34c
TD
1172 { } /* end */
1173};
1174
9e05b7a3 1175static struct snd_kcontrol_new stac9205_mixer[] = {
9e05b7a3 1176 STAC_INPUT_SOURCE(2),
e1f0d669 1177 STAC_ANALOG_LOOPBACK(0xFE0, 0x7E0, 1),
9e05b7a3
ML
1178
1179 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x1b, 0x0, HDA_INPUT),
1180 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x1d, 0x0, HDA_OUTPUT),
9e05b7a3
ML
1181
1182 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x1c, 0x0, HDA_INPUT),
1183 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x1e, 0x0, HDA_OUTPUT),
2f2f4251
M
1184 { } /* end */
1185};
1186
19039bd0 1187/* This needs to be generated dynamically based on sequence */
9e05b7a3
ML
1188static struct snd_kcontrol_new stac922x_mixer[] = {
1189 STAC_INPUT_SOURCE(2),
9e05b7a3
ML
1190 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x17, 0x0, HDA_INPUT),
1191 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x17, 0x0, HDA_INPUT),
9e05b7a3
ML
1192
1193 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x18, 0x0, HDA_INPUT),
1194 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x18, 0x0, HDA_INPUT),
19039bd0
TI
1195 { } /* end */
1196};
1197
9e05b7a3 1198
d1d985f0 1199static struct snd_kcontrol_new stac927x_mixer[] = {
9e05b7a3 1200 STAC_INPUT_SOURCE(3),
e1f0d669 1201 STAC_ANALOG_LOOPBACK(0xFEB, 0x7EB, 1),
3cc08dc6 1202
9e05b7a3
ML
1203 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x0, 0x18, 0x0, HDA_INPUT),
1204 HDA_CODEC_MUTE_IDX("Capture Switch", 0x0, 0x1b, 0x0, HDA_OUTPUT),
9e05b7a3
ML
1205
1206 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x1, 0x19, 0x0, HDA_INPUT),
1207 HDA_CODEC_MUTE_IDX("Capture Switch", 0x1, 0x1c, 0x0, HDA_OUTPUT),
9e05b7a3
ML
1208
1209 HDA_CODEC_VOLUME_IDX("Capture Volume", 0x2, 0x1A, 0x0, HDA_INPUT),
1210 HDA_CODEC_MUTE_IDX("Capture Switch", 0x2, 0x1d, 0x0, HDA_OUTPUT),
f3302a59
MP
1211 { } /* end */
1212};
1213
1697055e
TI
1214static struct snd_kcontrol_new stac_dmux_mixer = {
1215 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1216 .name = "Digital Input Source",
1217 /* count set later */
1218 .info = stac92xx_dmux_enum_info,
1219 .get = stac92xx_dmux_enum_get,
1220 .put = stac92xx_dmux_enum_put,
1221};
1222
d9737751
MR
1223static struct snd_kcontrol_new stac_smux_mixer = {
1224 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
e3487970 1225 .name = "IEC958 Playback Source",
d9737751
MR
1226 /* count set later */
1227 .info = stac92xx_smux_enum_info,
1228 .get = stac92xx_smux_enum_get,
1229 .put = stac92xx_smux_enum_put,
1230};
1231
2134ea4f
TI
1232static const char *slave_vols[] = {
1233 "Front Playback Volume",
1234 "Surround Playback Volume",
1235 "Center Playback Volume",
1236 "LFE Playback Volume",
1237 "Side Playback Volume",
1238 "Headphone Playback Volume",
1239 "Headphone Playback Volume",
1240 "Speaker Playback Volume",
1241 "External Speaker Playback Volume",
1242 "Speaker2 Playback Volume",
1243 NULL
1244};
1245
1246static const char *slave_sws[] = {
1247 "Front Playback Switch",
1248 "Surround Playback Switch",
1249 "Center Playback Switch",
1250 "LFE Playback Switch",
1251 "Side Playback Switch",
1252 "Headphone Playback Switch",
1253 "Headphone Playback Switch",
1254 "Speaker Playback Switch",
1255 "External Speaker Playback Switch",
1256 "Speaker2 Playback Switch",
edb54a55 1257 "IEC958 Playback Switch",
2134ea4f
TI
1258 NULL
1259};
1260
603c4019 1261static void stac92xx_free_kctls(struct hda_codec *codec);
e4973e1e 1262static int stac92xx_add_jack(struct hda_codec *codec, hda_nid_t nid, int type);
603c4019 1263
2f2f4251
M
1264static int stac92xx_build_controls(struct hda_codec *codec)
1265{
1266 struct sigmatel_spec *spec = codec->spec;
e4973e1e
TI
1267 struct auto_pin_cfg *cfg = &spec->autocfg;
1268 hda_nid_t nid;
2f2f4251 1269 int err;
c7d4b2fa 1270 int i;
2f2f4251
M
1271
1272 err = snd_hda_add_new_ctls(codec, spec->mixer);
1273 if (err < 0)
1274 return err;
c7d4b2fa
M
1275
1276 for (i = 0; i < spec->num_mixers; i++) {
1277 err = snd_hda_add_new_ctls(codec, spec->mixers[i]);
1278 if (err < 0)
1279 return err;
1280 }
1697055e
TI
1281 if (spec->num_dmuxes > 0) {
1282 stac_dmux_mixer.count = spec->num_dmuxes;
d13bd412 1283 err = snd_hda_ctl_add(codec,
1697055e
TI
1284 snd_ctl_new1(&stac_dmux_mixer, codec));
1285 if (err < 0)
1286 return err;
1287 }
d9737751 1288 if (spec->num_smuxes > 0) {
00ef50c2
MR
1289 int wcaps = get_wcaps(codec, spec->multiout.dig_out_nid);
1290 struct hda_input_mux *smux = &spec->private_smux;
1291 /* check for mute support on SPDIF out */
1292 if (wcaps & AC_WCAP_OUT_AMP) {
1293 smux->items[smux->num_items].label = "Off";
1294 smux->items[smux->num_items].index = 0;
1295 smux->num_items++;
1296 spec->spdif_mute = 1;
1297 }
d9737751
MR
1298 stac_smux_mixer.count = spec->num_smuxes;
1299 err = snd_ctl_add(codec->bus->card,
1300 snd_ctl_new1(&stac_smux_mixer, codec));
1301 if (err < 0)
1302 return err;
1303 }
c7d4b2fa 1304
dabbed6f
M
1305 if (spec->multiout.dig_out_nid) {
1306 err = snd_hda_create_spdif_out_ctls(codec, spec->multiout.dig_out_nid);
1307 if (err < 0)
1308 return err;
9a08160b
TI
1309 err = snd_hda_create_spdif_share_sw(codec,
1310 &spec->multiout);
1311 if (err < 0)
1312 return err;
1313 spec->multiout.share_spdif = 1;
dabbed6f 1314 }
da74ae3e 1315 if (spec->dig_in_nid && !(spec->gpio_dir & 0x01)) {
dabbed6f
M
1316 err = snd_hda_create_spdif_in_ctls(codec, spec->dig_in_nid);
1317 if (err < 0)
1318 return err;
1319 }
2134ea4f
TI
1320
1321 /* if we have no master control, let's create it */
1322 if (!snd_hda_find_mixer_ctl(codec, "Master Playback Volume")) {
1c82ed1b 1323 unsigned int vmaster_tlv[4];
2134ea4f 1324 snd_hda_set_vmaster_tlv(codec, spec->multiout.dac_nids[0],
1c82ed1b 1325 HDA_OUTPUT, vmaster_tlv);
2134ea4f 1326 err = snd_hda_add_vmaster(codec, "Master Playback Volume",
1c82ed1b 1327 vmaster_tlv, slave_vols);
2134ea4f
TI
1328 if (err < 0)
1329 return err;
1330 }
1331 if (!snd_hda_find_mixer_ctl(codec, "Master Playback Switch")) {
1332 err = snd_hda_add_vmaster(codec, "Master Playback Switch",
1333 NULL, slave_sws);
1334 if (err < 0)
1335 return err;
1336 }
1337
603c4019 1338 stac92xx_free_kctls(codec); /* no longer needed */
e4973e1e
TI
1339
1340 /* create jack input elements */
1341 if (spec->hp_detect) {
1342 for (i = 0; i < cfg->hp_outs; i++) {
1343 int type = SND_JACK_HEADPHONE;
1344 nid = cfg->hp_pins[i];
1345 /* jack detection */
1346 if (cfg->hp_outs == i)
1347 type |= SND_JACK_LINEOUT;
1348 err = stac92xx_add_jack(codec, nid, type);
1349 if (err < 0)
1350 return err;
1351 }
1352 }
1353 for (i = 0; i < cfg->line_outs; i++) {
1354 err = stac92xx_add_jack(codec, cfg->line_out_pins[i],
1355 SND_JACK_LINEOUT);
1356 if (err < 0)
1357 return err;
1358 }
1359 for (i = 0; i < AUTO_PIN_LAST; i++) {
1360 nid = cfg->input_pins[i];
1361 if (nid) {
1362 err = stac92xx_add_jack(codec, nid,
1363 SND_JACK_MICROPHONE);
1364 if (err < 0)
1365 return err;
1366 }
1367 }
1368
dabbed6f 1369 return 0;
2f2f4251
M
1370}
1371
403d1944 1372static unsigned int ref9200_pin_configs[8] = {
dabbed6f 1373 0x01c47010, 0x01447010, 0x0221401f, 0x01114010,
2f2f4251
M
1374 0x02a19020, 0x01a19021, 0x90100140, 0x01813122,
1375};
1376
58eec423
MCC
1377static unsigned int gateway9200_m4_pin_configs[8] = {
1378 0x400000fe, 0x404500f4, 0x400100f0, 0x90110010,
1379 0x400100f1, 0x02a1902e, 0x500000f2, 0x500000f3,
1380};
1381static unsigned int gateway9200_m4_2_pin_configs[8] = {
1382 0x400000fe, 0x404500f4, 0x400100f0, 0x90110010,
1383 0x400100f1, 0x02a1902e, 0x500000f2, 0x500000f3,
1384};
1385
1386/*
dfe495d0
TI
1387 STAC 9200 pin configs for
1388 102801A8
1389 102801DE
1390 102801E8
1391*/
1392static unsigned int dell9200_d21_pin_configs[8] = {
af6c016e
TI
1393 0x400001f0, 0x400001f1, 0x02214030, 0x01014010,
1394 0x02a19020, 0x01a19021, 0x90100140, 0x01813122,
dfe495d0
TI
1395};
1396
1397/*
1398 STAC 9200 pin configs for
1399 102801C0
1400 102801C1
1401*/
1402static unsigned int dell9200_d22_pin_configs[8] = {
af6c016e
TI
1403 0x400001f0, 0x400001f1, 0x0221401f, 0x01014010,
1404 0x01813020, 0x02a19021, 0x90100140, 0x400001f2,
dfe495d0
TI
1405};
1406
1407/*
1408 STAC 9200 pin configs for
1409 102801C4 (Dell Dimension E310)
1410 102801C5
1411 102801C7
1412 102801D9
1413 102801DA
1414 102801E3
1415*/
1416static unsigned int dell9200_d23_pin_configs[8] = {
af6c016e
TI
1417 0x400001f0, 0x400001f1, 0x0221401f, 0x01014010,
1418 0x01813020, 0x01a19021, 0x90100140, 0x400001f2,
dfe495d0
TI
1419};
1420
1421
1422/*
1423 STAC 9200-32 pin configs for
1424 102801B5 (Dell Inspiron 630m)
1425 102801D8 (Dell Inspiron 640m)
1426*/
1427static unsigned int dell9200_m21_pin_configs[8] = {
af6c016e
TI
1428 0x40c003fa, 0x03441340, 0x0321121f, 0x90170310,
1429 0x408003fb, 0x03a11020, 0x401003fc, 0x403003fd,
dfe495d0
TI
1430};
1431
1432/*
1433 STAC 9200-32 pin configs for
1434 102801C2 (Dell Latitude D620)
1435 102801C8
1436 102801CC (Dell Latitude D820)
1437 102801D4
1438 102801D6
1439*/
1440static unsigned int dell9200_m22_pin_configs[8] = {
af6c016e
TI
1441 0x40c003fa, 0x0144131f, 0x0321121f, 0x90170310,
1442 0x90a70321, 0x03a11020, 0x401003fb, 0x40f000fc,
dfe495d0
TI
1443};
1444
1445/*
1446 STAC 9200-32 pin configs for
1447 102801CE (Dell XPS M1710)
1448 102801CF (Dell Precision M90)
1449*/
1450static unsigned int dell9200_m23_pin_configs[8] = {
1451 0x40c003fa, 0x01441340, 0x0421421f, 0x90170310,
1452 0x408003fb, 0x04a1102e, 0x90170311, 0x403003fc,
1453};
1454
1455/*
1456 STAC 9200-32 pin configs for
1457 102801C9
1458 102801CA
1459 102801CB (Dell Latitude 120L)
1460 102801D3
1461*/
1462static unsigned int dell9200_m24_pin_configs[8] = {
af6c016e
TI
1463 0x40c003fa, 0x404003fb, 0x0321121f, 0x90170310,
1464 0x408003fc, 0x03a11020, 0x401003fd, 0x403003fe,
dfe495d0
TI
1465};
1466
1467/*
1468 STAC 9200-32 pin configs for
1469 102801BD (Dell Inspiron E1505n)
1470 102801EE
1471 102801EF
1472*/
1473static unsigned int dell9200_m25_pin_configs[8] = {
af6c016e
TI
1474 0x40c003fa, 0x01441340, 0x0421121f, 0x90170310,
1475 0x408003fb, 0x04a11020, 0x401003fc, 0x403003fd,
dfe495d0
TI
1476};
1477
1478/*
1479 STAC 9200-32 pin configs for
1480 102801F5 (Dell Inspiron 1501)
1481 102801F6
1482*/
1483static unsigned int dell9200_m26_pin_configs[8] = {
af6c016e
TI
1484 0x40c003fa, 0x404003fb, 0x0421121f, 0x90170310,
1485 0x408003fc, 0x04a11020, 0x401003fd, 0x403003fe,
dfe495d0
TI
1486};
1487
1488/*
1489 STAC 9200-32
1490 102801CD (Dell Inspiron E1705/9400)
1491*/
1492static unsigned int dell9200_m27_pin_configs[8] = {
af6c016e
TI
1493 0x40c003fa, 0x01441340, 0x0421121f, 0x90170310,
1494 0x90170310, 0x04a11020, 0x90170310, 0x40f003fc,
dfe495d0
TI
1495};
1496
bf277785
TD
1497static unsigned int oqo9200_pin_configs[8] = {
1498 0x40c000f0, 0x404000f1, 0x0221121f, 0x02211210,
1499 0x90170111, 0x90a70120, 0x400000f2, 0x400000f3,
1500};
1501
dfe495d0 1502
f5fcc13c
TI
1503static unsigned int *stac9200_brd_tbl[STAC_9200_MODELS] = {
1504 [STAC_REF] = ref9200_pin_configs,
bf277785 1505 [STAC_9200_OQO] = oqo9200_pin_configs,
dfe495d0
TI
1506 [STAC_9200_DELL_D21] = dell9200_d21_pin_configs,
1507 [STAC_9200_DELL_D22] = dell9200_d22_pin_configs,
1508 [STAC_9200_DELL_D23] = dell9200_d23_pin_configs,
1509 [STAC_9200_DELL_M21] = dell9200_m21_pin_configs,
1510 [STAC_9200_DELL_M22] = dell9200_m22_pin_configs,
1511 [STAC_9200_DELL_M23] = dell9200_m23_pin_configs,
1512 [STAC_9200_DELL_M24] = dell9200_m24_pin_configs,
1513 [STAC_9200_DELL_M25] = dell9200_m25_pin_configs,
1514 [STAC_9200_DELL_M26] = dell9200_m26_pin_configs,
1515 [STAC_9200_DELL_M27] = dell9200_m27_pin_configs,
58eec423
MCC
1516 [STAC_9200_M4] = gateway9200_m4_pin_configs,
1517 [STAC_9200_M4_2] = gateway9200_m4_2_pin_configs,
117f257d 1518 [STAC_9200_PANASONIC] = ref9200_pin_configs,
403d1944
MP
1519};
1520
f5fcc13c
TI
1521static const char *stac9200_models[STAC_9200_MODELS] = {
1522 [STAC_REF] = "ref",
bf277785 1523 [STAC_9200_OQO] = "oqo",
dfe495d0
TI
1524 [STAC_9200_DELL_D21] = "dell-d21",
1525 [STAC_9200_DELL_D22] = "dell-d22",
1526 [STAC_9200_DELL_D23] = "dell-d23",
1527 [STAC_9200_DELL_M21] = "dell-m21",
1528 [STAC_9200_DELL_M22] = "dell-m22",
1529 [STAC_9200_DELL_M23] = "dell-m23",
1530 [STAC_9200_DELL_M24] = "dell-m24",
1531 [STAC_9200_DELL_M25] = "dell-m25",
1532 [STAC_9200_DELL_M26] = "dell-m26",
1533 [STAC_9200_DELL_M27] = "dell-m27",
58eec423
MCC
1534 [STAC_9200_M4] = "gateway-m4",
1535 [STAC_9200_M4_2] = "gateway-m4-2",
117f257d 1536 [STAC_9200_PANASONIC] = "panasonic",
f5fcc13c
TI
1537};
1538
1539static struct snd_pci_quirk stac9200_cfg_tbl[] = {
1540 /* SigmaTel reference board */
1541 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
1542 "DFI LanParty", STAC_REF),
e7377071 1543 /* Dell laptops have BIOS problem */
dfe495d0
TI
1544 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a8,
1545 "unknown Dell", STAC_9200_DELL_D21),
f5fcc13c 1546 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01b5,
dfe495d0
TI
1547 "Dell Inspiron 630m", STAC_9200_DELL_M21),
1548 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01bd,
1549 "Dell Inspiron E1505n", STAC_9200_DELL_M25),
1550 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c0,
1551 "unknown Dell", STAC_9200_DELL_D22),
1552 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c1,
1553 "unknown Dell", STAC_9200_DELL_D22),
f5fcc13c 1554 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c2,
dfe495d0
TI
1555 "Dell Latitude D620", STAC_9200_DELL_M22),
1556 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c5,
1557 "unknown Dell", STAC_9200_DELL_D23),
1558 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c7,
1559 "unknown Dell", STAC_9200_DELL_D23),
1560 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c8,
1561 "unknown Dell", STAC_9200_DELL_M22),
1562 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c9,
1563 "unknown Dell", STAC_9200_DELL_M24),
1564 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ca,
1565 "unknown Dell", STAC_9200_DELL_M24),
f5fcc13c 1566 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cb,
dfe495d0 1567 "Dell Latitude 120L", STAC_9200_DELL_M24),
877b866d 1568 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cc,
dfe495d0 1569 "Dell Latitude D820", STAC_9200_DELL_M22),
46f02ca3 1570 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cd,
dfe495d0 1571 "Dell Inspiron E1705/9400", STAC_9200_DELL_M27),
46f02ca3 1572 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ce,
dfe495d0 1573 "Dell XPS M1710", STAC_9200_DELL_M23),
f0f96745 1574 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cf,
dfe495d0
TI
1575 "Dell Precision M90", STAC_9200_DELL_M23),
1576 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d3,
1577 "unknown Dell", STAC_9200_DELL_M22),
1578 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d4,
1579 "unknown Dell", STAC_9200_DELL_M22),
8286c53e 1580 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d6,
dfe495d0 1581 "unknown Dell", STAC_9200_DELL_M22),
49c605db 1582 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d8,
dfe495d0
TI
1583 "Dell Inspiron 640m", STAC_9200_DELL_M21),
1584 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d9,
1585 "unknown Dell", STAC_9200_DELL_D23),
1586 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01da,
1587 "unknown Dell", STAC_9200_DELL_D23),
1588 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01de,
1589 "unknown Dell", STAC_9200_DELL_D21),
1590 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01e3,
1591 "unknown Dell", STAC_9200_DELL_D23),
1592 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01e8,
1593 "unknown Dell", STAC_9200_DELL_D21),
1594 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ee,
1595 "unknown Dell", STAC_9200_DELL_M25),
1596 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ef,
1597 "unknown Dell", STAC_9200_DELL_M25),
49c605db 1598 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f5,
dfe495d0
TI
1599 "Dell Inspiron 1501", STAC_9200_DELL_M26),
1600 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f6,
1601 "unknown Dell", STAC_9200_DELL_M26),
49c605db 1602 /* Panasonic */
117f257d 1603 SND_PCI_QUIRK(0x10f7, 0x8338, "Panasonic CF-74", STAC_9200_PANASONIC),
1194b5b7 1604 /* Gateway machines needs EAPD to be set on resume */
58eec423
MCC
1605 SND_PCI_QUIRK(0x107b, 0x0205, "Gateway S-7110M", STAC_9200_M4),
1606 SND_PCI_QUIRK(0x107b, 0x0317, "Gateway MT3423, MX341*", STAC_9200_M4_2),
1607 SND_PCI_QUIRK(0x107b, 0x0318, "Gateway ML3019, MT3707", STAC_9200_M4_2),
bf277785
TD
1608 /* OQO Mobile */
1609 SND_PCI_QUIRK(0x1106, 0x3288, "OQO Model 2", STAC_9200_OQO),
403d1944
MP
1610 {} /* terminator */
1611};
1612
8e21c34c
TD
1613static unsigned int ref925x_pin_configs[8] = {
1614 0x40c003f0, 0x424503f2, 0x01813022, 0x02a19021,
09a99959 1615 0x90a70320, 0x02214210, 0x01019020, 0x9033032e,
8e21c34c
TD
1616};
1617
9cb36c2a
MCC
1618static unsigned int stac925xM1_pin_configs[8] = {
1619 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1620 0x40a000f0, 0x90100210, 0x400003f1, 0x9033032e,
1621};
58eec423 1622
9cb36c2a
MCC
1623static unsigned int stac925xM1_2_pin_configs[8] = {
1624 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1625 0x40a000f0, 0x90100210, 0x400003f1, 0x9033032e,
1626};
58eec423 1627
9cb36c2a
MCC
1628static unsigned int stac925xM2_pin_configs[8] = {
1629 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1630 0x40a000f0, 0x90100210, 0x400003f1, 0x9033032e,
1631};
1632
58eec423
MCC
1633static unsigned int stac925xM2_2_pin_configs[8] = {
1634 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1635 0x40a000f0, 0x90100210, 0x400003f1, 0x9033032e,
1636};
1637
9cb36c2a
MCC
1638static unsigned int stac925xM3_pin_configs[8] = {
1639 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1640 0x40a000f0, 0x90100210, 0x400003f1, 0x503303f3,
1641};
58eec423 1642
9cb36c2a
MCC
1643static unsigned int stac925xM5_pin_configs[8] = {
1644 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1645 0x40a000f0, 0x90100210, 0x400003f1, 0x9033032e,
1646};
1647
9cb36c2a
MCC
1648static unsigned int stac925xM6_pin_configs[8] = {
1649 0x40c003f4, 0x424503f2, 0x400000f3, 0x02a19020,
1650 0x40a000f0, 0x90100210, 0x400003f1, 0x90330320,
1651};
1652
8e21c34c
TD
1653static unsigned int *stac925x_brd_tbl[STAC_925x_MODELS] = {
1654 [STAC_REF] = ref925x_pin_configs,
9cb36c2a
MCC
1655 [STAC_M1] = stac925xM1_pin_configs,
1656 [STAC_M1_2] = stac925xM1_2_pin_configs,
1657 [STAC_M2] = stac925xM2_pin_configs,
8e21c34c 1658 [STAC_M2_2] = stac925xM2_2_pin_configs,
9cb36c2a
MCC
1659 [STAC_M3] = stac925xM3_pin_configs,
1660 [STAC_M5] = stac925xM5_pin_configs,
1661 [STAC_M6] = stac925xM6_pin_configs,
8e21c34c
TD
1662};
1663
1664static const char *stac925x_models[STAC_925x_MODELS] = {
1665 [STAC_REF] = "ref",
9cb36c2a
MCC
1666 [STAC_M1] = "m1",
1667 [STAC_M1_2] = "m1-2",
1668 [STAC_M2] = "m2",
8e21c34c 1669 [STAC_M2_2] = "m2-2",
9cb36c2a
MCC
1670 [STAC_M3] = "m3",
1671 [STAC_M5] = "m5",
1672 [STAC_M6] = "m6",
8e21c34c
TD
1673};
1674
9cb36c2a 1675static struct snd_pci_quirk stac925x_codec_id_cfg_tbl[] = {
58eec423
MCC
1676 SND_PCI_QUIRK(0x107b, 0x0316, "Gateway M255", STAC_M2),
1677 SND_PCI_QUIRK(0x107b, 0x0366, "Gateway MP6954", STAC_M5),
1678 SND_PCI_QUIRK(0x107b, 0x0461, "Gateway NX560XL", STAC_M1),
1679 SND_PCI_QUIRK(0x107b, 0x0681, "Gateway NX860", STAC_M2),
9cb36c2a 1680 SND_PCI_QUIRK(0x107b, 0x0367, "Gateway MX6453", STAC_M1_2),
9cb36c2a
MCC
1681 /* Not sure about the brand name for those */
1682 SND_PCI_QUIRK(0x107b, 0x0281, "Gateway mobile", STAC_M1),
1683 SND_PCI_QUIRK(0x107b, 0x0507, "Gateway mobile", STAC_M3),
1684 SND_PCI_QUIRK(0x107b, 0x0281, "Gateway mobile", STAC_M6),
1685 SND_PCI_QUIRK(0x107b, 0x0685, "Gateway mobile", STAC_M2_2),
9cb36c2a
MCC
1686 {} /* terminator */
1687};
1688
1689static struct snd_pci_quirk stac925x_cfg_tbl[] = {
1690 /* SigmaTel reference board */
1691 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668, "DFI LanParty", STAC_REF),
1692 SND_PCI_QUIRK(0x8384, 0x7632, "Stac9202 Reference Board", STAC_REF),
1693
1694 /* Default table for unknown ID */
1695 SND_PCI_QUIRK(0x1002, 0x437b, "Gateway mobile", STAC_M2_2),
1696
8e21c34c
TD
1697 {} /* terminator */
1698};
1699
a7662640 1700static unsigned int ref92hd73xx_pin_configs[13] = {
e1f0d669
MR
1701 0x02214030, 0x02a19040, 0x01a19020, 0x02214030,
1702 0x0181302e, 0x01014010, 0x01014020, 0x01014030,
1703 0x02319040, 0x90a000f0, 0x90a000f0, 0x01452050,
a7662640
MR
1704 0x01452050,
1705};
1706
1707static unsigned int dell_m6_pin_configs[13] = {
1708 0x0321101f, 0x4f00000f, 0x4f0000f0, 0x90170110,
7c2ba97b 1709 0x03a11020, 0x0321101f, 0x4f0000f0, 0x4f0000f0,
a7662640
MR
1710 0x4f0000f0, 0x90a60160, 0x4f0000f0, 0x4f0000f0,
1711 0x4f0000f0,
e1f0d669
MR
1712};
1713
1714static unsigned int *stac92hd73xx_brd_tbl[STAC_92HD73XX_MODELS] = {
a7662640 1715 [STAC_92HD73XX_REF] = ref92hd73xx_pin_configs,
661cd8fb
TI
1716 [STAC_DELL_M6_AMIC] = dell_m6_pin_configs,
1717 [STAC_DELL_M6_DMIC] = dell_m6_pin_configs,
1718 [STAC_DELL_M6_BOTH] = dell_m6_pin_configs,
6b3ab21e 1719 [STAC_DELL_EQ] = dell_m6_pin_configs,
e1f0d669
MR
1720};
1721
1722static const char *stac92hd73xx_models[STAC_92HD73XX_MODELS] = {
1723 [STAC_92HD73XX_REF] = "ref",
661cd8fb
TI
1724 [STAC_DELL_M6_AMIC] = "dell-m6-amic",
1725 [STAC_DELL_M6_DMIC] = "dell-m6-dmic",
1726 [STAC_DELL_M6_BOTH] = "dell-m6",
6b3ab21e 1727 [STAC_DELL_EQ] = "dell-eq",
e1f0d669
MR
1728};
1729
1730static struct snd_pci_quirk stac92hd73xx_cfg_tbl[] = {
1731 /* SigmaTel reference board */
1732 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
a7662640
MR
1733 "DFI LanParty", STAC_92HD73XX_REF),
1734 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0254,
661cd8fb 1735 "Dell Studio 1535", STAC_DELL_M6_DMIC),
a7662640 1736 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0255,
661cd8fb 1737 "unknown Dell", STAC_DELL_M6_DMIC),
a7662640 1738 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0256,
661cd8fb 1739 "unknown Dell", STAC_DELL_M6_BOTH),
a7662640 1740 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0257,
661cd8fb 1741 "unknown Dell", STAC_DELL_M6_BOTH),
a7662640 1742 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x025e,
661cd8fb 1743 "unknown Dell", STAC_DELL_M6_AMIC),
a7662640 1744 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x025f,
661cd8fb 1745 "unknown Dell", STAC_DELL_M6_AMIC),
a7662640 1746 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0271,
661cd8fb
TI
1747 "unknown Dell", STAC_DELL_M6_DMIC),
1748 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0272,
1749 "unknown Dell", STAC_DELL_M6_DMIC),
b0fc5e04 1750 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x029f,
661cd8fb 1751 "Dell Studio 1537", STAC_DELL_M6_DMIC),
e1f0d669
MR
1752 {} /* terminator */
1753};
1754
d0513fc6
MR
1755static unsigned int ref92hd83xxx_pin_configs[14] = {
1756 0x02214030, 0x02211010, 0x02a19020, 0x02170130,
1757 0x01014050, 0x01819040, 0x01014020, 0x90a3014e,
1758 0x40f000f0, 0x40f000f0, 0x40f000f0, 0x40f000f0,
1759 0x01451160, 0x98560170,
1760};
1761
1762static unsigned int *stac92hd83xxx_brd_tbl[STAC_92HD83XXX_MODELS] = {
1763 [STAC_92HD83XXX_REF] = ref92hd83xxx_pin_configs,
1764};
1765
1766static const char *stac92hd83xxx_models[STAC_92HD83XXX_MODELS] = {
1767 [STAC_92HD83XXX_REF] = "ref",
1768};
1769
1770static struct snd_pci_quirk stac92hd83xxx_cfg_tbl[] = {
1771 /* SigmaTel reference board */
1772 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
1773 "DFI LanParty", STAC_92HD71BXX_REF),
1774};
1775
0ffa9807 1776static unsigned int ref92hd71bxx_pin_configs[11] = {
e035b841 1777 0x02214030, 0x02a19040, 0x01a19020, 0x01014010,
4b33c767 1778 0x0181302e, 0x01014010, 0x01019020, 0x90a000f0,
0ffa9807 1779 0x90a000f0, 0x01452050, 0x01452050,
e035b841
MR
1780};
1781
0ffa9807 1782static unsigned int dell_m4_1_pin_configs[11] = {
a7662640 1783 0x0421101f, 0x04a11221, 0x40f000f0, 0x90170110,
07bcb316 1784 0x23a1902e, 0x23014250, 0x40f000f0, 0x90a000f0,
0ffa9807 1785 0x40f000f0, 0x4f0000f0, 0x4f0000f0,
a7662640
MR
1786};
1787
0ffa9807 1788static unsigned int dell_m4_2_pin_configs[11] = {
a7662640
MR
1789 0x0421101f, 0x04a11221, 0x90a70330, 0x90170110,
1790 0x23a1902e, 0x23014250, 0x40f000f0, 0x40f000f0,
0ffa9807 1791 0x40f000f0, 0x044413b0, 0x044413b0,
a7662640
MR
1792};
1793
3a7abfd2
MR
1794static unsigned int dell_m4_3_pin_configs[11] = {
1795 0x0421101f, 0x04a11221, 0x90a70330, 0x90170110,
1796 0x40f000f0, 0x40f000f0, 0x40f000f0, 0x90a000f0,
1797 0x40f000f0, 0x044413b0, 0x044413b0,
1798};
1799
e035b841
MR
1800static unsigned int *stac92hd71bxx_brd_tbl[STAC_92HD71BXX_MODELS] = {
1801 [STAC_92HD71BXX_REF] = ref92hd71bxx_pin_configs,
a7662640
MR
1802 [STAC_DELL_M4_1] = dell_m4_1_pin_configs,
1803 [STAC_DELL_M4_2] = dell_m4_2_pin_configs,
3a7abfd2 1804 [STAC_DELL_M4_3] = dell_m4_3_pin_configs,
6a14f585 1805 [STAC_HP_M4] = NULL,
e035b841
MR
1806};
1807
1808static const char *stac92hd71bxx_models[STAC_92HD71BXX_MODELS] = {
1809 [STAC_92HD71BXX_REF] = "ref",
a7662640
MR
1810 [STAC_DELL_M4_1] = "dell-m4-1",
1811 [STAC_DELL_M4_2] = "dell-m4-2",
3a7abfd2 1812 [STAC_DELL_M4_3] = "dell-m4-3",
6a14f585 1813 [STAC_HP_M4] = "hp-m4",
e035b841
MR
1814};
1815
1816static struct snd_pci_quirk stac92hd71bxx_cfg_tbl[] = {
1817 /* SigmaTel reference board */
1818 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
1819 "DFI LanParty", STAC_92HD71BXX_REF),
80bf2724
TI
1820 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30f2,
1821 "HP dv5", STAC_HP_M4),
1822 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30f4,
1823 "HP dv7", STAC_HP_M4),
9a9e2359
MR
1824 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x361a,
1825 "unknown HP", STAC_HP_M4),
a7662640
MR
1826 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0233,
1827 "unknown Dell", STAC_DELL_M4_1),
1828 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0234,
1829 "unknown Dell", STAC_DELL_M4_1),
1830 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0250,
1831 "unknown Dell", STAC_DELL_M4_1),
1832 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x024f,
1833 "unknown Dell", STAC_DELL_M4_1),
1834 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x024d,
1835 "unknown Dell", STAC_DELL_M4_1),
1836 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0251,
1837 "unknown Dell", STAC_DELL_M4_1),
1838 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0277,
1839 "unknown Dell", STAC_DELL_M4_1),
1840 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0263,
1841 "unknown Dell", STAC_DELL_M4_2),
1842 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0265,
1843 "unknown Dell", STAC_DELL_M4_2),
1844 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0262,
1845 "unknown Dell", STAC_DELL_M4_2),
1846 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0264,
1847 "unknown Dell", STAC_DELL_M4_2),
3a7abfd2
MR
1848 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02aa,
1849 "unknown Dell", STAC_DELL_M4_3),
e035b841
MR
1850 {} /* terminator */
1851};
1852
403d1944
MP
1853static unsigned int ref922x_pin_configs[10] = {
1854 0x01014010, 0x01016011, 0x01012012, 0x0221401f,
1855 0x01813122, 0x01011014, 0x01441030, 0x01c41030,
2f2f4251
M
1856 0x40000100, 0x40000100,
1857};
1858
dfe495d0
TI
1859/*
1860 STAC 922X pin configs for
1861 102801A7
1862 102801AB
1863 102801A9
1864 102801D1
1865 102801D2
1866*/
1867static unsigned int dell_922x_d81_pin_configs[10] = {
1868 0x02214030, 0x01a19021, 0x01111012, 0x01114010,
1869 0x02a19020, 0x01117011, 0x400001f0, 0x400001f1,
1870 0x01813122, 0x400001f2,
1871};
1872
1873/*
1874 STAC 922X pin configs for
1875 102801AC
1876 102801D0
1877*/
1878static unsigned int dell_922x_d82_pin_configs[10] = {
1879 0x02214030, 0x01a19021, 0x01111012, 0x01114010,
1880 0x02a19020, 0x01117011, 0x01451140, 0x400001f0,
1881 0x01813122, 0x400001f1,
1882};
1883
1884/*
1885 STAC 922X pin configs for
1886 102801BF
1887*/
1888static unsigned int dell_922x_m81_pin_configs[10] = {
1889 0x0321101f, 0x01112024, 0x01111222, 0x91174220,
1890 0x03a11050, 0x01116221, 0x90a70330, 0x01452340,
1891 0x40C003f1, 0x405003f0,
1892};
1893
1894/*
1895 STAC 9221 A1 pin configs for
1896 102801D7 (Dell XPS M1210)
1897*/
1898static unsigned int dell_922x_m82_pin_configs[10] = {
7f9310c1
JZ
1899 0x02211211, 0x408103ff, 0x02a1123e, 0x90100310,
1900 0x408003f1, 0x0221121f, 0x03451340, 0x40c003f2,
dfe495d0
TI
1901 0x508003f3, 0x405003f4,
1902};
1903
403d1944 1904static unsigned int d945gtp3_pin_configs[10] = {
869264c4 1905 0x0221401f, 0x01a19022, 0x01813021, 0x01014010,
403d1944
MP
1906 0x40000100, 0x40000100, 0x40000100, 0x40000100,
1907 0x02a19120, 0x40000100,
1908};
1909
1910static unsigned int d945gtp5_pin_configs[10] = {
869264c4
MP
1911 0x0221401f, 0x01011012, 0x01813024, 0x01014010,
1912 0x01a19021, 0x01016011, 0x01452130, 0x40000100,
403d1944
MP
1913 0x02a19320, 0x40000100,
1914};
1915
5d5d3bc3
IZ
1916static unsigned int intel_mac_v1_pin_configs[10] = {
1917 0x0121e21f, 0x400000ff, 0x9017e110, 0x400000fd,
1918 0x400000fe, 0x0181e020, 0x1145e030, 0x11c5e240,
1919 0x400000fc, 0x400000fb,
1920};
1921
1922static unsigned int intel_mac_v2_pin_configs[10] = {
1923 0x0121e21f, 0x90a7012e, 0x9017e110, 0x400000fd,
1924 0x400000fe, 0x0181e020, 0x1145e230, 0x500000fa,
1925 0x400000fc, 0x400000fb,
6f0778d8
NB
1926};
1927
5d5d3bc3
IZ
1928static unsigned int intel_mac_v3_pin_configs[10] = {
1929 0x0121e21f, 0x90a7012e, 0x9017e110, 0x400000fd,
1930 0x400000fe, 0x0181e020, 0x1145e230, 0x11c5e240,
3fc24d85
TI
1931 0x400000fc, 0x400000fb,
1932};
1933
5d5d3bc3
IZ
1934static unsigned int intel_mac_v4_pin_configs[10] = {
1935 0x0321e21f, 0x03a1e02e, 0x9017e110, 0x9017e11f,
1936 0x400000fe, 0x0381e020, 0x1345e230, 0x13c5e240,
f16928fb
SF
1937 0x400000fc, 0x400000fb,
1938};
1939
5d5d3bc3
IZ
1940static unsigned int intel_mac_v5_pin_configs[10] = {
1941 0x0321e21f, 0x03a1e02e, 0x9017e110, 0x9017e11f,
1942 0x400000fe, 0x0381e020, 0x1345e230, 0x13c5e240,
1943 0x400000fc, 0x400000fb,
0dae0f83
TI
1944};
1945
8c650087
MCC
1946static unsigned int ecs202_pin_configs[10] = {
1947 0x0221401f, 0x02a19020, 0x01a19020, 0x01114010,
1948 0x408000f0, 0x01813022, 0x074510a0, 0x40c400f1,
1949 0x9037012e, 0x40e000f2,
1950};
76c08828 1951
19039bd0 1952static unsigned int *stac922x_brd_tbl[STAC_922X_MODELS] = {
f5fcc13c 1953 [STAC_D945_REF] = ref922x_pin_configs,
19039bd0
TI
1954 [STAC_D945GTP3] = d945gtp3_pin_configs,
1955 [STAC_D945GTP5] = d945gtp5_pin_configs,
5d5d3bc3
IZ
1956 [STAC_INTEL_MAC_V1] = intel_mac_v1_pin_configs,
1957 [STAC_INTEL_MAC_V2] = intel_mac_v2_pin_configs,
1958 [STAC_INTEL_MAC_V3] = intel_mac_v3_pin_configs,
1959 [STAC_INTEL_MAC_V4] = intel_mac_v4_pin_configs,
1960 [STAC_INTEL_MAC_V5] = intel_mac_v5_pin_configs,
536319af 1961 [STAC_INTEL_MAC_AUTO] = intel_mac_v3_pin_configs,
dfe495d0 1962 /* for backward compatibility */
5d5d3bc3
IZ
1963 [STAC_MACMINI] = intel_mac_v3_pin_configs,
1964 [STAC_MACBOOK] = intel_mac_v5_pin_configs,
1965 [STAC_MACBOOK_PRO_V1] = intel_mac_v3_pin_configs,
1966 [STAC_MACBOOK_PRO_V2] = intel_mac_v3_pin_configs,
1967 [STAC_IMAC_INTEL] = intel_mac_v2_pin_configs,
1968 [STAC_IMAC_INTEL_20] = intel_mac_v3_pin_configs,
8c650087 1969 [STAC_ECS_202] = ecs202_pin_configs,
dfe495d0
TI
1970 [STAC_922X_DELL_D81] = dell_922x_d81_pin_configs,
1971 [STAC_922X_DELL_D82] = dell_922x_d82_pin_configs,
1972 [STAC_922X_DELL_M81] = dell_922x_m81_pin_configs,
1973 [STAC_922X_DELL_M82] = dell_922x_m82_pin_configs,
403d1944
MP
1974};
1975
f5fcc13c
TI
1976static const char *stac922x_models[STAC_922X_MODELS] = {
1977 [STAC_D945_REF] = "ref",
1978 [STAC_D945GTP5] = "5stack",
1979 [STAC_D945GTP3] = "3stack",
5d5d3bc3
IZ
1980 [STAC_INTEL_MAC_V1] = "intel-mac-v1",
1981 [STAC_INTEL_MAC_V2] = "intel-mac-v2",
1982 [STAC_INTEL_MAC_V3] = "intel-mac-v3",
1983 [STAC_INTEL_MAC_V4] = "intel-mac-v4",
1984 [STAC_INTEL_MAC_V5] = "intel-mac-v5",
536319af 1985 [STAC_INTEL_MAC_AUTO] = "intel-mac-auto",
dfe495d0 1986 /* for backward compatibility */
f5fcc13c 1987 [STAC_MACMINI] = "macmini",
3fc24d85 1988 [STAC_MACBOOK] = "macbook",
6f0778d8
NB
1989 [STAC_MACBOOK_PRO_V1] = "macbook-pro-v1",
1990 [STAC_MACBOOK_PRO_V2] = "macbook-pro",
f16928fb 1991 [STAC_IMAC_INTEL] = "imac-intel",
0dae0f83 1992 [STAC_IMAC_INTEL_20] = "imac-intel-20",
8c650087 1993 [STAC_ECS_202] = "ecs202",
dfe495d0
TI
1994 [STAC_922X_DELL_D81] = "dell-d81",
1995 [STAC_922X_DELL_D82] = "dell-d82",
1996 [STAC_922X_DELL_M81] = "dell-m81",
1997 [STAC_922X_DELL_M82] = "dell-m82",
f5fcc13c
TI
1998};
1999
2000static struct snd_pci_quirk stac922x_cfg_tbl[] = {
2001 /* SigmaTel reference board */
2002 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
2003 "DFI LanParty", STAC_D945_REF),
2004 /* Intel 945G based systems */
2005 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0101,
2006 "Intel D945G", STAC_D945GTP3),
2007 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0202,
2008 "Intel D945G", STAC_D945GTP3),
2009 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0606,
2010 "Intel D945G", STAC_D945GTP3),
2011 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0601,
2012 "Intel D945G", STAC_D945GTP3),
2013 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0111,
2014 "Intel D945G", STAC_D945GTP3),
2015 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1115,
2016 "Intel D945G", STAC_D945GTP3),
2017 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1116,
2018 "Intel D945G", STAC_D945GTP3),
2019 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1117,
2020 "Intel D945G", STAC_D945GTP3),
2021 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1118,
2022 "Intel D945G", STAC_D945GTP3),
2023 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1119,
2024 "Intel D945G", STAC_D945GTP3),
2025 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x8826,
2026 "Intel D945G", STAC_D945GTP3),
2027 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5049,
2028 "Intel D945G", STAC_D945GTP3),
2029 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5055,
2030 "Intel D945G", STAC_D945GTP3),
2031 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5048,
2032 "Intel D945G", STAC_D945GTP3),
2033 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0110,
2034 "Intel D945G", STAC_D945GTP3),
2035 /* Intel D945G 5-stack systems */
2036 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0404,
2037 "Intel D945G", STAC_D945GTP5),
2038 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0303,
2039 "Intel D945G", STAC_D945GTP5),
2040 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0013,
2041 "Intel D945G", STAC_D945GTP5),
2042 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0417,
2043 "Intel D945G", STAC_D945GTP5),
2044 /* Intel 945P based systems */
2045 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0b0b,
2046 "Intel D945P", STAC_D945GTP3),
2047 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0112,
2048 "Intel D945P", STAC_D945GTP3),
2049 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0d0d,
2050 "Intel D945P", STAC_D945GTP3),
2051 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0909,
2052 "Intel D945P", STAC_D945GTP3),
2053 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0505,
2054 "Intel D945P", STAC_D945GTP3),
2055 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0707,
2056 "Intel D945P", STAC_D945GTP5),
2057 /* other systems */
536319af 2058 /* Apple Intel Mac (Mac Mini, MacBook, MacBook Pro...) */
f5fcc13c 2059 SND_PCI_QUIRK(0x8384, 0x7680,
536319af 2060 "Mac", STAC_INTEL_MAC_AUTO),
dfe495d0
TI
2061 /* Dell systems */
2062 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a7,
2063 "unknown Dell", STAC_922X_DELL_D81),
2064 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a9,
2065 "unknown Dell", STAC_922X_DELL_D81),
2066 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ab,
2067 "unknown Dell", STAC_922X_DELL_D81),
2068 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ac,
2069 "unknown Dell", STAC_922X_DELL_D82),
2070 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01bf,
2071 "unknown Dell", STAC_922X_DELL_M81),
2072 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d0,
2073 "unknown Dell", STAC_922X_DELL_D82),
2074 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d1,
2075 "unknown Dell", STAC_922X_DELL_D81),
2076 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d2,
2077 "unknown Dell", STAC_922X_DELL_D81),
2078 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d7,
2079 "Dell XPS M1210", STAC_922X_DELL_M82),
8c650087
MCC
2080 /* ECS/PC Chips boards */
2081 SND_PCI_QUIRK(0x1019, 0x2144,
2082 "ECS/PC chips", STAC_ECS_202),
2083 SND_PCI_QUIRK(0x1019, 0x2608,
2084 "ECS/PC chips", STAC_ECS_202),
2085 SND_PCI_QUIRK(0x1019, 0x2633,
2086 "ECS/PC chips P17G/1333", STAC_ECS_202),
2087 SND_PCI_QUIRK(0x1019, 0x2811,
2088 "ECS/PC chips", STAC_ECS_202),
2089 SND_PCI_QUIRK(0x1019, 0x2812,
2090 "ECS/PC chips", STAC_ECS_202),
2091 SND_PCI_QUIRK(0x1019, 0x2813,
2092 "ECS/PC chips", STAC_ECS_202),
2093 SND_PCI_QUIRK(0x1019, 0x2814,
2094 "ECS/PC chips", STAC_ECS_202),
2095 SND_PCI_QUIRK(0x1019, 0x2815,
2096 "ECS/PC chips", STAC_ECS_202),
2097 SND_PCI_QUIRK(0x1019, 0x2816,
2098 "ECS/PC chips", STAC_ECS_202),
2099 SND_PCI_QUIRK(0x1019, 0x2817,
2100 "ECS/PC chips", STAC_ECS_202),
2101 SND_PCI_QUIRK(0x1019, 0x2818,
2102 "ECS/PC chips", STAC_ECS_202),
2103 SND_PCI_QUIRK(0x1019, 0x2819,
2104 "ECS/PC chips", STAC_ECS_202),
2105 SND_PCI_QUIRK(0x1019, 0x2820,
2106 "ECS/PC chips", STAC_ECS_202),
403d1944
MP
2107 {} /* terminator */
2108};
2109
3cc08dc6 2110static unsigned int ref927x_pin_configs[14] = {
93ed1503
TD
2111 0x02214020, 0x02a19080, 0x0181304e, 0x01014010,
2112 0x01a19040, 0x01011012, 0x01016011, 0x0101201f,
2113 0x183301f0, 0x18a001f0, 0x18a001f0, 0x01442070,
2114 0x01c42190, 0x40000100,
3cc08dc6
MP
2115};
2116
93ed1503 2117static unsigned int d965_3st_pin_configs[14] = {
81d3dbde
TD
2118 0x0221401f, 0x02a19120, 0x40000100, 0x01014011,
2119 0x01a19021, 0x01813024, 0x40000100, 0x40000100,
2120 0x40000100, 0x40000100, 0x40000100, 0x40000100,
2121 0x40000100, 0x40000100
2122};
2123
93ed1503
TD
2124static unsigned int d965_5st_pin_configs[14] = {
2125 0x02214020, 0x02a19080, 0x0181304e, 0x01014010,
2126 0x01a19040, 0x01011012, 0x01016011, 0x40000100,
2127 0x40000100, 0x40000100, 0x40000100, 0x01442070,
2128 0x40000100, 0x40000100
2129};
2130
4ff076e5
TD
2131static unsigned int dell_3st_pin_configs[14] = {
2132 0x02211230, 0x02a11220, 0x01a19040, 0x01114210,
2133 0x01111212, 0x01116211, 0x01813050, 0x01112214,
8e9068b1 2134 0x403003fa, 0x90a60040, 0x90a60040, 0x404003fb,
4ff076e5
TD
2135 0x40c003fc, 0x40000100
2136};
2137
93ed1503 2138static unsigned int *stac927x_brd_tbl[STAC_927X_MODELS] = {
8e9068b1
MR
2139 [STAC_D965_REF] = ref927x_pin_configs,
2140 [STAC_D965_3ST] = d965_3st_pin_configs,
2141 [STAC_D965_5ST] = d965_5st_pin_configs,
2142 [STAC_DELL_3ST] = dell_3st_pin_configs,
2143 [STAC_DELL_BIOS] = NULL,
3cc08dc6
MP
2144};
2145
f5fcc13c 2146static const char *stac927x_models[STAC_927X_MODELS] = {
8e9068b1
MR
2147 [STAC_D965_REF] = "ref",
2148 [STAC_D965_3ST] = "3stack",
2149 [STAC_D965_5ST] = "5stack",
2150 [STAC_DELL_3ST] = "dell-3stack",
2151 [STAC_DELL_BIOS] = "dell-bios",
f5fcc13c
TI
2152};
2153
2154static struct snd_pci_quirk stac927x_cfg_tbl[] = {
2155 /* SigmaTel reference board */
2156 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
2157 "DFI LanParty", STAC_D965_REF),
81d3dbde 2158 /* Intel 946 based systems */
f5fcc13c
TI
2159 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x3d01, "Intel D946", STAC_D965_3ST),
2160 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0xa301, "Intel D946", STAC_D965_3ST),
93ed1503 2161 /* 965 based 3 stack systems */
f5fcc13c
TI
2162 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2116, "Intel D965", STAC_D965_3ST),
2163 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2115, "Intel D965", STAC_D965_3ST),
2164 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2114, "Intel D965", STAC_D965_3ST),
2165 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2113, "Intel D965", STAC_D965_3ST),
2166 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2112, "Intel D965", STAC_D965_3ST),
2167 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2111, "Intel D965", STAC_D965_3ST),
2168 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2110, "Intel D965", STAC_D965_3ST),
2169 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2009, "Intel D965", STAC_D965_3ST),
2170 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2008, "Intel D965", STAC_D965_3ST),
2171 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2007, "Intel D965", STAC_D965_3ST),
2172 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2006, "Intel D965", STAC_D965_3ST),
2173 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2005, "Intel D965", STAC_D965_3ST),
2174 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2004, "Intel D965", STAC_D965_3ST),
2175 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2003, "Intel D965", STAC_D965_3ST),
2176 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2002, "Intel D965", STAC_D965_3ST),
2177 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2001, "Intel D965", STAC_D965_3ST),
4ff076e5 2178 /* Dell 3 stack systems */
8e9068b1 2179 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f7, "Dell XPS M1730", STAC_DELL_3ST),
dfe495d0 2180 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01dd, "Dell Dimension E520", STAC_DELL_3ST),
4ff076e5
TD
2181 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ed, "Dell ", STAC_DELL_3ST),
2182 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f4, "Dell ", STAC_DELL_3ST),
8e9068b1 2183 /* Dell 3 stack systems with verb table in BIOS */
2f32d909
MR
2184 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f3, "Dell Inspiron 1420", STAC_DELL_BIOS),
2185 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0227, "Dell Vostro 1400 ", STAC_DELL_BIOS),
8e9068b1 2186 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x022e, "Dell ", STAC_DELL_BIOS),
24918b61 2187 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x022f, "Dell Inspiron 1525", STAC_DELL_3ST),
8e9068b1
MR
2188 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0242, "Dell ", STAC_DELL_BIOS),
2189 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0243, "Dell ", STAC_DELL_BIOS),
2190 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02ff, "Dell ", STAC_DELL_BIOS),
2191 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0209, "Dell XPS 1330", STAC_DELL_BIOS),
93ed1503 2192 /* 965 based 5 stack systems */
f5fcc13c
TI
2193 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2301, "Intel D965", STAC_D965_5ST),
2194 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2302, "Intel D965", STAC_D965_5ST),
2195 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2303, "Intel D965", STAC_D965_5ST),
2196 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2304, "Intel D965", STAC_D965_5ST),
2197 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2305, "Intel D965", STAC_D965_5ST),
2198 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2501, "Intel D965", STAC_D965_5ST),
2199 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2502, "Intel D965", STAC_D965_5ST),
2200 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2503, "Intel D965", STAC_D965_5ST),
2201 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2504, "Intel D965", STAC_D965_5ST),
3cc08dc6
MP
2202 {} /* terminator */
2203};
2204
f3302a59
MP
2205static unsigned int ref9205_pin_configs[12] = {
2206 0x40000100, 0x40000100, 0x01016011, 0x01014010,
09a99959 2207 0x01813122, 0x01a19021, 0x01019020, 0x40000100,
8b65727b 2208 0x90a000f0, 0x90a000f0, 0x01441030, 0x01c41030
f3302a59
MP
2209};
2210
dfe495d0
TI
2211/*
2212 STAC 9205 pin configs for
2213 102801F1
2214 102801F2
2215 102801FC
2216 102801FD
2217 10280204
2218 1028021F
3fa2ef74 2219 10280228 (Dell Vostro 1500)
dfe495d0
TI
2220*/
2221static unsigned int dell_9205_m42_pin_configs[12] = {
2222 0x0321101F, 0x03A11020, 0x400003FA, 0x90170310,
2223 0x400003FB, 0x400003FC, 0x400003FD, 0x40F000F9,
2224 0x90A60330, 0x400003FF, 0x0144131F, 0x40C003FE,
2225};
2226
2227/*
2228 STAC 9205 pin configs for
2229 102801F9
2230 102801FA
2231 102801FE
2232 102801FF (Dell Precision M4300)
2233 10280206
2234 10280200
2235 10280201
2236*/
2237static unsigned int dell_9205_m43_pin_configs[12] = {
ae0a8ed8
TD
2238 0x0321101f, 0x03a11020, 0x90a70330, 0x90170310,
2239 0x400000fe, 0x400000ff, 0x400000fd, 0x40f000f9,
2240 0x400000fa, 0x400000fc, 0x0144131f, 0x40c003f8,
2241};
2242
dfe495d0 2243static unsigned int dell_9205_m44_pin_configs[12] = {
ae0a8ed8
TD
2244 0x0421101f, 0x04a11020, 0x400003fa, 0x90170310,
2245 0x400003fb, 0x400003fc, 0x400003fd, 0x400003f9,
2246 0x90a60330, 0x400003ff, 0x01441340, 0x40c003fe,
2247};
2248
f5fcc13c 2249static unsigned int *stac9205_brd_tbl[STAC_9205_MODELS] = {
ae0a8ed8 2250 [STAC_9205_REF] = ref9205_pin_configs,
dfe495d0
TI
2251 [STAC_9205_DELL_M42] = dell_9205_m42_pin_configs,
2252 [STAC_9205_DELL_M43] = dell_9205_m43_pin_configs,
2253 [STAC_9205_DELL_M44] = dell_9205_m44_pin_configs,
f3302a59
MP
2254};
2255
f5fcc13c
TI
2256static const char *stac9205_models[STAC_9205_MODELS] = {
2257 [STAC_9205_REF] = "ref",
dfe495d0 2258 [STAC_9205_DELL_M42] = "dell-m42",
ae0a8ed8
TD
2259 [STAC_9205_DELL_M43] = "dell-m43",
2260 [STAC_9205_DELL_M44] = "dell-m44",
f5fcc13c
TI
2261};
2262
2263static struct snd_pci_quirk stac9205_cfg_tbl[] = {
2264 /* SigmaTel reference board */
2265 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
2266 "DFI LanParty", STAC_9205_REF),
dfe495d0
TI
2267 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f1,
2268 "unknown Dell", STAC_9205_DELL_M42),
2269 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f2,
2270 "unknown Dell", STAC_9205_DELL_M42),
ae0a8ed8 2271 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f8,
b44ef2f1 2272 "Dell Precision", STAC_9205_DELL_M43),
ae0a8ed8
TD
2273 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f9,
2274 "Dell Precision", STAC_9205_DELL_M43),
2275 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fa,
2276 "Dell Precision", STAC_9205_DELL_M43),
dfe495d0
TI
2277 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fc,
2278 "unknown Dell", STAC_9205_DELL_M42),
2279 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fd,
2280 "unknown Dell", STAC_9205_DELL_M42),
ae0a8ed8
TD
2281 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fe,
2282 "Dell Precision", STAC_9205_DELL_M43),
2283 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ff,
dfe495d0 2284 "Dell Precision M4300", STAC_9205_DELL_M43),
dfe495d0
TI
2285 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0204,
2286 "unknown Dell", STAC_9205_DELL_M42),
4549915c
TI
2287 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0206,
2288 "Dell Precision", STAC_9205_DELL_M43),
2289 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021b,
2290 "Dell Precision", STAC_9205_DELL_M43),
2291 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021c,
2292 "Dell Precision", STAC_9205_DELL_M43),
ae0a8ed8
TD
2293 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021f,
2294 "Dell Inspiron", STAC_9205_DELL_M44),
3fa2ef74
MR
2295 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0228,
2296 "Dell Vostro 1500", STAC_9205_DELL_M42),
f3302a59
MP
2297 {} /* terminator */
2298};
2299
11b44bbd
RF
2300static int stac92xx_save_bios_config_regs(struct hda_codec *codec)
2301{
2302 int i;
2303 struct sigmatel_spec *spec = codec->spec;
2304
af9f341a
TI
2305 kfree(spec->pin_configs);
2306 spec->pin_configs = kcalloc(spec->num_pins, sizeof(*spec->pin_configs),
2307 GFP_KERNEL);
2308 if (!spec->pin_configs)
2309 return -ENOMEM;
11b44bbd
RF
2310
2311 for (i = 0; i < spec->num_pins; i++) {
2312 hda_nid_t nid = spec->pin_nids[i];
2313 unsigned int pin_cfg;
2314
2315 pin_cfg = snd_hda_codec_read(codec, nid, 0,
2316 AC_VERB_GET_CONFIG_DEFAULT, 0x00);
2317 snd_printdd(KERN_INFO "hda_codec: pin nid %2.2x bios pin config %8.8x\n",
2318 nid, pin_cfg);
af9f341a 2319 spec->pin_configs[i] = pin_cfg;
11b44bbd
RF
2320 }
2321
2322 return 0;
2323}
2324
87d48363
MR
2325static void stac92xx_set_config_reg(struct hda_codec *codec,
2326 hda_nid_t pin_nid, unsigned int pin_config)
2327{
2328 int i;
2329 snd_hda_codec_write(codec, pin_nid, 0,
2330 AC_VERB_SET_CONFIG_DEFAULT_BYTES_0,
2331 pin_config & 0x000000ff);
2332 snd_hda_codec_write(codec, pin_nid, 0,
2333 AC_VERB_SET_CONFIG_DEFAULT_BYTES_1,
2334 (pin_config & 0x0000ff00) >> 8);
2335 snd_hda_codec_write(codec, pin_nid, 0,
2336 AC_VERB_SET_CONFIG_DEFAULT_BYTES_2,
2337 (pin_config & 0x00ff0000) >> 16);
2338 snd_hda_codec_write(codec, pin_nid, 0,
2339 AC_VERB_SET_CONFIG_DEFAULT_BYTES_3,
2340 pin_config >> 24);
2341 i = snd_hda_codec_read(codec, pin_nid, 0,
2342 AC_VERB_GET_CONFIG_DEFAULT,
2343 0x00);
2344 snd_printdd(KERN_INFO "hda_codec: pin nid %2.2x pin config %8.8x\n",
2345 pin_nid, i);
2346}
2347
2f2f4251
M
2348static void stac92xx_set_config_regs(struct hda_codec *codec)
2349{
2350 int i;
2351 struct sigmatel_spec *spec = codec->spec;
2f2f4251 2352
87d48363
MR
2353 if (!spec->pin_configs)
2354 return;
11b44bbd 2355
87d48363
MR
2356 for (i = 0; i < spec->num_pins; i++)
2357 stac92xx_set_config_reg(codec, spec->pin_nids[i],
2358 spec->pin_configs[i]);
2f2f4251 2359}
2f2f4251 2360
af9f341a
TI
2361static int stac_save_pin_cfgs(struct hda_codec *codec, unsigned int *pins)
2362{
2363 struct sigmatel_spec *spec = codec->spec;
2364
2365 if (!pins)
2366 return stac92xx_save_bios_config_regs(codec);
2367
2368 kfree(spec->pin_configs);
2369 spec->pin_configs = kmemdup(pins,
2370 spec->num_pins * sizeof(*pins),
2371 GFP_KERNEL);
2372 if (!spec->pin_configs)
2373 return -ENOMEM;
2374
2375 stac92xx_set_config_regs(codec);
2376 return 0;
2377}
2378
2379static void stac_change_pin_config(struct hda_codec *codec, hda_nid_t nid,
2380 unsigned int cfg)
2381{
2382 struct sigmatel_spec *spec = codec->spec;
2383 int i;
2384
2385 for (i = 0; i < spec->num_pins; i++) {
2386 if (spec->pin_nids[i] == nid) {
2387 spec->pin_configs[i] = cfg;
2388 stac92xx_set_config_reg(codec, nid, cfg);
2389 break;
2390 }
2391 }
2392}
2393
dabbed6f 2394/*
c7d4b2fa 2395 * Analog playback callbacks
dabbed6f 2396 */
c7d4b2fa
M
2397static int stac92xx_playback_pcm_open(struct hda_pcm_stream *hinfo,
2398 struct hda_codec *codec,
c8b6bf9b 2399 struct snd_pcm_substream *substream)
2f2f4251 2400{
dabbed6f 2401 struct sigmatel_spec *spec = codec->spec;
8daaaa97
MR
2402 if (spec->stream_delay)
2403 msleep(spec->stream_delay);
9a08160b
TI
2404 return snd_hda_multi_out_analog_open(codec, &spec->multiout, substream,
2405 hinfo);
2f2f4251
M
2406}
2407
2f2f4251
M
2408static int stac92xx_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
2409 struct hda_codec *codec,
2410 unsigned int stream_tag,
2411 unsigned int format,
c8b6bf9b 2412 struct snd_pcm_substream *substream)
2f2f4251
M
2413{
2414 struct sigmatel_spec *spec = codec->spec;
403d1944 2415 return snd_hda_multi_out_analog_prepare(codec, &spec->multiout, stream_tag, format, substream);
2f2f4251
M
2416}
2417
2418static int stac92xx_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
2419 struct hda_codec *codec,
c8b6bf9b 2420 struct snd_pcm_substream *substream)
2f2f4251
M
2421{
2422 struct sigmatel_spec *spec = codec->spec;
2423 return snd_hda_multi_out_analog_cleanup(codec, &spec->multiout);
2424}
2425
dabbed6f
M
2426/*
2427 * Digital playback callbacks
2428 */
2429static int stac92xx_dig_playback_pcm_open(struct hda_pcm_stream *hinfo,
2430 struct hda_codec *codec,
c8b6bf9b 2431 struct snd_pcm_substream *substream)
dabbed6f
M
2432{
2433 struct sigmatel_spec *spec = codec->spec;
2434 return snd_hda_multi_out_dig_open(codec, &spec->multiout);
2435}
2436
2437static int stac92xx_dig_playback_pcm_close(struct hda_pcm_stream *hinfo,
2438 struct hda_codec *codec,
c8b6bf9b 2439 struct snd_pcm_substream *substream)
dabbed6f
M
2440{
2441 struct sigmatel_spec *spec = codec->spec;
2442 return snd_hda_multi_out_dig_close(codec, &spec->multiout);
2443}
2444
6b97eb45
TI
2445static int stac92xx_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
2446 struct hda_codec *codec,
2447 unsigned int stream_tag,
2448 unsigned int format,
2449 struct snd_pcm_substream *substream)
2450{
2451 struct sigmatel_spec *spec = codec->spec;
2452 return snd_hda_multi_out_dig_prepare(codec, &spec->multiout,
2453 stream_tag, format, substream);
2454}
2455
dabbed6f 2456
2f2f4251
M
2457/*
2458 * Analog capture callbacks
2459 */
2460static int stac92xx_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
2461 struct hda_codec *codec,
2462 unsigned int stream_tag,
2463 unsigned int format,
c8b6bf9b 2464 struct snd_pcm_substream *substream)
2f2f4251
M
2465{
2466 struct sigmatel_spec *spec = codec->spec;
8daaaa97 2467 hda_nid_t nid = spec->adc_nids[substream->number];
2f2f4251 2468
8daaaa97
MR
2469 if (spec->powerdown_adcs) {
2470 msleep(40);
2471 snd_hda_codec_write_cache(codec, nid, 0,
2472 AC_VERB_SET_POWER_STATE, AC_PWRST_D0);
2473 }
2474 snd_hda_codec_setup_stream(codec, nid, stream_tag, 0, format);
2f2f4251
M
2475 return 0;
2476}
2477
2478static int stac92xx_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
2479 struct hda_codec *codec,
c8b6bf9b 2480 struct snd_pcm_substream *substream)
2f2f4251
M
2481{
2482 struct sigmatel_spec *spec = codec->spec;
8daaaa97 2483 hda_nid_t nid = spec->adc_nids[substream->number];
2f2f4251 2484
8daaaa97
MR
2485 snd_hda_codec_cleanup_stream(codec, nid);
2486 if (spec->powerdown_adcs)
2487 snd_hda_codec_write_cache(codec, nid, 0,
2488 AC_VERB_SET_POWER_STATE, AC_PWRST_D3);
2f2f4251
M
2489 return 0;
2490}
2491
dabbed6f
M
2492static struct hda_pcm_stream stac92xx_pcm_digital_playback = {
2493 .substreams = 1,
2494 .channels_min = 2,
2495 .channels_max = 2,
2496 /* NID is set in stac92xx_build_pcms */
2497 .ops = {
2498 .open = stac92xx_dig_playback_pcm_open,
6b97eb45
TI
2499 .close = stac92xx_dig_playback_pcm_close,
2500 .prepare = stac92xx_dig_playback_pcm_prepare
dabbed6f
M
2501 },
2502};
2503
2504static struct hda_pcm_stream stac92xx_pcm_digital_capture = {
2505 .substreams = 1,
2506 .channels_min = 2,
2507 .channels_max = 2,
2508 /* NID is set in stac92xx_build_pcms */
2509};
2510
2f2f4251
M
2511static struct hda_pcm_stream stac92xx_pcm_analog_playback = {
2512 .substreams = 1,
2513 .channels_min = 2,
c7d4b2fa 2514 .channels_max = 8,
2f2f4251
M
2515 .nid = 0x02, /* NID to query formats and rates */
2516 .ops = {
2517 .open = stac92xx_playback_pcm_open,
2518 .prepare = stac92xx_playback_pcm_prepare,
2519 .cleanup = stac92xx_playback_pcm_cleanup
2520 },
2521};
2522
3cc08dc6
MP
2523static struct hda_pcm_stream stac92xx_pcm_analog_alt_playback = {
2524 .substreams = 1,
2525 .channels_min = 2,
2526 .channels_max = 2,
2527 .nid = 0x06, /* NID to query formats and rates */
2528 .ops = {
2529 .open = stac92xx_playback_pcm_open,
2530 .prepare = stac92xx_playback_pcm_prepare,
2531 .cleanup = stac92xx_playback_pcm_cleanup
2532 },
2533};
2534
2f2f4251 2535static struct hda_pcm_stream stac92xx_pcm_analog_capture = {
2f2f4251
M
2536 .channels_min = 2,
2537 .channels_max = 2,
9e05b7a3 2538 /* NID + .substreams is set in stac92xx_build_pcms */
2f2f4251
M
2539 .ops = {
2540 .prepare = stac92xx_capture_pcm_prepare,
2541 .cleanup = stac92xx_capture_pcm_cleanup
2542 },
2543};
2544
2545static int stac92xx_build_pcms(struct hda_codec *codec)
2546{
2547 struct sigmatel_spec *spec = codec->spec;
2548 struct hda_pcm *info = spec->pcm_rec;
2549
2550 codec->num_pcms = 1;
2551 codec->pcm_info = info;
2552
c7d4b2fa 2553 info->name = "STAC92xx Analog";
2f2f4251 2554 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = stac92xx_pcm_analog_playback;
2f2f4251 2555 info->stream[SNDRV_PCM_STREAM_CAPTURE] = stac92xx_pcm_analog_capture;
3cc08dc6 2556 info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->adc_nids[0];
9e05b7a3 2557 info->stream[SNDRV_PCM_STREAM_CAPTURE].substreams = spec->num_adcs;
3cc08dc6
MP
2558
2559 if (spec->alt_switch) {
2560 codec->num_pcms++;
2561 info++;
2562 info->name = "STAC92xx Analog Alt";
2563 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = stac92xx_pcm_analog_alt_playback;
2564 }
2f2f4251 2565
dabbed6f
M
2566 if (spec->multiout.dig_out_nid || spec->dig_in_nid) {
2567 codec->num_pcms++;
2568 info++;
2569 info->name = "STAC92xx Digital";
7ba72ba1 2570 info->pcm_type = HDA_PCM_TYPE_SPDIF;
dabbed6f
M
2571 if (spec->multiout.dig_out_nid) {
2572 info->stream[SNDRV_PCM_STREAM_PLAYBACK] = stac92xx_pcm_digital_playback;
2573 info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dig_out_nid;
2574 }
2575 if (spec->dig_in_nid) {
2576 info->stream[SNDRV_PCM_STREAM_CAPTURE] = stac92xx_pcm_digital_capture;
2577 info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->dig_in_nid;
2578 }
2579 }
2580
2f2f4251
M
2581 return 0;
2582}
2583
c960a03b
TI
2584static unsigned int stac92xx_get_vref(struct hda_codec *codec, hda_nid_t nid)
2585{
2586 unsigned int pincap = snd_hda_param_read(codec, nid,
2587 AC_PAR_PIN_CAP);
2588 pincap = (pincap & AC_PINCAP_VREF) >> AC_PINCAP_VREF_SHIFT;
2589 if (pincap & AC_PINCAP_VREF_100)
2590 return AC_PINCTL_VREF_100;
2591 if (pincap & AC_PINCAP_VREF_80)
2592 return AC_PINCTL_VREF_80;
2593 if (pincap & AC_PINCAP_VREF_50)
2594 return AC_PINCTL_VREF_50;
2595 if (pincap & AC_PINCAP_VREF_GRD)
2596 return AC_PINCTL_VREF_GRD;
2597 return 0;
2598}
2599
403d1944
MP
2600static void stac92xx_auto_set_pinctl(struct hda_codec *codec, hda_nid_t nid, int pin_type)
2601
2602{
82beb8fd
TI
2603 snd_hda_codec_write_cache(codec, nid, 0,
2604 AC_VERB_SET_PIN_WIDGET_CONTROL, pin_type);
403d1944
MP
2605}
2606
7c2ba97b
MR
2607#define stac92xx_hp_switch_info snd_ctl_boolean_mono_info
2608
2609static int stac92xx_hp_switch_get(struct snd_kcontrol *kcontrol,
2610 struct snd_ctl_elem_value *ucontrol)
2611{
2612 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2613 struct sigmatel_spec *spec = codec->spec;
2614
d7a89436 2615 ucontrol->value.integer.value[0] = !!spec->hp_switch;
7c2ba97b
MR
2616 return 0;
2617}
2618
c6e4c666
TI
2619static void stac_issue_unsol_event(struct hda_codec *codec, hda_nid_t nid,
2620 unsigned char type);
2621
7c2ba97b
MR
2622static int stac92xx_hp_switch_put(struct snd_kcontrol *kcontrol,
2623 struct snd_ctl_elem_value *ucontrol)
2624{
2625 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2626 struct sigmatel_spec *spec = codec->spec;
d7a89436
TI
2627 int nid = kcontrol->private_value;
2628
2629 spec->hp_switch = ucontrol->value.integer.value[0] ? nid : 0;
7c2ba97b
MR
2630
2631 /* check to be sure that the ports are upto date with
2632 * switch changes
2633 */
c6e4c666 2634 stac_issue_unsol_event(codec, nid, STAC_HP_EVENT);
7c2ba97b
MR
2635
2636 return 1;
2637}
2638
a5ce8890 2639#define stac92xx_io_switch_info snd_ctl_boolean_mono_info
403d1944
MP
2640
2641static int stac92xx_io_switch_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
2642{
2643 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2644 struct sigmatel_spec *spec = codec->spec;
2645 int io_idx = kcontrol-> private_value & 0xff;
2646
2647 ucontrol->value.integer.value[0] = spec->io_switch[io_idx];
2648 return 0;
2649}
2650
2651static int stac92xx_io_switch_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
2652{
2653 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2654 struct sigmatel_spec *spec = codec->spec;
2655 hda_nid_t nid = kcontrol->private_value >> 8;
2656 int io_idx = kcontrol-> private_value & 0xff;
68ea7b2f 2657 unsigned short val = !!ucontrol->value.integer.value[0];
403d1944
MP
2658
2659 spec->io_switch[io_idx] = val;
2660
2661 if (val)
2662 stac92xx_auto_set_pinctl(codec, nid, AC_PINCTL_OUT_EN);
c960a03b
TI
2663 else {
2664 unsigned int pinctl = AC_PINCTL_IN_EN;
2665 if (io_idx) /* set VREF for mic */
2666 pinctl |= stac92xx_get_vref(codec, nid);
2667 stac92xx_auto_set_pinctl(codec, nid, pinctl);
2668 }
40c1d308
JZ
2669
2670 /* check the auto-mute again: we need to mute/unmute the speaker
2671 * appropriately according to the pin direction
2672 */
2673 if (spec->hp_detect)
c6e4c666 2674 stac_issue_unsol_event(codec, nid, STAC_HP_EVENT);
40c1d308 2675
403d1944
MP
2676 return 1;
2677}
2678
0fb87bb4
ML
2679#define stac92xx_clfe_switch_info snd_ctl_boolean_mono_info
2680
2681static int stac92xx_clfe_switch_get(struct snd_kcontrol *kcontrol,
2682 struct snd_ctl_elem_value *ucontrol)
2683{
2684 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2685 struct sigmatel_spec *spec = codec->spec;
2686
2687 ucontrol->value.integer.value[0] = spec->clfe_swap;
2688 return 0;
2689}
2690
2691static int stac92xx_clfe_switch_put(struct snd_kcontrol *kcontrol,
2692 struct snd_ctl_elem_value *ucontrol)
2693{
2694 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2695 struct sigmatel_spec *spec = codec->spec;
2696 hda_nid_t nid = kcontrol->private_value & 0xff;
68ea7b2f 2697 unsigned int val = !!ucontrol->value.integer.value[0];
0fb87bb4 2698
68ea7b2f 2699 if (spec->clfe_swap == val)
0fb87bb4
ML
2700 return 0;
2701
68ea7b2f 2702 spec->clfe_swap = val;
0fb87bb4
ML
2703
2704 snd_hda_codec_write_cache(codec, nid, 0, AC_VERB_SET_EAPD_BTLENABLE,
2705 spec->clfe_swap ? 0x4 : 0x0);
2706
2707 return 1;
2708}
2709
7c2ba97b
MR
2710#define STAC_CODEC_HP_SWITCH(xname) \
2711 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2712 .name = xname, \
2713 .index = 0, \
2714 .info = stac92xx_hp_switch_info, \
2715 .get = stac92xx_hp_switch_get, \
2716 .put = stac92xx_hp_switch_put, \
2717 }
2718
403d1944
MP
2719#define STAC_CODEC_IO_SWITCH(xname, xpval) \
2720 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2721 .name = xname, \
2722 .index = 0, \
2723 .info = stac92xx_io_switch_info, \
2724 .get = stac92xx_io_switch_get, \
2725 .put = stac92xx_io_switch_put, \
2726 .private_value = xpval, \
2727 }
2728
0fb87bb4
ML
2729#define STAC_CODEC_CLFE_SWITCH(xname, xpval) \
2730 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2731 .name = xname, \
2732 .index = 0, \
2733 .info = stac92xx_clfe_switch_info, \
2734 .get = stac92xx_clfe_switch_get, \
2735 .put = stac92xx_clfe_switch_put, \
2736 .private_value = xpval, \
2737 }
403d1944 2738
c7d4b2fa
M
2739enum {
2740 STAC_CTL_WIDGET_VOL,
2741 STAC_CTL_WIDGET_MUTE,
09a99959 2742 STAC_CTL_WIDGET_MONO_MUX,
89385035
MR
2743 STAC_CTL_WIDGET_AMP_MUX,
2744 STAC_CTL_WIDGET_AMP_VOL,
7c2ba97b 2745 STAC_CTL_WIDGET_HP_SWITCH,
403d1944 2746 STAC_CTL_WIDGET_IO_SWITCH,
0fb87bb4 2747 STAC_CTL_WIDGET_CLFE_SWITCH
c7d4b2fa
M
2748};
2749
c8b6bf9b 2750static struct snd_kcontrol_new stac92xx_control_templates[] = {
c7d4b2fa
M
2751 HDA_CODEC_VOLUME(NULL, 0, 0, 0),
2752 HDA_CODEC_MUTE(NULL, 0, 0, 0),
09a99959 2753 STAC_MONO_MUX,
89385035
MR
2754 STAC_AMP_MUX,
2755 STAC_AMP_VOL(NULL, 0, 0, 0, 0),
7c2ba97b 2756 STAC_CODEC_HP_SWITCH(NULL),
403d1944 2757 STAC_CODEC_IO_SWITCH(NULL, 0),
0fb87bb4 2758 STAC_CODEC_CLFE_SWITCH(NULL, 0),
c7d4b2fa
M
2759};
2760
2761/* add dynamic controls */
4d4e9bb3
TI
2762static int stac92xx_add_control_temp(struct sigmatel_spec *spec,
2763 struct snd_kcontrol_new *ktemp,
2764 int idx, const char *name,
2765 unsigned long val)
c7d4b2fa 2766{
c8b6bf9b 2767 struct snd_kcontrol_new *knew;
c7d4b2fa 2768
603c4019
TI
2769 snd_array_init(&spec->kctls, sizeof(*knew), 32);
2770 knew = snd_array_new(&spec->kctls);
2771 if (!knew)
2772 return -ENOMEM;
4d4e9bb3 2773 *knew = *ktemp;
4682eee0 2774 knew->index = idx;
82fe0c58 2775 knew->name = kstrdup(name, GFP_KERNEL);
4d4e9bb3 2776 if (!knew->name)
c7d4b2fa
M
2777 return -ENOMEM;
2778 knew->private_value = val;
c7d4b2fa
M
2779 return 0;
2780}
2781
4d4e9bb3
TI
2782static inline int stac92xx_add_control_idx(struct sigmatel_spec *spec,
2783 int type, int idx, const char *name,
2784 unsigned long val)
2785{
2786 return stac92xx_add_control_temp(spec,
2787 &stac92xx_control_templates[type],
2788 idx, name, val);
2789}
2790
4682eee0
MR
2791
2792/* add dynamic controls */
4d4e9bb3
TI
2793static inline int stac92xx_add_control(struct sigmatel_spec *spec, int type,
2794 const char *name, unsigned long val)
4682eee0
MR
2795{
2796 return stac92xx_add_control_idx(spec, type, 0, name, val);
2797}
2798
403d1944
MP
2799/* flag inputs as additional dynamic lineouts */
2800static int stac92xx_add_dyn_out_pins(struct hda_codec *codec, struct auto_pin_cfg *cfg)
2801{
2802 struct sigmatel_spec *spec = codec->spec;
7b043899
SL
2803 unsigned int wcaps, wtype;
2804 int i, num_dacs = 0;
2805
2806 /* use the wcaps cache to count all DACs available for line-outs */
2807 for (i = 0; i < codec->num_nodes; i++) {
2808 wcaps = codec->wcaps[i];
2809 wtype = (wcaps & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT;
8e9068b1 2810
7b043899
SL
2811 if (wtype == AC_WID_AUD_OUT && !(wcaps & AC_WCAP_DIGITAL))
2812 num_dacs++;
2813 }
403d1944 2814
7b043899
SL
2815 snd_printdd("%s: total dac count=%d\n", __func__, num_dacs);
2816
403d1944
MP
2817 switch (cfg->line_outs) {
2818 case 3:
2819 /* add line-in as side */
7b043899 2820 if (cfg->input_pins[AUTO_PIN_LINE] && num_dacs > 3) {
c480f79b
TI
2821 cfg->line_out_pins[cfg->line_outs] =
2822 cfg->input_pins[AUTO_PIN_LINE];
403d1944
MP
2823 spec->line_switch = 1;
2824 cfg->line_outs++;
2825 }
2826 break;
2827 case 2:
2828 /* add line-in as clfe and mic as side */
7b043899 2829 if (cfg->input_pins[AUTO_PIN_LINE] && num_dacs > 2) {
c480f79b
TI
2830 cfg->line_out_pins[cfg->line_outs] =
2831 cfg->input_pins[AUTO_PIN_LINE];
403d1944
MP
2832 spec->line_switch = 1;
2833 cfg->line_outs++;
2834 }
7b043899 2835 if (cfg->input_pins[AUTO_PIN_MIC] && num_dacs > 3) {
c480f79b
TI
2836 cfg->line_out_pins[cfg->line_outs] =
2837 cfg->input_pins[AUTO_PIN_MIC];
403d1944
MP
2838 spec->mic_switch = 1;
2839 cfg->line_outs++;
2840 }
2841 break;
2842 case 1:
2843 /* add line-in as surr and mic as clfe */
7b043899 2844 if (cfg->input_pins[AUTO_PIN_LINE] && num_dacs > 1) {
c480f79b
TI
2845 cfg->line_out_pins[cfg->line_outs] =
2846 cfg->input_pins[AUTO_PIN_LINE];
403d1944
MP
2847 spec->line_switch = 1;
2848 cfg->line_outs++;
2849 }
7b043899 2850 if (cfg->input_pins[AUTO_PIN_MIC] && num_dacs > 2) {
c480f79b
TI
2851 cfg->line_out_pins[cfg->line_outs] =
2852 cfg->input_pins[AUTO_PIN_MIC];
403d1944
MP
2853 spec->mic_switch = 1;
2854 cfg->line_outs++;
2855 }
2856 break;
2857 }
2858
2859 return 0;
2860}
2861
7b043899
SL
2862
2863static int is_in_dac_nids(struct sigmatel_spec *spec, hda_nid_t nid)
2864{
2865 int i;
2866
2867 for (i = 0; i < spec->multiout.num_dacs; i++) {
2868 if (spec->multiout.dac_nids[i] == nid)
2869 return 1;
2870 }
2871
2872 return 0;
2873}
2874
3cc08dc6 2875/*
7b043899
SL
2876 * Fill in the dac_nids table from the parsed pin configuration
2877 * This function only works when every pin in line_out_pins[]
2878 * contains atleast one DAC in its connection list. Some 92xx
2879 * codecs are not connected directly to a DAC, such as the 9200
2880 * and 9202/925x. For those, dac_nids[] must be hard-coded.
3cc08dc6 2881 */
19039bd0 2882static int stac92xx_auto_fill_dac_nids(struct hda_codec *codec,
df802952 2883 struct auto_pin_cfg *cfg)
c7d4b2fa
M
2884{
2885 struct sigmatel_spec *spec = codec->spec;
7b043899
SL
2886 int i, j, conn_len = 0;
2887 hda_nid_t nid, conn[HDA_MAX_CONNECTIONS];
2888 unsigned int wcaps, wtype;
2889
c7d4b2fa
M
2890 for (i = 0; i < cfg->line_outs; i++) {
2891 nid = cfg->line_out_pins[i];
7b043899
SL
2892 conn_len = snd_hda_get_connections(codec, nid, conn,
2893 HDA_MAX_CONNECTIONS);
2894 for (j = 0; j < conn_len; j++) {
2895 wcaps = snd_hda_param_read(codec, conn[j],
2896 AC_PAR_AUDIO_WIDGET_CAP);
2897 wtype = (wcaps & AC_WCAP_TYPE) >> AC_WCAP_TYPE_SHIFT;
7b043899
SL
2898 if (wtype != AC_WID_AUD_OUT ||
2899 (wcaps & AC_WCAP_DIGITAL))
2900 continue;
2901 /* conn[j] is a DAC routed to this line-out */
2902 if (!is_in_dac_nids(spec, conn[j]))
2903 break;
2904 }
2905
2906 if (j == conn_len) {
df802952
TI
2907 if (spec->multiout.num_dacs > 0) {
2908 /* we have already working output pins,
2909 * so let's drop the broken ones again
2910 */
2911 cfg->line_outs = spec->multiout.num_dacs;
2912 break;
2913 }
7b043899
SL
2914 /* error out, no available DAC found */
2915 snd_printk(KERN_ERR
2916 "%s: No available DAC for pin 0x%x\n",
2917 __func__, nid);
2918 return -ENODEV;
2919 }
2920
2921 spec->multiout.dac_nids[i] = conn[j];
2922 spec->multiout.num_dacs++;
2923 if (conn_len > 1) {
2924 /* select this DAC in the pin's input mux */
82beb8fd
TI
2925 snd_hda_codec_write_cache(codec, nid, 0,
2926 AC_VERB_SET_CONNECT_SEL, j);
c7d4b2fa 2927
7b043899
SL
2928 }
2929 }
c7d4b2fa 2930
7b043899
SL
2931 snd_printd("dac_nids=%d (0x%x/0x%x/0x%x/0x%x/0x%x)\n",
2932 spec->multiout.num_dacs,
2933 spec->multiout.dac_nids[0],
2934 spec->multiout.dac_nids[1],
2935 spec->multiout.dac_nids[2],
2936 spec->multiout.dac_nids[3],
2937 spec->multiout.dac_nids[4]);
c7d4b2fa
M
2938 return 0;
2939}
2940
eb06ed8f
TI
2941/* create volume control/switch for the given prefx type */
2942static int create_controls(struct sigmatel_spec *spec, const char *pfx, hda_nid_t nid, int chs)
2943{
2944 char name[32];
2945 int err;
2946
2947 sprintf(name, "%s Playback Volume", pfx);
2948 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_VOL, name,
2949 HDA_COMPOSE_AMP_VAL(nid, chs, 0, HDA_OUTPUT));
2950 if (err < 0)
2951 return err;
2952 sprintf(name, "%s Playback Switch", pfx);
2953 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_MUTE, name,
2954 HDA_COMPOSE_AMP_VAL(nid, chs, 0, HDA_OUTPUT));
2955 if (err < 0)
2956 return err;
2957 return 0;
2958}
2959
ae0afd81
MR
2960static int add_spec_dacs(struct sigmatel_spec *spec, hda_nid_t nid)
2961{
2962 if (!spec->multiout.hp_nid)
2963 spec->multiout.hp_nid = nid;
2964 else if (spec->multiout.num_dacs > 4) {
2965 printk(KERN_WARNING "stac92xx: No space for DAC 0x%x\n", nid);
2966 return 1;
2967 } else {
2968 spec->multiout.dac_nids[spec->multiout.num_dacs] = nid;
2969 spec->multiout.num_dacs++;
2970 }
2971 return 0;
2972}
2973
2974static int check_in_dac_nids(struct sigmatel_spec *spec, hda_nid_t nid)
2975{
2976 if (is_in_dac_nids(spec, nid))
2977 return 1;
2978 if (spec->multiout.hp_nid == nid)
2979 return 1;
2980 return 0;
2981}
2982
c7d4b2fa 2983/* add playback controls from the parsed DAC table */
0fb87bb4 2984static int stac92xx_auto_create_multi_out_ctls(struct hda_codec *codec,
19039bd0 2985 const struct auto_pin_cfg *cfg)
c7d4b2fa 2986{
19039bd0
TI
2987 static const char *chname[4] = {
2988 "Front", "Surround", NULL /*CLFE*/, "Side"
2989 };
d21995e3 2990 hda_nid_t nid = 0;
c7d4b2fa
M
2991 int i, err;
2992
0fb87bb4 2993 struct sigmatel_spec *spec = codec->spec;
b5895dc8 2994 unsigned int wid_caps, pincap;
0fb87bb4
ML
2995
2996
40ac8c4f 2997 for (i = 0; i < cfg->line_outs && i < spec->multiout.num_dacs; i++) {
403d1944 2998 if (!spec->multiout.dac_nids[i])
c7d4b2fa
M
2999 continue;
3000
3001 nid = spec->multiout.dac_nids[i];
3002
3003 if (i == 2) {
3004 /* Center/LFE */
eb06ed8f
TI
3005 err = create_controls(spec, "Center", nid, 1);
3006 if (err < 0)
c7d4b2fa 3007 return err;
eb06ed8f
TI
3008 err = create_controls(spec, "LFE", nid, 2);
3009 if (err < 0)
c7d4b2fa 3010 return err;
0fb87bb4
ML
3011
3012 wid_caps = get_wcaps(codec, nid);
3013
3014 if (wid_caps & AC_WCAP_LR_SWAP) {
3015 err = stac92xx_add_control(spec,
3016 STAC_CTL_WIDGET_CLFE_SWITCH,
3017 "Swap Center/LFE Playback Switch", nid);
3018
3019 if (err < 0)
3020 return err;
3021 }
3022
c7d4b2fa 3023 } else {
eb06ed8f
TI
3024 err = create_controls(spec, chname[i], nid, 3);
3025 if (err < 0)
c7d4b2fa
M
3026 return err;
3027 }
3028 }
3029
fedb7569
MR
3030 if ((spec->multiout.num_dacs - cfg->line_outs) > 0 &&
3031 cfg->hp_outs && !spec->multiout.hp_nid)
3032 spec->multiout.hp_nid = nid;
3033
a9cb5c90 3034 if (cfg->hp_outs > 1 && cfg->line_out_type == AUTO_PIN_LINE_OUT) {
7c2ba97b
MR
3035 err = stac92xx_add_control(spec,
3036 STAC_CTL_WIDGET_HP_SWITCH,
d7a89436
TI
3037 "Headphone as Line Out Switch",
3038 cfg->hp_pins[cfg->hp_outs - 1]);
7c2ba97b
MR
3039 if (err < 0)
3040 return err;
3041 }
3042
b5895dc8
MR
3043 if (spec->line_switch) {
3044 nid = cfg->input_pins[AUTO_PIN_LINE];
3045 pincap = snd_hda_param_read(codec, nid,
3046 AC_PAR_PIN_CAP);
3047 if (pincap & AC_PINCAP_OUT) {
3048 err = stac92xx_add_control(spec,
3049 STAC_CTL_WIDGET_IO_SWITCH,
3050 "Line In as Output Switch", nid << 8);
3051 if (err < 0)
3052 return err;
3053 }
3054 }
403d1944 3055
b5895dc8 3056 if (spec->mic_switch) {
cace16f1 3057 unsigned int def_conf;
ae0afd81
MR
3058 unsigned int mic_pin = AUTO_PIN_MIC;
3059again:
3060 nid = cfg->input_pins[mic_pin];
cace16f1
MR
3061 def_conf = snd_hda_codec_read(codec, nid, 0,
3062 AC_VERB_GET_CONFIG_DEFAULT, 0);
cace16f1
MR
3063 /* some laptops have an internal analog microphone
3064 * which can't be used as a output */
3065 if (get_defcfg_connect(def_conf) != AC_JACK_PORT_FIXED) {
3066 pincap = snd_hda_param_read(codec, nid,
3067 AC_PAR_PIN_CAP);
3068 if (pincap & AC_PINCAP_OUT) {
3069 err = stac92xx_add_control(spec,
3070 STAC_CTL_WIDGET_IO_SWITCH,
3071 "Mic as Output Switch", (nid << 8) | 1);
ae0afd81
MR
3072 nid = snd_hda_codec_read(codec, nid, 0,
3073 AC_VERB_GET_CONNECT_LIST, 0) & 0xff;
3074 if (!check_in_dac_nids(spec, nid))
3075 add_spec_dacs(spec, nid);
cace16f1
MR
3076 if (err < 0)
3077 return err;
3078 }
ae0afd81
MR
3079 } else if (mic_pin == AUTO_PIN_MIC) {
3080 mic_pin = AUTO_PIN_FRONT_MIC;
3081 goto again;
b5895dc8
MR
3082 }
3083 }
403d1944 3084
c7d4b2fa
M
3085 return 0;
3086}
3087
eb06ed8f
TI
3088/* add playback controls for Speaker and HP outputs */
3089static int stac92xx_auto_create_hp_ctls(struct hda_codec *codec,
3090 struct auto_pin_cfg *cfg)
3091{
3092 struct sigmatel_spec *spec = codec->spec;
3093 hda_nid_t nid;
3094 int i, old_num_dacs, err;
3095
3096 old_num_dacs = spec->multiout.num_dacs;
3097 for (i = 0; i < cfg->hp_outs; i++) {
3098 unsigned int wid_caps = get_wcaps(codec, cfg->hp_pins[i]);
3099 if (wid_caps & AC_WCAP_UNSOL_CAP)
3100 spec->hp_detect = 1;
3101 nid = snd_hda_codec_read(codec, cfg->hp_pins[i], 0,
3102 AC_VERB_GET_CONNECT_LIST, 0) & 0xff;
3103 if (check_in_dac_nids(spec, nid))
3104 nid = 0;
3105 if (! nid)
c7d4b2fa 3106 continue;
eb06ed8f
TI
3107 add_spec_dacs(spec, nid);
3108 }
3109 for (i = 0; i < cfg->speaker_outs; i++) {
7b043899 3110 nid = snd_hda_codec_read(codec, cfg->speaker_pins[i], 0,
eb06ed8f
TI
3111 AC_VERB_GET_CONNECT_LIST, 0) & 0xff;
3112 if (check_in_dac_nids(spec, nid))
3113 nid = 0;
eb06ed8f
TI
3114 if (! nid)
3115 continue;
3116 add_spec_dacs(spec, nid);
c7d4b2fa 3117 }
1b290a51
MR
3118 for (i = 0; i < cfg->line_outs; i++) {
3119 nid = snd_hda_codec_read(codec, cfg->line_out_pins[i], 0,
3120 AC_VERB_GET_CONNECT_LIST, 0) & 0xff;
3121 if (check_in_dac_nids(spec, nid))
3122 nid = 0;
3123 if (! nid)
3124 continue;
3125 add_spec_dacs(spec, nid);
3126 }
eb06ed8f
TI
3127 for (i = old_num_dacs; i < spec->multiout.num_dacs; i++) {
3128 static const char *pfxs[] = {
3129 "Speaker", "External Speaker", "Speaker2",
3130 };
3131 err = create_controls(spec, pfxs[i - old_num_dacs],
3132 spec->multiout.dac_nids[i], 3);
3133 if (err < 0)
3134 return err;
3135 }
3136 if (spec->multiout.hp_nid) {
2626a263
TI
3137 err = create_controls(spec, "Headphone",
3138 spec->multiout.hp_nid, 3);
eb06ed8f
TI
3139 if (err < 0)
3140 return err;
3141 }
c7d4b2fa
M
3142
3143 return 0;
3144}
3145
b22b4821 3146/* labels for mono mux outputs */
d0513fc6
MR
3147static const char *stac92xx_mono_labels[4] = {
3148 "DAC0", "DAC1", "Mixer", "DAC2"
b22b4821
MR
3149};
3150
3151/* create mono mux for mono out on capable codecs */
3152static int stac92xx_auto_create_mono_output_ctls(struct hda_codec *codec)
3153{
3154 struct sigmatel_spec *spec = codec->spec;
3155 struct hda_input_mux *mono_mux = &spec->private_mono_mux;
3156 int i, num_cons;
3157 hda_nid_t con_lst[ARRAY_SIZE(stac92xx_mono_labels)];
3158
3159 num_cons = snd_hda_get_connections(codec,
3160 spec->mono_nid,
3161 con_lst,
3162 HDA_MAX_NUM_INPUTS);
3163 if (!num_cons || num_cons > ARRAY_SIZE(stac92xx_mono_labels))
3164 return -EINVAL;
3165
3166 for (i = 0; i < num_cons; i++) {
3167 mono_mux->items[mono_mux->num_items].label =
3168 stac92xx_mono_labels[i];
3169 mono_mux->items[mono_mux->num_items].index = i;
3170 mono_mux->num_items++;
3171 }
09a99959
MR
3172
3173 return stac92xx_add_control(spec, STAC_CTL_WIDGET_MONO_MUX,
3174 "Mono Mux", spec->mono_nid);
b22b4821
MR
3175}
3176
89385035
MR
3177/* labels for amp mux outputs */
3178static const char *stac92xx_amp_labels[3] = {
4b33c767 3179 "Front Microphone", "Microphone", "Line In",
89385035
MR
3180};
3181
3182/* create amp out controls mux on capable codecs */
3183static int stac92xx_auto_create_amp_output_ctls(struct hda_codec *codec)
3184{
3185 struct sigmatel_spec *spec = codec->spec;
3186 struct hda_input_mux *amp_mux = &spec->private_amp_mux;
3187 int i, err;
3188
2a9c7816 3189 for (i = 0; i < spec->num_amps; i++) {
89385035
MR
3190 amp_mux->items[amp_mux->num_items].label =
3191 stac92xx_amp_labels[i];
3192 amp_mux->items[amp_mux->num_items].index = i;
3193 amp_mux->num_items++;
3194 }
3195
2a9c7816
MR
3196 if (spec->num_amps > 1) {
3197 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_AMP_MUX,
3198 "Amp Selector Capture Switch", 0);
3199 if (err < 0)
3200 return err;
3201 }
89385035
MR
3202 return stac92xx_add_control(spec, STAC_CTL_WIDGET_AMP_VOL,
3203 "Amp Capture Volume",
3204 HDA_COMPOSE_AMP_VAL(spec->amp_nids[0], 3, 0, HDA_INPUT));
3205}
3206
3207
1cd2224c
MR
3208/* create PC beep volume controls */
3209static int stac92xx_auto_create_beep_ctls(struct hda_codec *codec,
3210 hda_nid_t nid)
3211{
3212 struct sigmatel_spec *spec = codec->spec;
3213 u32 caps = query_amp_caps(codec, nid, HDA_OUTPUT);
3214 int err;
3215
3216 /* check for mute support for the the amp */
3217 if ((caps & AC_AMPCAP_MUTE) >> AC_AMPCAP_MUTE_SHIFT) {
3218 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_MUTE,
3219 "PC Beep Playback Switch",
3220 HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT));
3221 if (err < 0)
3222 return err;
3223 }
3224
3225 /* check to see if there is volume support for the amp */
3226 if ((caps & AC_AMPCAP_NUM_STEPS) >> AC_AMPCAP_NUM_STEPS_SHIFT) {
3227 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_VOL,
3228 "PC Beep Playback Volume",
3229 HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT));
3230 if (err < 0)
3231 return err;
3232 }
3233 return 0;
3234}
3235
4d4e9bb3
TI
3236#ifdef CONFIG_SND_HDA_INPUT_BEEP
3237#define stac92xx_dig_beep_switch_info snd_ctl_boolean_mono_info
3238
3239static int stac92xx_dig_beep_switch_get(struct snd_kcontrol *kcontrol,
3240 struct snd_ctl_elem_value *ucontrol)
3241{
3242 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
3243 ucontrol->value.integer.value[0] = codec->beep->enabled;
3244 return 0;
3245}
3246
3247static int stac92xx_dig_beep_switch_put(struct snd_kcontrol *kcontrol,
3248 struct snd_ctl_elem_value *ucontrol)
3249{
3250 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
3251 int enabled = !!ucontrol->value.integer.value[0];
3252 if (codec->beep->enabled != enabled) {
3253 codec->beep->enabled = enabled;
3254 return 1;
3255 }
3256 return 0;
3257}
3258
3259static struct snd_kcontrol_new stac92xx_dig_beep_ctrl = {
3260 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
3261 .info = stac92xx_dig_beep_switch_info,
3262 .get = stac92xx_dig_beep_switch_get,
3263 .put = stac92xx_dig_beep_switch_put,
3264};
3265
3266static int stac92xx_beep_switch_ctl(struct hda_codec *codec)
3267{
3268 return stac92xx_add_control_temp(codec->spec, &stac92xx_dig_beep_ctrl,
3269 0, "PC Beep Playback Switch", 0);
3270}
3271#endif
3272
4682eee0
MR
3273static int stac92xx_auto_create_mux_input_ctls(struct hda_codec *codec)
3274{
3275 struct sigmatel_spec *spec = codec->spec;
3276 int wcaps, nid, i, err = 0;
3277
3278 for (i = 0; i < spec->num_muxes; i++) {
3279 nid = spec->mux_nids[i];
3280 wcaps = get_wcaps(codec, nid);
3281
3282 if (wcaps & AC_WCAP_OUT_AMP) {
3283 err = stac92xx_add_control_idx(spec,
3284 STAC_CTL_WIDGET_VOL, i, "Mux Capture Volume",
3285 HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_OUTPUT));
3286 if (err < 0)
3287 return err;
3288 }
3289 }
3290 return 0;
3291};
3292
d9737751 3293static const char *stac92xx_spdif_labels[3] = {
65973632 3294 "Digital Playback", "Analog Mux 1", "Analog Mux 2",
d9737751
MR
3295};
3296
3297static int stac92xx_auto_create_spdif_mux_ctls(struct hda_codec *codec)
3298{
3299 struct sigmatel_spec *spec = codec->spec;
3300 struct hda_input_mux *spdif_mux = &spec->private_smux;
65973632 3301 const char **labels = spec->spdif_labels;
d9737751 3302 int i, num_cons;
65973632 3303 hda_nid_t con_lst[HDA_MAX_NUM_INPUTS];
d9737751
MR
3304
3305 num_cons = snd_hda_get_connections(codec,
3306 spec->smux_nids[0],
3307 con_lst,
3308 HDA_MAX_NUM_INPUTS);
65973632 3309 if (!num_cons)
d9737751
MR
3310 return -EINVAL;
3311
65973632
MR
3312 if (!labels)
3313 labels = stac92xx_spdif_labels;
3314
d9737751 3315 for (i = 0; i < num_cons; i++) {
65973632 3316 spdif_mux->items[spdif_mux->num_items].label = labels[i];
d9737751
MR
3317 spdif_mux->items[spdif_mux->num_items].index = i;
3318 spdif_mux->num_items++;
3319 }
3320
3321 return 0;
3322}
3323
8b65727b 3324/* labels for dmic mux inputs */
ddc2cec4 3325static const char *stac92xx_dmic_labels[5] = {
8b65727b
MP
3326 "Analog Inputs", "Digital Mic 1", "Digital Mic 2",
3327 "Digital Mic 3", "Digital Mic 4"
3328};
3329
3330/* create playback/capture controls for input pins on dmic capable codecs */
3331static int stac92xx_auto_create_dmic_input_ctls(struct hda_codec *codec,
3332 const struct auto_pin_cfg *cfg)
3333{
3334 struct sigmatel_spec *spec = codec->spec;
3335 struct hda_input_mux *dimux = &spec->private_dimux;
3336 hda_nid_t con_lst[HDA_MAX_NUM_INPUTS];
0678accd
MR
3337 int err, i, j;
3338 char name[32];
8b65727b
MP
3339
3340 dimux->items[dimux->num_items].label = stac92xx_dmic_labels[0];
3341 dimux->items[dimux->num_items].index = 0;
3342 dimux->num_items++;
3343
3344 for (i = 0; i < spec->num_dmics; i++) {
0678accd 3345 hda_nid_t nid;
8b65727b
MP
3346 int index;
3347 int num_cons;
0678accd 3348 unsigned int wcaps;
8b65727b
MP
3349 unsigned int def_conf;
3350
3351 def_conf = snd_hda_codec_read(codec,
3352 spec->dmic_nids[i],
3353 0,
3354 AC_VERB_GET_CONFIG_DEFAULT,
3355 0);
3356 if (get_defcfg_connect(def_conf) == AC_JACK_PORT_NONE)
3357 continue;
3358
0678accd 3359 nid = spec->dmic_nids[i];
8b65727b 3360 num_cons = snd_hda_get_connections(codec,
e1f0d669 3361 spec->dmux_nids[0],
8b65727b
MP
3362 con_lst,
3363 HDA_MAX_NUM_INPUTS);
3364 for (j = 0; j < num_cons; j++)
0678accd 3365 if (con_lst[j] == nid) {
8b65727b
MP
3366 index = j;
3367 goto found;
3368 }
3369 continue;
3370found:
d0513fc6
MR
3371 wcaps = get_wcaps(codec, nid) &
3372 (AC_WCAP_OUT_AMP | AC_WCAP_IN_AMP);
0678accd 3373
d0513fc6 3374 if (wcaps) {
0678accd
MR
3375 sprintf(name, "%s Capture Volume",
3376 stac92xx_dmic_labels[dimux->num_items]);
3377
3378 err = stac92xx_add_control(spec,
3379 STAC_CTL_WIDGET_VOL,
3380 name,
d0513fc6
MR
3381 HDA_COMPOSE_AMP_VAL(nid, 3, 0,
3382 (wcaps & AC_WCAP_OUT_AMP) ?
3383 HDA_OUTPUT : HDA_INPUT));
0678accd
MR
3384 if (err < 0)
3385 return err;
3386 }
3387
8b65727b
MP
3388 dimux->items[dimux->num_items].label =
3389 stac92xx_dmic_labels[dimux->num_items];
3390 dimux->items[dimux->num_items].index = index;
3391 dimux->num_items++;
3392 }
3393
3394 return 0;
3395}
3396
c7d4b2fa
M
3397/* create playback/capture controls for input pins */
3398static int stac92xx_auto_create_analog_input_ctls(struct hda_codec *codec, const struct auto_pin_cfg *cfg)
3399{
3400 struct sigmatel_spec *spec = codec->spec;
c7d4b2fa
M
3401 struct hda_input_mux *imux = &spec->private_imux;
3402 hda_nid_t con_lst[HDA_MAX_NUM_INPUTS];
3403 int i, j, k;
3404
3405 for (i = 0; i < AUTO_PIN_LAST; i++) {
314634bc
TI
3406 int index;
3407
3408 if (!cfg->input_pins[i])
3409 continue;
3410 index = -1;
3411 for (j = 0; j < spec->num_muxes; j++) {
3412 int num_cons;
3413 num_cons = snd_hda_get_connections(codec,
3414 spec->mux_nids[j],
3415 con_lst,
3416 HDA_MAX_NUM_INPUTS);
3417 for (k = 0; k < num_cons; k++)
3418 if (con_lst[k] == cfg->input_pins[i]) {
3419 index = k;
3420 goto found;
3421 }
c7d4b2fa 3422 }
314634bc
TI
3423 continue;
3424 found:
3425 imux->items[imux->num_items].label = auto_pin_cfg_labels[i];
3426 imux->items[imux->num_items].index = index;
3427 imux->num_items++;
c7d4b2fa
M
3428 }
3429
7b043899 3430 if (imux->num_items) {
62fe78e9
SR
3431 /*
3432 * Set the current input for the muxes.
3433 * The STAC9221 has two input muxes with identical source
3434 * NID lists. Hopefully this won't get confused.
3435 */
3436 for (i = 0; i < spec->num_muxes; i++) {
82beb8fd
TI
3437 snd_hda_codec_write_cache(codec, spec->mux_nids[i], 0,
3438 AC_VERB_SET_CONNECT_SEL,
3439 imux->items[0].index);
62fe78e9
SR
3440 }
3441 }
3442
c7d4b2fa
M
3443 return 0;
3444}
3445
c7d4b2fa
M
3446static void stac92xx_auto_init_multi_out(struct hda_codec *codec)
3447{
3448 struct sigmatel_spec *spec = codec->spec;
3449 int i;
3450
3451 for (i = 0; i < spec->autocfg.line_outs; i++) {
3452 hda_nid_t nid = spec->autocfg.line_out_pins[i];
3453 stac92xx_auto_set_pinctl(codec, nid, AC_PINCTL_OUT_EN);
3454 }
3455}
3456
3457static void stac92xx_auto_init_hp_out(struct hda_codec *codec)
3458{
3459 struct sigmatel_spec *spec = codec->spec;
eb06ed8f 3460 int i;
c7d4b2fa 3461
eb06ed8f
TI
3462 for (i = 0; i < spec->autocfg.hp_outs; i++) {
3463 hda_nid_t pin;
3464 pin = spec->autocfg.hp_pins[i];
3465 if (pin) /* connect to front */
3466 stac92xx_auto_set_pinctl(codec, pin, AC_PINCTL_OUT_EN | AC_PINCTL_HP_EN);
3467 }
3468 for (i = 0; i < spec->autocfg.speaker_outs; i++) {
3469 hda_nid_t pin;
3470 pin = spec->autocfg.speaker_pins[i];
3471 if (pin) /* connect to front */
3472 stac92xx_auto_set_pinctl(codec, pin, AC_PINCTL_OUT_EN);
3473 }
c7d4b2fa
M
3474}
3475
3cc08dc6 3476static int stac92xx_parse_auto_config(struct hda_codec *codec, hda_nid_t dig_out, hda_nid_t dig_in)
c7d4b2fa
M
3477{
3478 struct sigmatel_spec *spec = codec->spec;
3479 int err;
bcecd9bd 3480 int hp_speaker_swap = 0;
c7d4b2fa 3481
8b65727b
MP
3482 if ((err = snd_hda_parse_pin_def_config(codec,
3483 &spec->autocfg,
3484 spec->dmic_nids)) < 0)
c7d4b2fa 3485 return err;
82bc955f 3486 if (! spec->autocfg.line_outs)
869264c4 3487 return 0; /* can't find valid pin config */
19039bd0 3488
bcecd9bd
JZ
3489 /* If we have no real line-out pin and multiple hp-outs, HPs should
3490 * be set up as multi-channel outputs.
3491 */
3492 if (spec->autocfg.line_out_type == AUTO_PIN_SPEAKER_OUT &&
3493 spec->autocfg.hp_outs > 1) {
3494 /* Copy hp_outs to line_outs, backup line_outs in
3495 * speaker_outs so that the following routines can handle
3496 * HP pins as primary outputs.
3497 */
3498 memcpy(spec->autocfg.speaker_pins, spec->autocfg.line_out_pins,
3499 sizeof(spec->autocfg.line_out_pins));
3500 spec->autocfg.speaker_outs = spec->autocfg.line_outs;
3501 memcpy(spec->autocfg.line_out_pins, spec->autocfg.hp_pins,
3502 sizeof(spec->autocfg.hp_pins));
3503 spec->autocfg.line_outs = spec->autocfg.hp_outs;
3504 hp_speaker_swap = 1;
3505 }
09a99959 3506 if (spec->autocfg.mono_out_pin) {
d0513fc6
MR
3507 int dir = get_wcaps(codec, spec->autocfg.mono_out_pin) &
3508 (AC_WCAP_OUT_AMP | AC_WCAP_IN_AMP);
09a99959
MR
3509 u32 caps = query_amp_caps(codec,
3510 spec->autocfg.mono_out_pin, dir);
3511 hda_nid_t conn_list[1];
3512
3513 /* get the mixer node and then the mono mux if it exists */
3514 if (snd_hda_get_connections(codec,
3515 spec->autocfg.mono_out_pin, conn_list, 1) &&
3516 snd_hda_get_connections(codec, conn_list[0],
3517 conn_list, 1)) {
3518
3519 int wcaps = get_wcaps(codec, conn_list[0]);
3520 int wid_type = (wcaps & AC_WCAP_TYPE)
3521 >> AC_WCAP_TYPE_SHIFT;
3522 /* LR swap check, some stac925x have a mux that
3523 * changes the DACs output path instead of the
3524 * mono-mux path.
3525 */
3526 if (wid_type == AC_WID_AUD_SEL &&
3527 !(wcaps & AC_WCAP_LR_SWAP))
3528 spec->mono_nid = conn_list[0];
3529 }
d0513fc6
MR
3530 if (dir) {
3531 hda_nid_t nid = spec->autocfg.mono_out_pin;
3532
3533 /* most mono outs have a least a mute/unmute switch */
3534 dir = (dir & AC_WCAP_OUT_AMP) ? HDA_OUTPUT : HDA_INPUT;
3535 err = stac92xx_add_control(spec, STAC_CTL_WIDGET_MUTE,
3536 "Mono Playback Switch",
3537 HDA_COMPOSE_AMP_VAL(nid, 1, 0, dir));
09a99959
MR
3538 if (err < 0)
3539 return err;
d0513fc6
MR
3540 /* check for volume support for the amp */
3541 if ((caps & AC_AMPCAP_NUM_STEPS)
3542 >> AC_AMPCAP_NUM_STEPS_SHIFT) {
3543 err = stac92xx_add_control(spec,
3544 STAC_CTL_WIDGET_VOL,
3545 "Mono Playback Volume",
3546 HDA_COMPOSE_AMP_VAL(nid, 1, 0, dir));
3547 if (err < 0)
3548 return err;
3549 }
09a99959
MR
3550 }
3551
3552 stac92xx_auto_set_pinctl(codec, spec->autocfg.mono_out_pin,
3553 AC_PINCTL_OUT_EN);
3554 }
bcecd9bd 3555
403d1944
MP
3556 if ((err = stac92xx_add_dyn_out_pins(codec, &spec->autocfg)) < 0)
3557 return err;
19039bd0
TI
3558 if (spec->multiout.num_dacs == 0)
3559 if ((err = stac92xx_auto_fill_dac_nids(codec, &spec->autocfg)) < 0)
3560 return err;
c7d4b2fa 3561
0fb87bb4
ML
3562 err = stac92xx_auto_create_multi_out_ctls(codec, &spec->autocfg);
3563
3564 if (err < 0)
3565 return err;
3566
1cd2224c
MR
3567 /* setup analog beep controls */
3568 if (spec->anabeep_nid > 0) {
3569 err = stac92xx_auto_create_beep_ctls(codec,
3570 spec->anabeep_nid);
3571 if (err < 0)
3572 return err;
3573 }
3574
3575 /* setup digital beep controls and input device */
3576#ifdef CONFIG_SND_HDA_INPUT_BEEP
3577 if (spec->digbeep_nid > 0) {
3578 hda_nid_t nid = spec->digbeep_nid;
4d4e9bb3 3579 unsigned int caps;
1cd2224c
MR
3580
3581 err = stac92xx_auto_create_beep_ctls(codec, nid);
3582 if (err < 0)
3583 return err;
3584 err = snd_hda_attach_beep_device(codec, nid);
3585 if (err < 0)
3586 return err;
4d4e9bb3
TI
3587 /* if no beep switch is available, make its own one */
3588 caps = query_amp_caps(codec, nid, HDA_OUTPUT);
3589 if (codec->beep &&
3590 !((caps & AC_AMPCAP_MUTE) >> AC_AMPCAP_MUTE_SHIFT)) {
3591 err = stac92xx_beep_switch_ctl(codec);
3592 if (err < 0)
3593 return err;
3594 }
1cd2224c
MR
3595 }
3596#endif
3597
bcecd9bd
JZ
3598 if (hp_speaker_swap == 1) {
3599 /* Restore the hp_outs and line_outs */
3600 memcpy(spec->autocfg.hp_pins, spec->autocfg.line_out_pins,
3601 sizeof(spec->autocfg.line_out_pins));
3602 spec->autocfg.hp_outs = spec->autocfg.line_outs;
3603 memcpy(spec->autocfg.line_out_pins, spec->autocfg.speaker_pins,
3604 sizeof(spec->autocfg.speaker_pins));
3605 spec->autocfg.line_outs = spec->autocfg.speaker_outs;
3606 memset(spec->autocfg.speaker_pins, 0,
3607 sizeof(spec->autocfg.speaker_pins));
3608 spec->autocfg.speaker_outs = 0;
3609 }
3610
0fb87bb4
ML
3611 err = stac92xx_auto_create_hp_ctls(codec, &spec->autocfg);
3612
3613 if (err < 0)
3614 return err;
3615
3616 err = stac92xx_auto_create_analog_input_ctls(codec, &spec->autocfg);
3617
3618 if (err < 0)
c7d4b2fa
M
3619 return err;
3620
b22b4821
MR
3621 if (spec->mono_nid > 0) {
3622 err = stac92xx_auto_create_mono_output_ctls(codec);
3623 if (err < 0)
3624 return err;
3625 }
2a9c7816 3626 if (spec->num_amps > 0) {
89385035
MR
3627 err = stac92xx_auto_create_amp_output_ctls(codec);
3628 if (err < 0)
3629 return err;
3630 }
2a9c7816 3631 if (spec->num_dmics > 0 && !spec->dinput_mux)
8b65727b
MP
3632 if ((err = stac92xx_auto_create_dmic_input_ctls(codec,
3633 &spec->autocfg)) < 0)
3634 return err;
4682eee0
MR
3635 if (spec->num_muxes > 0) {
3636 err = stac92xx_auto_create_mux_input_ctls(codec);
3637 if (err < 0)
3638 return err;
3639 }
d9737751
MR
3640 if (spec->num_smuxes > 0) {
3641 err = stac92xx_auto_create_spdif_mux_ctls(codec);
3642 if (err < 0)
3643 return err;
3644 }
8b65727b 3645
c7d4b2fa 3646 spec->multiout.max_channels = spec->multiout.num_dacs * 2;
403d1944 3647 if (spec->multiout.max_channels > 2)
c7d4b2fa 3648 spec->surr_switch = 1;
c7d4b2fa 3649
82bc955f 3650 if (spec->autocfg.dig_out_pin)
3cc08dc6 3651 spec->multiout.dig_out_nid = dig_out;
d0513fc6 3652 if (dig_in && spec->autocfg.dig_in_pin)
3cc08dc6 3653 spec->dig_in_nid = dig_in;
c7d4b2fa 3654
603c4019
TI
3655 if (spec->kctls.list)
3656 spec->mixers[spec->num_mixers++] = spec->kctls.list;
c7d4b2fa
M
3657
3658 spec->input_mux = &spec->private_imux;
2a9c7816 3659 spec->dinput_mux = &spec->private_dimux;
d9737751 3660 spec->sinput_mux = &spec->private_smux;
b22b4821 3661 spec->mono_mux = &spec->private_mono_mux;
89385035 3662 spec->amp_mux = &spec->private_amp_mux;
c7d4b2fa
M
3663 return 1;
3664}
3665
82bc955f
TI
3666/* add playback controls for HP output */
3667static int stac9200_auto_create_hp_ctls(struct hda_codec *codec,
3668 struct auto_pin_cfg *cfg)
3669{
3670 struct sigmatel_spec *spec = codec->spec;
eb06ed8f 3671 hda_nid_t pin = cfg->hp_pins[0];
82bc955f
TI
3672 unsigned int wid_caps;
3673
3674 if (! pin)
3675 return 0;
3676
3677 wid_caps = get_wcaps(codec, pin);
505cb341 3678 if (wid_caps & AC_WCAP_UNSOL_CAP)
82bc955f 3679 spec->hp_detect = 1;
82bc955f
TI
3680
3681 return 0;
3682}
3683
160ea0dc
RF
3684/* add playback controls for LFE output */
3685static int stac9200_auto_create_lfe_ctls(struct hda_codec *codec,
3686 struct auto_pin_cfg *cfg)
3687{
3688 struct sigmatel_spec *spec = codec->spec;
3689 int err;
3690 hda_nid_t lfe_pin = 0x0;
3691 int i;
3692
3693 /*
3694 * search speaker outs and line outs for a mono speaker pin
3695 * with an amp. If one is found, add LFE controls
3696 * for it.
3697 */
3698 for (i = 0; i < spec->autocfg.speaker_outs && lfe_pin == 0x0; i++) {
3699 hda_nid_t pin = spec->autocfg.speaker_pins[i];
64ed0dfd 3700 unsigned int wcaps = get_wcaps(codec, pin);
160ea0dc
RF
3701 wcaps &= (AC_WCAP_STEREO | AC_WCAP_OUT_AMP);
3702 if (wcaps == AC_WCAP_OUT_AMP)
3703 /* found a mono speaker with an amp, must be lfe */
3704 lfe_pin = pin;
3705 }
3706
3707 /* if speaker_outs is 0, then speakers may be in line_outs */
3708 if (lfe_pin == 0 && spec->autocfg.speaker_outs == 0) {
3709 for (i = 0; i < spec->autocfg.line_outs && lfe_pin == 0x0; i++) {
3710 hda_nid_t pin = spec->autocfg.line_out_pins[i];
64ed0dfd 3711 unsigned int defcfg;
8b551785 3712 defcfg = snd_hda_codec_read(codec, pin, 0,
160ea0dc
RF
3713 AC_VERB_GET_CONFIG_DEFAULT,
3714 0x00);
8b551785 3715 if (get_defcfg_device(defcfg) == AC_JACK_SPEAKER) {
64ed0dfd 3716 unsigned int wcaps = get_wcaps(codec, pin);
160ea0dc
RF
3717 wcaps &= (AC_WCAP_STEREO | AC_WCAP_OUT_AMP);
3718 if (wcaps == AC_WCAP_OUT_AMP)
3719 /* found a mono speaker with an amp,
3720 must be lfe */
3721 lfe_pin = pin;
3722 }
3723 }
3724 }
3725
3726 if (lfe_pin) {
eb06ed8f 3727 err = create_controls(spec, "LFE", lfe_pin, 1);
160ea0dc
RF
3728 if (err < 0)
3729 return err;
3730 }
3731
3732 return 0;
3733}
3734
c7d4b2fa
M
3735static int stac9200_parse_auto_config(struct hda_codec *codec)
3736{
3737 struct sigmatel_spec *spec = codec->spec;
3738 int err;
3739
df694daa 3740 if ((err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL)) < 0)
c7d4b2fa
M
3741 return err;
3742
3743 if ((err = stac92xx_auto_create_analog_input_ctls(codec, &spec->autocfg)) < 0)
3744 return err;
3745
82bc955f
TI
3746 if ((err = stac9200_auto_create_hp_ctls(codec, &spec->autocfg)) < 0)
3747 return err;
3748
160ea0dc
RF
3749 if ((err = stac9200_auto_create_lfe_ctls(codec, &spec->autocfg)) < 0)
3750 return err;
3751
355a0ec4
TI
3752 if (spec->num_muxes > 0) {
3753 err = stac92xx_auto_create_mux_input_ctls(codec);
3754 if (err < 0)
3755 return err;
3756 }
3757
82bc955f 3758 if (spec->autocfg.dig_out_pin)
c7d4b2fa 3759 spec->multiout.dig_out_nid = 0x05;
82bc955f 3760 if (spec->autocfg.dig_in_pin)
c7d4b2fa 3761 spec->dig_in_nid = 0x04;
c7d4b2fa 3762
603c4019
TI
3763 if (spec->kctls.list)
3764 spec->mixers[spec->num_mixers++] = spec->kctls.list;
c7d4b2fa
M
3765
3766 spec->input_mux = &spec->private_imux;
8b65727b 3767 spec->dinput_mux = &spec->private_dimux;
c7d4b2fa
M
3768
3769 return 1;
3770}
3771
62fe78e9
SR
3772/*
3773 * Early 2006 Intel Macintoshes with STAC9220X5 codecs seem to have a
3774 * funky external mute control using GPIO pins.
3775 */
3776
76e1ddfb 3777static void stac_gpio_set(struct hda_codec *codec, unsigned int mask,
4fe5195c 3778 unsigned int dir_mask, unsigned int data)
62fe78e9
SR
3779{
3780 unsigned int gpiostate, gpiomask, gpiodir;
3781
3782 gpiostate = snd_hda_codec_read(codec, codec->afg, 0,
3783 AC_VERB_GET_GPIO_DATA, 0);
4fe5195c 3784 gpiostate = (gpiostate & ~dir_mask) | (data & dir_mask);
62fe78e9
SR
3785
3786 gpiomask = snd_hda_codec_read(codec, codec->afg, 0,
3787 AC_VERB_GET_GPIO_MASK, 0);
76e1ddfb 3788 gpiomask |= mask;
62fe78e9
SR
3789
3790 gpiodir = snd_hda_codec_read(codec, codec->afg, 0,
3791 AC_VERB_GET_GPIO_DIRECTION, 0);
4fe5195c 3792 gpiodir |= dir_mask;
62fe78e9 3793
76e1ddfb 3794 /* Configure GPIOx as CMOS */
62fe78e9
SR
3795 snd_hda_codec_write(codec, codec->afg, 0, 0x7e7, 0);
3796
3797 snd_hda_codec_write(codec, codec->afg, 0,
3798 AC_VERB_SET_GPIO_MASK, gpiomask);
76e1ddfb
TI
3799 snd_hda_codec_read(codec, codec->afg, 0,
3800 AC_VERB_SET_GPIO_DIRECTION, gpiodir); /* sync */
62fe78e9
SR
3801
3802 msleep(1);
3803
76e1ddfb
TI
3804 snd_hda_codec_read(codec, codec->afg, 0,
3805 AC_VERB_SET_GPIO_DATA, gpiostate); /* sync */
62fe78e9
SR
3806}
3807
74aeaabc
MR
3808static int stac92xx_add_jack(struct hda_codec *codec,
3809 hda_nid_t nid, int type)
3810{
e4973e1e 3811#ifdef CONFIG_SND_JACK
74aeaabc
MR
3812 struct sigmatel_spec *spec = codec->spec;
3813 struct sigmatel_jack *jack;
3814 int def_conf = snd_hda_codec_read(codec, nid,
3815 0, AC_VERB_GET_CONFIG_DEFAULT, 0);
3816 int connectivity = get_defcfg_connect(def_conf);
3817 char name[32];
3818
3819 if (connectivity && connectivity != AC_JACK_PORT_FIXED)
3820 return 0;
3821
3822 snd_array_init(&spec->jacks, sizeof(*jack), 32);
3823 jack = snd_array_new(&spec->jacks);
3824 if (!jack)
3825 return -ENOMEM;
3826 jack->nid = nid;
3827 jack->type = type;
3828
3829 sprintf(name, "%s at %s %s Jack",
3830 snd_hda_get_jack_type(def_conf),
3831 snd_hda_get_jack_connectivity(def_conf),
3832 snd_hda_get_jack_location(def_conf));
3833
3834 return snd_jack_new(codec->bus->card, name, type, &jack->jack);
e4973e1e
TI
3835#else
3836 return 0;
3837#endif
74aeaabc
MR
3838}
3839
c6e4c666
TI
3840static int stac_add_event(struct sigmatel_spec *spec, hda_nid_t nid,
3841 unsigned char type, int data)
74aeaabc
MR
3842{
3843 struct sigmatel_event *event;
3844
3845 snd_array_init(&spec->events, sizeof(*event), 32);
3846 event = snd_array_new(&spec->events);
3847 if (!event)
3848 return -ENOMEM;
3849 event->nid = nid;
c6e4c666
TI
3850 event->type = type;
3851 event->tag = spec->events.used;
74aeaabc
MR
3852 event->data = data;
3853
c6e4c666 3854 return event->tag;
74aeaabc
MR
3855}
3856
c6e4c666
TI
3857static struct sigmatel_event *stac_get_event(struct hda_codec *codec,
3858 hda_nid_t nid, unsigned char type)
74aeaabc
MR
3859{
3860 struct sigmatel_spec *spec = codec->spec;
c6e4c666
TI
3861 struct sigmatel_event *event = spec->events.list;
3862 int i;
3863
3864 for (i = 0; i < spec->events.used; i++, event++) {
3865 if (event->nid == nid && event->type == type)
3866 return event;
74aeaabc 3867 }
c6e4c666 3868 return NULL;
74aeaabc
MR
3869}
3870
c6e4c666
TI
3871static struct sigmatel_event *stac_get_event_from_tag(struct hda_codec *codec,
3872 unsigned char tag)
314634bc 3873{
c6e4c666
TI
3874 struct sigmatel_spec *spec = codec->spec;
3875 struct sigmatel_event *event = spec->events.list;
3876 int i;
3877
3878 for (i = 0; i < spec->events.used; i++, event++) {
3879 if (event->tag == tag)
3880 return event;
74aeaabc 3881 }
c6e4c666
TI
3882 return NULL;
3883}
3884
3885static void enable_pin_detect(struct hda_codec *codec, hda_nid_t nid,
3886 unsigned int type)
3887{
3888 struct sigmatel_event *event;
3889 int tag;
3890
3891 if (!(get_wcaps(codec, nid) & AC_WCAP_UNSOL_CAP))
3892 return;
3893 event = stac_get_event(codec, nid, type);
3894 if (event)
3895 tag = event->tag;
3896 else
3897 tag = stac_add_event(codec->spec, nid, type, 0);
3898 if (tag < 0)
3899 return;
3900 snd_hda_codec_write_cache(codec, nid, 0,
3901 AC_VERB_SET_UNSOLICITED_ENABLE,
3902 AC_USRSP_EN | tag);
314634bc
TI
3903}
3904
a64135a2
MR
3905static int is_nid_hp_pin(struct auto_pin_cfg *cfg, hda_nid_t nid)
3906{
3907 int i;
3908 for (i = 0; i < cfg->hp_outs; i++)
3909 if (cfg->hp_pins[i] == nid)
3910 return 1; /* nid is a HP-Out */
3911
3912 return 0; /* nid is not a HP-Out */
3913};
3914
b76c850f
MR
3915static void stac92xx_power_down(struct hda_codec *codec)
3916{
3917 struct sigmatel_spec *spec = codec->spec;
3918
3919 /* power down inactive DACs */
3920 hda_nid_t *dac;
3921 for (dac = spec->dac_list; *dac; dac++)
4451089e
MR
3922 if (!is_in_dac_nids(spec, *dac) &&
3923 spec->multiout.hp_nid != *dac)
b76c850f
MR
3924 snd_hda_codec_write_cache(codec, *dac, 0,
3925 AC_VERB_SET_POWER_STATE, AC_PWRST_D3);
3926}
3927
f73d3585
TI
3928static void stac_toggle_power_map(struct hda_codec *codec, hda_nid_t nid,
3929 int enable);
3930
c7d4b2fa
M
3931static int stac92xx_init(struct hda_codec *codec)
3932{
3933 struct sigmatel_spec *spec = codec->spec;
82bc955f 3934 struct auto_pin_cfg *cfg = &spec->autocfg;
f73d3585 3935 unsigned int gpio;
e4973e1e 3936 int i;
c7d4b2fa 3937
c7d4b2fa
M
3938 snd_hda_sequence_write(codec, spec->init);
3939
8daaaa97
MR
3940 /* power down adcs initially */
3941 if (spec->powerdown_adcs)
3942 for (i = 0; i < spec->num_adcs; i++)
3943 snd_hda_codec_write_cache(codec,
3944 spec->adc_nids[i], 0,
3945 AC_VERB_SET_POWER_STATE, AC_PWRST_D3);
f73d3585
TI
3946
3947 /* set up GPIO */
3948 gpio = spec->gpio_data;
3949 /* turn on EAPD statically when spec->eapd_switch isn't set.
3950 * otherwise, unsol event will turn it on/off dynamically
3951 */
3952 if (!spec->eapd_switch)
3953 gpio |= spec->eapd_mask;
3954 stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir, gpio);
3955
82bc955f
TI
3956 /* set up pins */
3957 if (spec->hp_detect) {
505cb341 3958 /* Enable unsolicited responses on the HP widget */
74aeaabc 3959 for (i = 0; i < cfg->hp_outs; i++) {
74aeaabc 3960 hda_nid_t nid = cfg->hp_pins[i];
c6e4c666 3961 enable_pin_detect(codec, nid, STAC_HP_EVENT);
74aeaabc 3962 }
0a07acaf
TI
3963 /* force to enable the first line-out; the others are set up
3964 * in unsol_event
3965 */
3966 stac92xx_auto_set_pinctl(codec, spec->autocfg.line_out_pins[0],
74aeaabc 3967 AC_PINCTL_OUT_EN);
82bc955f 3968 /* fake event to set up pins */
c6e4c666
TI
3969 stac_issue_unsol_event(codec, spec->autocfg.hp_pins[0],
3970 STAC_HP_EVENT);
82bc955f
TI
3971 } else {
3972 stac92xx_auto_init_multi_out(codec);
3973 stac92xx_auto_init_hp_out(codec);
3974 }
3975 for (i = 0; i < AUTO_PIN_LAST; i++) {
c960a03b
TI
3976 hda_nid_t nid = cfg->input_pins[i];
3977 if (nid) {
4f1e6bc3
TI
3978 unsigned int pinctl;
3979 if (i == AUTO_PIN_MIC || i == AUTO_PIN_FRONT_MIC) {
3980 /* for mic pins, force to initialize */
3981 pinctl = stac92xx_get_vref(codec, nid);
3982 } else {
3983 pinctl = snd_hda_codec_read(codec, nid, 0,
3984 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
3985 /* if PINCTL already set then skip */
3986 if (pinctl & AC_PINCTL_IN_EN)
3987 continue;
3988 }
3989 pinctl |= AC_PINCTL_IN_EN;
c960a03b 3990 stac92xx_auto_set_pinctl(codec, nid, pinctl);
c6e4c666 3991 enable_pin_detect(codec, nid, STAC_INSERT_EVENT);
c960a03b 3992 }
82bc955f 3993 }
a64135a2
MR
3994 for (i = 0; i < spec->num_dmics; i++)
3995 stac92xx_auto_set_pinctl(codec, spec->dmic_nids[i],
3996 AC_PINCTL_IN_EN);
f73d3585
TI
3997 if (cfg->dig_out_pin)
3998 stac92xx_auto_set_pinctl(codec, cfg->dig_out_pin,
3999 AC_PINCTL_OUT_EN);
4000 if (cfg->dig_in_pin)
4001 stac92xx_auto_set_pinctl(codec, cfg->dig_in_pin,
4002 AC_PINCTL_IN_EN);
a64135a2 4003 for (i = 0; i < spec->num_pwrs; i++) {
f73d3585
TI
4004 hda_nid_t nid = spec->pwr_nids[i];
4005 int pinctl, def_conf;
f73d3585
TI
4006
4007 if (is_nid_hp_pin(cfg, nid) && spec->hp_detect)
4008 continue; /* already has an unsol event */
4009
4010 pinctl = snd_hda_codec_read(codec, nid, 0,
4011 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
a64135a2
MR
4012 /* outputs are only ports capable of power management
4013 * any attempts on powering down a input port cause the
4014 * referenced VREF to act quirky.
4015 */
4016 if (pinctl & AC_PINCTL_IN_EN)
4017 continue;
f73d3585
TI
4018 def_conf = snd_hda_codec_read(codec, nid, 0,
4019 AC_VERB_GET_CONFIG_DEFAULT, 0);
4020 def_conf = get_defcfg_connect(def_conf);
aafc4412
MR
4021 /* skip any ports that don't have jacks since presence
4022 * detection is useless */
f73d3585
TI
4023 if (def_conf != AC_JACK_PORT_COMPLEX) {
4024 if (def_conf != AC_JACK_PORT_NONE)
4025 stac_toggle_power_map(codec, nid, 1);
bce6c2b5 4026 continue;
f73d3585 4027 }
c6e4c666
TI
4028 enable_pin_detect(codec, nid, STAC_PWR_EVENT);
4029 stac_issue_unsol_event(codec, nid, STAC_PWR_EVENT);
a64135a2 4030 }
b76c850f
MR
4031 if (spec->dac_list)
4032 stac92xx_power_down(codec);
c7d4b2fa
M
4033 return 0;
4034}
4035
74aeaabc
MR
4036static void stac92xx_free_jacks(struct hda_codec *codec)
4037{
e4973e1e 4038#ifdef CONFIG_SND_JACK
b94d3539 4039 /* free jack instances manually when clearing/reconfiguring */
74aeaabc 4040 struct sigmatel_spec *spec = codec->spec;
b94d3539 4041 if (!codec->bus->shutdown && spec->jacks.list) {
74aeaabc
MR
4042 struct sigmatel_jack *jacks = spec->jacks.list;
4043 int i;
4044 for (i = 0; i < spec->jacks.used; i++)
4045 snd_device_free(codec->bus->card, &jacks[i].jack);
4046 }
4047 snd_array_free(&spec->jacks);
e4973e1e 4048#endif
74aeaabc
MR
4049}
4050
603c4019
TI
4051static void stac92xx_free_kctls(struct hda_codec *codec)
4052{
4053 struct sigmatel_spec *spec = codec->spec;
4054
4055 if (spec->kctls.list) {
4056 struct snd_kcontrol_new *kctl = spec->kctls.list;
4057 int i;
4058 for (i = 0; i < spec->kctls.used; i++)
4059 kfree(kctl[i].name);
4060 }
4061 snd_array_free(&spec->kctls);
4062}
4063
2f2f4251
M
4064static void stac92xx_free(struct hda_codec *codec)
4065{
c7d4b2fa 4066 struct sigmatel_spec *spec = codec->spec;
c7d4b2fa
M
4067
4068 if (! spec)
4069 return;
4070
af9f341a 4071 kfree(spec->pin_configs);
74aeaabc
MR
4072 stac92xx_free_jacks(codec);
4073 snd_array_free(&spec->events);
11b44bbd 4074
c7d4b2fa 4075 kfree(spec);
1cd2224c 4076 snd_hda_detach_beep_device(codec);
2f2f4251
M
4077}
4078
4e55096e
M
4079static void stac92xx_set_pinctl(struct hda_codec *codec, hda_nid_t nid,
4080 unsigned int flag)
4081{
4082 unsigned int pin_ctl = snd_hda_codec_read(codec, nid,
4083 0, AC_VERB_GET_PIN_WIDGET_CONTROL, 0x00);
7b043899 4084
f9acba43
TI
4085 if (pin_ctl & AC_PINCTL_IN_EN) {
4086 /*
4087 * we need to check the current set-up direction of
4088 * shared input pins since they can be switched via
4089 * "xxx as Output" mixer switch
4090 */
4091 struct sigmatel_spec *spec = codec->spec;
4092 struct auto_pin_cfg *cfg = &spec->autocfg;
4093 if ((nid == cfg->input_pins[AUTO_PIN_LINE] &&
4094 spec->line_switch) ||
4095 (nid == cfg->input_pins[AUTO_PIN_MIC] &&
4096 spec->mic_switch))
4097 return;
4098 }
4099
7b043899
SL
4100 /* if setting pin direction bits, clear the current
4101 direction bits first */
4102 if (flag & (AC_PINCTL_IN_EN | AC_PINCTL_OUT_EN))
4103 pin_ctl &= ~(AC_PINCTL_IN_EN | AC_PINCTL_OUT_EN);
4104
82beb8fd 4105 snd_hda_codec_write_cache(codec, nid, 0,
4e55096e
M
4106 AC_VERB_SET_PIN_WIDGET_CONTROL,
4107 pin_ctl | flag);
4108}
4109
4110static void stac92xx_reset_pinctl(struct hda_codec *codec, hda_nid_t nid,
4111 unsigned int flag)
4112{
4113 unsigned int pin_ctl = snd_hda_codec_read(codec, nid,
4114 0, AC_VERB_GET_PIN_WIDGET_CONTROL, 0x00);
82beb8fd 4115 snd_hda_codec_write_cache(codec, nid, 0,
4e55096e
M
4116 AC_VERB_SET_PIN_WIDGET_CONTROL,
4117 pin_ctl & ~flag);
4118}
4119
40c1d308 4120static int get_hp_pin_presence(struct hda_codec *codec, hda_nid_t nid)
314634bc
TI
4121{
4122 if (!nid)
4123 return 0;
4124 if (snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_PIN_SENSE, 0x00)
40c1d308
JZ
4125 & (1 << 31)) {
4126 unsigned int pinctl;
4127 pinctl = snd_hda_codec_read(codec, nid, 0,
4128 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
4129 if (pinctl & AC_PINCTL_IN_EN)
4130 return 0; /* mic- or line-input */
4131 else
4132 return 1; /* HP-output */
4133 }
314634bc
TI
4134 return 0;
4135}
4136
d7a89436
TI
4137/* return non-zero if the hp-pin of the given array index isn't
4138 * a jack-detection target
4139 */
4140static int no_hp_sensing(struct sigmatel_spec *spec, int i)
4141{
4142 struct auto_pin_cfg *cfg = &spec->autocfg;
4143
4144 /* ignore sensing of shared line and mic jacks */
4145 if (spec->line_switch &&
4146 cfg->hp_pins[i] == cfg->input_pins[AUTO_PIN_LINE])
4147 return 1;
4148 if (spec->mic_switch &&
4149 cfg->hp_pins[i] == cfg->input_pins[AUTO_PIN_MIC])
4150 return 1;
4151 /* ignore if the pin is set as line-out */
4152 if (cfg->hp_pins[i] == spec->hp_switch)
4153 return 1;
4154 return 0;
4155}
4156
c6e4c666 4157static void stac92xx_hp_detect(struct hda_codec *codec)
4e55096e
M
4158{
4159 struct sigmatel_spec *spec = codec->spec;
4160 struct auto_pin_cfg *cfg = &spec->autocfg;
4161 int i, presence;
4162
eb06ed8f 4163 presence = 0;
4fe5195c
MR
4164 if (spec->gpio_mute)
4165 presence = !(snd_hda_codec_read(codec, codec->afg, 0,
4166 AC_VERB_GET_GPIO_DATA, 0) & spec->gpio_mute);
4167
eb06ed8f 4168 for (i = 0; i < cfg->hp_outs; i++) {
314634bc
TI
4169 if (presence)
4170 break;
d7a89436
TI
4171 if (no_hp_sensing(spec, i))
4172 continue;
4fe5195c 4173 presence = get_hp_pin_presence(codec, cfg->hp_pins[i]);
eb06ed8f 4174 }
4e55096e
M
4175
4176 if (presence) {
d7a89436 4177 /* disable lineouts */
7c2ba97b 4178 if (spec->hp_switch)
d7a89436
TI
4179 stac92xx_reset_pinctl(codec, spec->hp_switch,
4180 AC_PINCTL_OUT_EN);
4e55096e
M
4181 for (i = 0; i < cfg->line_outs; i++)
4182 stac92xx_reset_pinctl(codec, cfg->line_out_pins[i],
4183 AC_PINCTL_OUT_EN);
eb06ed8f
TI
4184 for (i = 0; i < cfg->speaker_outs; i++)
4185 stac92xx_reset_pinctl(codec, cfg->speaker_pins[i],
4186 AC_PINCTL_OUT_EN);
c0cea0d0 4187 if (spec->eapd_mask && spec->eapd_switch)
0fc9dec4
MR
4188 stac_gpio_set(codec, spec->gpio_mask,
4189 spec->gpio_dir, spec->gpio_data &
4190 ~spec->eapd_mask);
4e55096e 4191 } else {
d7a89436 4192 /* enable lineouts */
7c2ba97b 4193 if (spec->hp_switch)
d7a89436
TI
4194 stac92xx_set_pinctl(codec, spec->hp_switch,
4195 AC_PINCTL_OUT_EN);
4e55096e
M
4196 for (i = 0; i < cfg->line_outs; i++)
4197 stac92xx_set_pinctl(codec, cfg->line_out_pins[i],
4198 AC_PINCTL_OUT_EN);
eb06ed8f
TI
4199 for (i = 0; i < cfg->speaker_outs; i++)
4200 stac92xx_set_pinctl(codec, cfg->speaker_pins[i],
4201 AC_PINCTL_OUT_EN);
c0cea0d0 4202 if (spec->eapd_mask && spec->eapd_switch)
0fc9dec4
MR
4203 stac_gpio_set(codec, spec->gpio_mask,
4204 spec->gpio_dir, spec->gpio_data |
4205 spec->eapd_mask);
4e55096e 4206 }
d7a89436
TI
4207 /* toggle hp outs */
4208 for (i = 0; i < cfg->hp_outs; i++) {
4209 unsigned int val = AC_PINCTL_OUT_EN | AC_PINCTL_HP_EN;
4210 if (no_hp_sensing(spec, i))
4211 continue;
4212 if (presence)
4213 stac92xx_set_pinctl(codec, cfg->hp_pins[i], val);
4214 else
4215 stac92xx_reset_pinctl(codec, cfg->hp_pins[i], val);
4216 }
4e55096e
M
4217}
4218
f73d3585
TI
4219static void stac_toggle_power_map(struct hda_codec *codec, hda_nid_t nid,
4220 int enable)
a64135a2
MR
4221{
4222 struct sigmatel_spec *spec = codec->spec;
f73d3585
TI
4223 unsigned int idx, val;
4224
4225 for (idx = 0; idx < spec->num_pwrs; idx++) {
4226 if (spec->pwr_nids[idx] == nid)
4227 break;
4228 }
4229 if (idx >= spec->num_pwrs)
4230 return;
d0513fc6
MR
4231
4232 /* several codecs have two power down bits */
4233 if (spec->pwr_mapping)
4234 idx = spec->pwr_mapping[idx];
4235 else
4236 idx = 1 << idx;
a64135a2 4237
f73d3585
TI
4238 val = snd_hda_codec_read(codec, codec->afg, 0, 0x0fec, 0x0) & 0xff;
4239 if (enable)
a64135a2
MR
4240 val &= ~idx;
4241 else
4242 val |= idx;
4243
4244 /* power down unused output ports */
4245 snd_hda_codec_write(codec, codec->afg, 0, 0x7ec, val);
74aeaabc
MR
4246}
4247
f73d3585
TI
4248static void stac92xx_pin_sense(struct hda_codec *codec, hda_nid_t nid)
4249{
4250 stac_toggle_power_map(codec, nid, get_hp_pin_presence(codec, nid));
4251}
a64135a2 4252
74aeaabc
MR
4253static void stac92xx_report_jack(struct hda_codec *codec, hda_nid_t nid)
4254{
4255 struct sigmatel_spec *spec = codec->spec;
4256 struct sigmatel_jack *jacks = spec->jacks.list;
4257
4258 if (jacks) {
4259 int i;
4260 for (i = 0; i < spec->jacks.used; i++) {
4261 if (jacks->nid == nid) {
4262 unsigned int pin_ctl =
4263 snd_hda_codec_read(codec, nid,
4264 0, AC_VERB_GET_PIN_WIDGET_CONTROL,
4265 0x00);
4266 int type = jacks->type;
4267 if (type == (SND_JACK_LINEOUT
4268 | SND_JACK_HEADPHONE))
4269 type = (pin_ctl & AC_PINCTL_HP_EN)
4270 ? SND_JACK_HEADPHONE : SND_JACK_LINEOUT;
4271 snd_jack_report(jacks->jack,
4272 get_hp_pin_presence(codec, nid)
4273 ? type : 0);
4274 }
4275 jacks++;
4276 }
4277 }
4278}
a64135a2 4279
c6e4c666
TI
4280static void stac_issue_unsol_event(struct hda_codec *codec, hda_nid_t nid,
4281 unsigned char type)
4282{
4283 struct sigmatel_event *event = stac_get_event(codec, nid, type);
4284 if (!event)
4285 return;
4286 codec->patch_ops.unsol_event(codec, (unsigned)event->tag << 26);
4287}
4288
314634bc
TI
4289static void stac92xx_unsol_event(struct hda_codec *codec, unsigned int res)
4290{
a64135a2 4291 struct sigmatel_spec *spec = codec->spec;
c6e4c666
TI
4292 struct sigmatel_event *event;
4293 int tag, data;
a64135a2 4294
c6e4c666
TI
4295 tag = (res >> 26) & 0x7f;
4296 event = stac_get_event_from_tag(codec, tag);
4297 if (!event)
4298 return;
4299
4300 switch (event->type) {
314634bc 4301 case STAC_HP_EVENT:
c6e4c666 4302 stac92xx_hp_detect(codec);
a64135a2 4303 /* fallthru */
74aeaabc 4304 case STAC_INSERT_EVENT:
a64135a2 4305 case STAC_PWR_EVENT:
c6e4c666
TI
4306 if (spec->num_pwrs > 0)
4307 stac92xx_pin_sense(codec, event->nid);
4308 stac92xx_report_jack(codec, event->nid);
72474be6 4309 break;
c6e4c666
TI
4310 case STAC_VREF_EVENT:
4311 data = snd_hda_codec_read(codec, codec->afg, 0,
4312 AC_VERB_GET_GPIO_DATA, 0);
72474be6
MR
4313 /* toggle VREF state based on GPIOx status */
4314 snd_hda_codec_write(codec, codec->afg, 0, 0x7e0,
c6e4c666 4315 !!(data & (1 << event->data)));
72474be6 4316 break;
314634bc
TI
4317 }
4318}
4319
cb53c626 4320#ifdef SND_HDA_NEEDS_RESUME
ff6fdc37
M
4321static int stac92xx_resume(struct hda_codec *codec)
4322{
dc81bed1
TI
4323 struct sigmatel_spec *spec = codec->spec;
4324
11b44bbd 4325 stac92xx_set_config_regs(codec);
2c885878 4326 stac92xx_init(codec);
82beb8fd
TI
4327 snd_hda_codec_resume_amp(codec);
4328 snd_hda_codec_resume_cache(codec);
2c885878 4329 /* fake event to set up pins again to override cached values */
dc81bed1 4330 if (spec->hp_detect)
c6e4c666
TI
4331 stac_issue_unsol_event(codec, spec->autocfg.hp_pins[0],
4332 STAC_HP_EVENT);
ff6fdc37
M
4333 return 0;
4334}
c6798d2b
MR
4335
4336static int stac92xx_suspend(struct hda_codec *codec, pm_message_t state)
4337{
4338 struct sigmatel_spec *spec = codec->spec;
4339 if (spec->eapd_mask)
4340 stac_gpio_set(codec, spec->gpio_mask,
4341 spec->gpio_dir, spec->gpio_data &
4342 ~spec->eapd_mask);
4343 return 0;
4344}
ff6fdc37
M
4345#endif
4346
2f2f4251
M
4347static struct hda_codec_ops stac92xx_patch_ops = {
4348 .build_controls = stac92xx_build_controls,
4349 .build_pcms = stac92xx_build_pcms,
4350 .init = stac92xx_init,
4351 .free = stac92xx_free,
4e55096e 4352 .unsol_event = stac92xx_unsol_event,
cb53c626 4353#ifdef SND_HDA_NEEDS_RESUME
c6798d2b 4354 .suspend = stac92xx_suspend,
ff6fdc37
M
4355 .resume = stac92xx_resume,
4356#endif
2f2f4251
M
4357};
4358
4359static int patch_stac9200(struct hda_codec *codec)
4360{
4361 struct sigmatel_spec *spec;
c7d4b2fa 4362 int err;
2f2f4251 4363
e560d8d8 4364 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
2f2f4251
M
4365 if (spec == NULL)
4366 return -ENOMEM;
4367
4368 codec->spec = spec;
a4eed138 4369 spec->num_pins = ARRAY_SIZE(stac9200_pin_nids);
11b44bbd 4370 spec->pin_nids = stac9200_pin_nids;
f5fcc13c
TI
4371 spec->board_config = snd_hda_check_board_config(codec, STAC_9200_MODELS,
4372 stac9200_models,
4373 stac9200_cfg_tbl);
11b44bbd
RF
4374 if (spec->board_config < 0) {
4375 snd_printdd(KERN_INFO "hda_codec: Unknown model for STAC9200, using BIOS defaults\n");
4376 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
4377 } else
4378 err = stac_save_pin_cfgs(codec,
4379 stac9200_brd_tbl[spec->board_config]);
4380 if (err < 0) {
4381 stac92xx_free(codec);
4382 return err;
403d1944 4383 }
2f2f4251
M
4384
4385 spec->multiout.max_channels = 2;
4386 spec->multiout.num_dacs = 1;
4387 spec->multiout.dac_nids = stac9200_dac_nids;
4388 spec->adc_nids = stac9200_adc_nids;
4389 spec->mux_nids = stac9200_mux_nids;
dabbed6f 4390 spec->num_muxes = 1;
8b65727b 4391 spec->num_dmics = 0;
9e05b7a3 4392 spec->num_adcs = 1;
a64135a2 4393 spec->num_pwrs = 0;
c7d4b2fa 4394
58eec423
MCC
4395 if (spec->board_config == STAC_9200_M4 ||
4396 spec->board_config == STAC_9200_M4_2 ||
bf277785 4397 spec->board_config == STAC_9200_OQO)
1194b5b7
TI
4398 spec->init = stac9200_eapd_init;
4399 else
4400 spec->init = stac9200_core_init;
2f2f4251 4401 spec->mixer = stac9200_mixer;
c7d4b2fa 4402
117f257d
TI
4403 if (spec->board_config == STAC_9200_PANASONIC) {
4404 spec->gpio_mask = spec->gpio_dir = 0x09;
4405 spec->gpio_data = 0x00;
4406 }
4407
c7d4b2fa
M
4408 err = stac9200_parse_auto_config(codec);
4409 if (err < 0) {
4410 stac92xx_free(codec);
4411 return err;
4412 }
2f2f4251
M
4413
4414 codec->patch_ops = stac92xx_patch_ops;
4415
4416 return 0;
4417}
4418
8e21c34c
TD
4419static int patch_stac925x(struct hda_codec *codec)
4420{
4421 struct sigmatel_spec *spec;
4422 int err;
4423
4424 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4425 if (spec == NULL)
4426 return -ENOMEM;
4427
4428 codec->spec = spec;
a4eed138 4429 spec->num_pins = ARRAY_SIZE(stac925x_pin_nids);
8e21c34c 4430 spec->pin_nids = stac925x_pin_nids;
9cb36c2a
MCC
4431
4432 /* Check first for codec ID */
4433 spec->board_config = snd_hda_check_board_codec_sid_config(codec,
4434 STAC_925x_MODELS,
4435 stac925x_models,
4436 stac925x_codec_id_cfg_tbl);
4437
4438 /* Now checks for PCI ID, if codec ID is not found */
4439 if (spec->board_config < 0)
4440 spec->board_config = snd_hda_check_board_config(codec,
4441 STAC_925x_MODELS,
8e21c34c
TD
4442 stac925x_models,
4443 stac925x_cfg_tbl);
9e507abd 4444 again:
8e21c34c 4445 if (spec->board_config < 0) {
9cb36c2a 4446 snd_printdd(KERN_INFO "hda_codec: Unknown model for STAC925x,"
2c11f955 4447 "using BIOS defaults\n");
8e21c34c 4448 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
4449 } else
4450 err = stac_save_pin_cfgs(codec,
4451 stac925x_brd_tbl[spec->board_config]);
4452 if (err < 0) {
4453 stac92xx_free(codec);
4454 return err;
8e21c34c
TD
4455 }
4456
4457 spec->multiout.max_channels = 2;
4458 spec->multiout.num_dacs = 1;
4459 spec->multiout.dac_nids = stac925x_dac_nids;
4460 spec->adc_nids = stac925x_adc_nids;
4461 spec->mux_nids = stac925x_mux_nids;
4462 spec->num_muxes = 1;
9e05b7a3 4463 spec->num_adcs = 1;
a64135a2 4464 spec->num_pwrs = 0;
2c11f955
TD
4465 switch (codec->vendor_id) {
4466 case 0x83847632: /* STAC9202 */
4467 case 0x83847633: /* STAC9202D */
4468 case 0x83847636: /* STAC9251 */
4469 case 0x83847637: /* STAC9251D */
f6e9852a 4470 spec->num_dmics = STAC925X_NUM_DMICS;
2c11f955 4471 spec->dmic_nids = stac925x_dmic_nids;
1697055e
TI
4472 spec->num_dmuxes = ARRAY_SIZE(stac925x_dmux_nids);
4473 spec->dmux_nids = stac925x_dmux_nids;
2c11f955
TD
4474 break;
4475 default:
4476 spec->num_dmics = 0;
4477 break;
4478 }
8e21c34c
TD
4479
4480 spec->init = stac925x_core_init;
4481 spec->mixer = stac925x_mixer;
4482
4483 err = stac92xx_parse_auto_config(codec, 0x8, 0x7);
9e507abd
TI
4484 if (!err) {
4485 if (spec->board_config < 0) {
4486 printk(KERN_WARNING "hda_codec: No auto-config is "
4487 "available, default to model=ref\n");
4488 spec->board_config = STAC_925x_REF;
4489 goto again;
4490 }
4491 err = -EINVAL;
4492 }
8e21c34c
TD
4493 if (err < 0) {
4494 stac92xx_free(codec);
4495 return err;
4496 }
4497
4498 codec->patch_ops = stac92xx_patch_ops;
4499
4500 return 0;
4501}
4502
e1f0d669
MR
4503static struct hda_input_mux stac92hd73xx_dmux = {
4504 .num_items = 4,
4505 .items = {
4506 { "Analog Inputs", 0x0b },
e1f0d669
MR
4507 { "Digital Mic 1", 0x09 },
4508 { "Digital Mic 2", 0x0a },
2a9c7816 4509 { "CD", 0x08 },
e1f0d669
MR
4510 }
4511};
4512
4513static int patch_stac92hd73xx(struct hda_codec *codec)
4514{
4515 struct sigmatel_spec *spec;
4516 hda_nid_t conn[STAC92HD73_DAC_COUNT + 2];
4517 int err = 0;
4518
4519 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4520 if (spec == NULL)
4521 return -ENOMEM;
4522
4523 codec->spec = spec;
e99d32b3 4524 codec->slave_dig_outs = stac92hd73xx_slave_dig_outs;
e1f0d669
MR
4525 spec->num_pins = ARRAY_SIZE(stac92hd73xx_pin_nids);
4526 spec->pin_nids = stac92hd73xx_pin_nids;
4527 spec->board_config = snd_hda_check_board_config(codec,
4528 STAC_92HD73XX_MODELS,
4529 stac92hd73xx_models,
4530 stac92hd73xx_cfg_tbl);
4531again:
4532 if (spec->board_config < 0) {
4533 snd_printdd(KERN_INFO "hda_codec: Unknown model for"
4534 " STAC92HD73XX, using BIOS defaults\n");
4535 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
4536 } else
4537 err = stac_save_pin_cfgs(codec,
4538 stac92hd73xx_brd_tbl[spec->board_config]);
4539 if (err < 0) {
4540 stac92xx_free(codec);
4541 return err;
e1f0d669
MR
4542 }
4543
4544 spec->multiout.num_dacs = snd_hda_get_connections(codec, 0x0a,
4545 conn, STAC92HD73_DAC_COUNT + 2) - 1;
4546
4547 if (spec->multiout.num_dacs < 0) {
4548 printk(KERN_WARNING "hda_codec: Could not determine "
4549 "number of channels defaulting to DAC count\n");
4550 spec->multiout.num_dacs = STAC92HD73_DAC_COUNT;
4551 }
4552
4553 switch (spec->multiout.num_dacs) {
4554 case 0x3: /* 6 Channel */
4555 spec->mixer = stac92hd73xx_6ch_mixer;
4556 spec->init = stac92hd73xx_6ch_core_init;
4557 break;
4558 case 0x4: /* 8 Channel */
e1f0d669
MR
4559 spec->mixer = stac92hd73xx_8ch_mixer;
4560 spec->init = stac92hd73xx_8ch_core_init;
4561 break;
4562 case 0x5: /* 10 Channel */
e1f0d669
MR
4563 spec->mixer = stac92hd73xx_10ch_mixer;
4564 spec->init = stac92hd73xx_10ch_core_init;
4565 };
4566
4567 spec->multiout.dac_nids = stac92hd73xx_dac_nids;
4568 spec->aloopback_mask = 0x01;
4569 spec->aloopback_shift = 8;
4570
1cd2224c 4571 spec->digbeep_nid = 0x1c;
e1f0d669
MR
4572 spec->mux_nids = stac92hd73xx_mux_nids;
4573 spec->adc_nids = stac92hd73xx_adc_nids;
4574 spec->dmic_nids = stac92hd73xx_dmic_nids;
4575 spec->dmux_nids = stac92hd73xx_dmux_nids;
d9737751 4576 spec->smux_nids = stac92hd73xx_smux_nids;
89385035 4577 spec->amp_nids = stac92hd73xx_amp_nids;
2a9c7816 4578 spec->num_amps = ARRAY_SIZE(stac92hd73xx_amp_nids);
e1f0d669
MR
4579
4580 spec->num_muxes = ARRAY_SIZE(stac92hd73xx_mux_nids);
4581 spec->num_adcs = ARRAY_SIZE(stac92hd73xx_adc_nids);
1697055e 4582 spec->num_dmuxes = ARRAY_SIZE(stac92hd73xx_dmux_nids);
2a9c7816
MR
4583 memcpy(&spec->private_dimux, &stac92hd73xx_dmux,
4584 sizeof(stac92hd73xx_dmux));
4585
a7662640 4586 switch (spec->board_config) {
6b3ab21e 4587 case STAC_DELL_EQ:
d654a660 4588 spec->init = dell_eq_core_init;
6b3ab21e 4589 /* fallthru */
661cd8fb
TI
4590 case STAC_DELL_M6_AMIC:
4591 case STAC_DELL_M6_DMIC:
4592 case STAC_DELL_M6_BOTH:
2a9c7816 4593 spec->num_smuxes = 0;
2a9c7816
MR
4594 spec->mixer = &stac92hd73xx_6ch_mixer[DELL_M6_MIXER];
4595 spec->amp_nids = &stac92hd73xx_amp_nids[DELL_M6_AMP];
c0cea0d0 4596 spec->eapd_switch = 0;
2a9c7816 4597 spec->num_amps = 1;
6b3ab21e
MR
4598
4599 if (!spec->init)
4600 spec->init = dell_m6_core_init;
661cd8fb
TI
4601 switch (spec->board_config) {
4602 case STAC_DELL_M6_AMIC: /* Analog Mics */
a7662640
MR
4603 stac92xx_set_config_reg(codec, 0x0b, 0x90A70170);
4604 spec->num_dmics = 0;
2a9c7816 4605 spec->private_dimux.num_items = 1;
a7662640 4606 break;
661cd8fb 4607 case STAC_DELL_M6_DMIC: /* Digital Mics */
a7662640
MR
4608 stac92xx_set_config_reg(codec, 0x13, 0x90A60160);
4609 spec->num_dmics = 1;
2a9c7816 4610 spec->private_dimux.num_items = 2;
a7662640 4611 break;
661cd8fb 4612 case STAC_DELL_M6_BOTH: /* Both */
a7662640
MR
4613 stac92xx_set_config_reg(codec, 0x0b, 0x90A70170);
4614 stac92xx_set_config_reg(codec, 0x13, 0x90A60160);
4615 spec->num_dmics = 1;
2a9c7816 4616 spec->private_dimux.num_items = 2;
a7662640
MR
4617 break;
4618 }
4619 break;
4620 default:
4621 spec->num_dmics = STAC92HD73XX_NUM_DMICS;
2a9c7816 4622 spec->num_smuxes = ARRAY_SIZE(stac92hd73xx_smux_nids);
c0cea0d0 4623 spec->eapd_switch = 1;
a7662640 4624 }
b2c4f4d7
MR
4625 if (spec->board_config > STAC_92HD73XX_REF) {
4626 /* GPIO0 High = Enable EAPD */
4627 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x1;
4628 spec->gpio_data = 0x01;
4629 }
2a9c7816 4630 spec->dinput_mux = &spec->private_dimux;
a7662640 4631
a64135a2
MR
4632 spec->num_pwrs = ARRAY_SIZE(stac92hd73xx_pwr_nids);
4633 spec->pwr_nids = stac92hd73xx_pwr_nids;
4634
d9737751 4635 err = stac92xx_parse_auto_config(codec, 0x25, 0x27);
e1f0d669
MR
4636
4637 if (!err) {
4638 if (spec->board_config < 0) {
4639 printk(KERN_WARNING "hda_codec: No auto-config is "
4640 "available, default to model=ref\n");
4641 spec->board_config = STAC_92HD73XX_REF;
4642 goto again;
4643 }
4644 err = -EINVAL;
4645 }
4646
4647 if (err < 0) {
4648 stac92xx_free(codec);
4649 return err;
4650 }
4651
4652 codec->patch_ops = stac92xx_patch_ops;
4653
4654 return 0;
4655}
4656
d0513fc6
MR
4657static struct hda_input_mux stac92hd83xxx_dmux = {
4658 .num_items = 3,
4659 .items = {
4660 { "Analog Inputs", 0x03 },
4661 { "Digital Mic 1", 0x04 },
4662 { "Digital Mic 2", 0x05 },
4663 }
4664};
4665
4666static int patch_stac92hd83xxx(struct hda_codec *codec)
4667{
4668 struct sigmatel_spec *spec;
4669 int err;
4670
4671 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4672 if (spec == NULL)
4673 return -ENOMEM;
4674
4675 codec->spec = spec;
0ffa9807 4676 codec->slave_dig_outs = stac92hd83xxx_slave_dig_outs;
d0513fc6
MR
4677 spec->mono_nid = 0x19;
4678 spec->digbeep_nid = 0x21;
4679 spec->dmic_nids = stac92hd83xxx_dmic_nids;
4680 spec->dmux_nids = stac92hd83xxx_dmux_nids;
4681 spec->adc_nids = stac92hd83xxx_adc_nids;
4682 spec->pwr_nids = stac92hd83xxx_pwr_nids;
4683 spec->pwr_mapping = stac92hd83xxx_pwr_mapping;
4684 spec->num_pwrs = ARRAY_SIZE(stac92hd83xxx_pwr_nids);
4685 spec->multiout.dac_nids = stac92hd83xxx_dac_nids;
4686
4687 spec->init = stac92hd83xxx_core_init;
4688 switch (codec->vendor_id) {
4689 case 0x111d7605:
4690 spec->multiout.num_dacs = STAC92HD81_DAC_COUNT;
4691 break;
4692 default:
4693 spec->num_pwrs--;
4694 spec->init++; /* switch to config #2 */
4695 spec->multiout.num_dacs = STAC92HD83_DAC_COUNT;
4696 }
4697
4698 spec->mixer = stac92hd83xxx_mixer;
4699 spec->num_pins = ARRAY_SIZE(stac92hd83xxx_pin_nids);
4700 spec->num_dmuxes = ARRAY_SIZE(stac92hd83xxx_dmux_nids);
4701 spec->num_adcs = ARRAY_SIZE(stac92hd83xxx_adc_nids);
4702 spec->num_dmics = STAC92HD83XXX_NUM_DMICS;
4703 spec->dinput_mux = &stac92hd83xxx_dmux;
4704 spec->pin_nids = stac92hd83xxx_pin_nids;
4705 spec->board_config = snd_hda_check_board_config(codec,
4706 STAC_92HD83XXX_MODELS,
4707 stac92hd83xxx_models,
4708 stac92hd83xxx_cfg_tbl);
4709again:
4710 if (spec->board_config < 0) {
4711 snd_printdd(KERN_INFO "hda_codec: Unknown model for"
4712 " STAC92HD83XXX, using BIOS defaults\n");
4713 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
4714 } else
4715 err = stac_save_pin_cfgs(codec,
4716 stac92hd83xxx_brd_tbl[spec->board_config]);
4717 if (err < 0) {
4718 stac92xx_free(codec);
4719 return err;
d0513fc6
MR
4720 }
4721
4722 err = stac92xx_parse_auto_config(codec, 0x1d, 0);
4723 if (!err) {
4724 if (spec->board_config < 0) {
4725 printk(KERN_WARNING "hda_codec: No auto-config is "
4726 "available, default to model=ref\n");
4727 spec->board_config = STAC_92HD83XXX_REF;
4728 goto again;
4729 }
4730 err = -EINVAL;
4731 }
4732
4733 if (err < 0) {
4734 stac92xx_free(codec);
4735 return err;
4736 }
4737
4738 codec->patch_ops = stac92xx_patch_ops;
4739
4740 return 0;
4741}
4742
8daaaa97
MR
4743#ifdef SND_HDA_NEEDS_RESUME
4744static void stac92hd71xx_set_power_state(struct hda_codec *codec, int pwr)
4745{
4746 struct sigmatel_spec *spec = codec->spec;
4747 int i;
4748 snd_hda_codec_write_cache(codec, codec->afg, 0,
4749 AC_VERB_SET_POWER_STATE, pwr);
4750
4751 msleep(1);
4752 for (i = 0; i < spec->num_adcs; i++) {
4753 snd_hda_codec_write_cache(codec,
4754 spec->adc_nids[i], 0,
4755 AC_VERB_SET_POWER_STATE, pwr);
4756 }
4757};
4758
4759static int stac92hd71xx_resume(struct hda_codec *codec)
4760{
4761 stac92hd71xx_set_power_state(codec, AC_PWRST_D0);
4762 return stac92xx_resume(codec);
4763}
4764
4765static int stac92hd71xx_suspend(struct hda_codec *codec, pm_message_t state)
4766{
4767 stac92hd71xx_set_power_state(codec, AC_PWRST_D3);
c6798d2b 4768 return stac92xx_suspend(codec, state);
8daaaa97
MR
4769};
4770
4771#endif
4772
4773static struct hda_codec_ops stac92hd71bxx_patch_ops = {
4774 .build_controls = stac92xx_build_controls,
4775 .build_pcms = stac92xx_build_pcms,
4776 .init = stac92xx_init,
4777 .free = stac92xx_free,
4778 .unsol_event = stac92xx_unsol_event,
4779#ifdef SND_HDA_NEEDS_RESUME
8daaaa97 4780 .suspend = stac92hd71xx_suspend,
c6798d2b 4781 .resume = stac92hd71xx_resume,
8daaaa97
MR
4782#endif
4783};
d0513fc6 4784
4b33c767
MR
4785static struct hda_input_mux stac92hd71bxx_dmux = {
4786 .num_items = 4,
4787 .items = {
4788 { "Analog Inputs", 0x00 },
4789 { "Mixer", 0x01 },
4790 { "Digital Mic 1", 0x02 },
4791 { "Digital Mic 2", 0x03 },
4792 }
4793};
4794
e035b841
MR
4795static int patch_stac92hd71bxx(struct hda_codec *codec)
4796{
4797 struct sigmatel_spec *spec;
4798 int err = 0;
4799
4800 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4801 if (spec == NULL)
4802 return -ENOMEM;
4803
4804 codec->spec = spec;
8daaaa97 4805 codec->patch_ops = stac92xx_patch_ops;
e035b841 4806 spec->num_pins = ARRAY_SIZE(stac92hd71bxx_pin_nids);
aafc4412 4807 spec->num_pwrs = ARRAY_SIZE(stac92hd71bxx_pwr_nids);
e035b841 4808 spec->pin_nids = stac92hd71bxx_pin_nids;
4b33c767
MR
4809 memcpy(&spec->private_dimux, &stac92hd71bxx_dmux,
4810 sizeof(stac92hd71bxx_dmux));
e035b841
MR
4811 spec->board_config = snd_hda_check_board_config(codec,
4812 STAC_92HD71BXX_MODELS,
4813 stac92hd71bxx_models,
4814 stac92hd71bxx_cfg_tbl);
4815again:
4816 if (spec->board_config < 0) {
4817 snd_printdd(KERN_INFO "hda_codec: Unknown model for"
4818 " STAC92HD71BXX, using BIOS defaults\n");
4819 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
4820 } else
4821 err = stac_save_pin_cfgs(codec,
4822 stac92hd71bxx_brd_tbl[spec->board_config]);
4823 if (err < 0) {
4824 stac92xx_free(codec);
4825 return err;
e035b841
MR
4826 }
4827
41c3b648
TI
4828 if (spec->board_config > STAC_92HD71BXX_REF) {
4829 /* GPIO0 = EAPD */
4830 spec->gpio_mask = 0x01;
4831 spec->gpio_dir = 0x01;
4832 spec->gpio_data = 0x01;
4833 }
4834
541eee87
MR
4835 switch (codec->vendor_id) {
4836 case 0x111d76b6: /* 4 Port without Analog Mixer */
4837 case 0x111d76b7:
4838 case 0x111d76b4: /* 6 Port without Analog Mixer */
4839 case 0x111d76b5:
4840 spec->mixer = stac92hd71bxx_mixer;
4841 spec->init = stac92hd71bxx_core_init;
0ffa9807 4842 codec->slave_dig_outs = stac92hd71bxx_slave_dig_outs;
541eee87 4843 break;
aafc4412 4844 case 0x111d7608: /* 5 Port with Analog Mixer */
8e5f262b
TI
4845 switch (spec->board_config) {
4846 case STAC_HP_M4:
72474be6 4847 /* Enable VREF power saving on GPIO1 detect */
c6e4c666
TI
4848 err = stac_add_event(spec, codec->afg,
4849 STAC_VREF_EVENT, 0x02);
4850 if (err < 0)
4851 return err;
c5d08bb5 4852 snd_hda_codec_write_cache(codec, codec->afg, 0,
72474be6
MR
4853 AC_VERB_SET_GPIO_UNSOLICITED_RSP_MASK, 0x02);
4854 snd_hda_codec_write_cache(codec, codec->afg, 0,
74aeaabc 4855 AC_VERB_SET_UNSOLICITED_ENABLE,
c6e4c666 4856 AC_USRSP_EN | err);
72474be6
MR
4857 spec->gpio_mask |= 0x02;
4858 break;
4859 }
8daaaa97
MR
4860 if ((codec->revision_id & 0xf) == 0 ||
4861 (codec->revision_id & 0xf) == 1) {
4862#ifdef SND_HDA_NEEDS_RESUME
4863 codec->patch_ops = stac92hd71bxx_patch_ops;
4864#endif
4865 spec->stream_delay = 40; /* 40 milliseconds */
4866 }
4867
aafc4412
MR
4868 /* no output amps */
4869 spec->num_pwrs = 0;
4870 spec->mixer = stac92hd71bxx_analog_mixer;
4b33c767 4871 spec->dinput_mux = &spec->private_dimux;
aafc4412
MR
4872
4873 /* disable VSW */
4874 spec->init = &stac92hd71bxx_analog_core_init[HD_DISABLE_PORTF];
af9f341a 4875 stac_change_pin_config(codec, 0xf, 0x40f000f0);
aafc4412
MR
4876 break;
4877 case 0x111d7603: /* 6 Port with Analog Mixer */
8daaaa97
MR
4878 if ((codec->revision_id & 0xf) == 1) {
4879#ifdef SND_HDA_NEEDS_RESUME
4880 codec->patch_ops = stac92hd71bxx_patch_ops;
4881#endif
4882 spec->stream_delay = 40; /* 40 milliseconds */
4883 }
4884
aafc4412
MR
4885 /* no output amps */
4886 spec->num_pwrs = 0;
4887 /* fallthru */
541eee87 4888 default:
4b33c767 4889 spec->dinput_mux = &spec->private_dimux;
541eee87
MR
4890 spec->mixer = stac92hd71bxx_analog_mixer;
4891 spec->init = stac92hd71bxx_analog_core_init;
0ffa9807 4892 codec->slave_dig_outs = stac92hd71bxx_slave_dig_outs;
541eee87
MR
4893 }
4894
4b33c767 4895 spec->aloopback_mask = 0x50;
541eee87
MR
4896 spec->aloopback_shift = 0;
4897
8daaaa97 4898 spec->powerdown_adcs = 1;
1cd2224c 4899 spec->digbeep_nid = 0x26;
e035b841
MR
4900 spec->mux_nids = stac92hd71bxx_mux_nids;
4901 spec->adc_nids = stac92hd71bxx_adc_nids;
4902 spec->dmic_nids = stac92hd71bxx_dmic_nids;
e1f0d669 4903 spec->dmux_nids = stac92hd71bxx_dmux_nids;
d9737751 4904 spec->smux_nids = stac92hd71bxx_smux_nids;
aafc4412 4905 spec->pwr_nids = stac92hd71bxx_pwr_nids;
e035b841
MR
4906
4907 spec->num_muxes = ARRAY_SIZE(stac92hd71bxx_mux_nids);
4908 spec->num_adcs = ARRAY_SIZE(stac92hd71bxx_adc_nids);
e035b841 4909
6a14f585
MR
4910 switch (spec->board_config) {
4911 case STAC_HP_M4:
6a14f585 4912 /* enable internal microphone */
af9f341a 4913 stac_change_pin_config(codec, 0x0e, 0x01813040);
b9aea715
MR
4914 stac92xx_auto_set_pinctl(codec, 0x0e,
4915 AC_PINCTL_IN_EN | AC_PINCTL_VREF_80);
3a7abfd2
MR
4916 /* fallthru */
4917 case STAC_DELL_M4_2:
4918 spec->num_dmics = 0;
4919 spec->num_smuxes = 0;
4920 spec->num_dmuxes = 0;
4921 break;
4922 case STAC_DELL_M4_1:
4923 case STAC_DELL_M4_3:
4924 spec->num_dmics = 1;
4925 spec->num_smuxes = 0;
4926 spec->num_dmuxes = 0;
6a14f585
MR
4927 break;
4928 default:
4929 spec->num_dmics = STAC92HD71BXX_NUM_DMICS;
4930 spec->num_smuxes = ARRAY_SIZE(stac92hd71bxx_smux_nids);
4931 spec->num_dmuxes = ARRAY_SIZE(stac92hd71bxx_dmux_nids);
4932 };
4933
aea7bb0a 4934 spec->multiout.num_dacs = 1;
e035b841
MR
4935 spec->multiout.hp_nid = 0x11;
4936 spec->multiout.dac_nids = stac92hd71bxx_dac_nids;
4b33c767
MR
4937 if (spec->dinput_mux)
4938 spec->private_dimux.num_items +=
4939 spec->num_dmics -
4940 (ARRAY_SIZE(stac92hd71bxx_dmic_nids) - 1);
e035b841
MR
4941
4942 err = stac92xx_parse_auto_config(codec, 0x21, 0x23);
4943 if (!err) {
4944 if (spec->board_config < 0) {
4945 printk(KERN_WARNING "hda_codec: No auto-config is "
4946 "available, default to model=ref\n");
4947 spec->board_config = STAC_92HD71BXX_REF;
4948 goto again;
4949 }
4950 err = -EINVAL;
4951 }
4952
4953 if (err < 0) {
4954 stac92xx_free(codec);
4955 return err;
4956 }
4957
e035b841
MR
4958 return 0;
4959};
4960
2f2f4251
M
4961static int patch_stac922x(struct hda_codec *codec)
4962{
4963 struct sigmatel_spec *spec;
c7d4b2fa 4964 int err;
2f2f4251 4965
e560d8d8 4966 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
2f2f4251
M
4967 if (spec == NULL)
4968 return -ENOMEM;
4969
4970 codec->spec = spec;
a4eed138 4971 spec->num_pins = ARRAY_SIZE(stac922x_pin_nids);
11b44bbd 4972 spec->pin_nids = stac922x_pin_nids;
f5fcc13c
TI
4973 spec->board_config = snd_hda_check_board_config(codec, STAC_922X_MODELS,
4974 stac922x_models,
4975 stac922x_cfg_tbl);
536319af 4976 if (spec->board_config == STAC_INTEL_MAC_AUTO) {
4fe5195c
MR
4977 spec->gpio_mask = spec->gpio_dir = 0x03;
4978 spec->gpio_data = 0x03;
3fc24d85
TI
4979 /* Intel Macs have all same PCI SSID, so we need to check
4980 * codec SSID to distinguish the exact models
4981 */
6f0778d8 4982 printk(KERN_INFO "hda_codec: STAC922x, Apple subsys_id=%x\n", codec->subsystem_id);
3fc24d85 4983 switch (codec->subsystem_id) {
5d5d3bc3
IZ
4984
4985 case 0x106b0800:
4986 spec->board_config = STAC_INTEL_MAC_V1;
c45e20eb 4987 break;
5d5d3bc3
IZ
4988 case 0x106b0600:
4989 case 0x106b0700:
4990 spec->board_config = STAC_INTEL_MAC_V2;
6f0778d8 4991 break;
5d5d3bc3
IZ
4992 case 0x106b0e00:
4993 case 0x106b0f00:
4994 case 0x106b1600:
4995 case 0x106b1700:
4996 case 0x106b0200:
4997 case 0x106b1e00:
4998 spec->board_config = STAC_INTEL_MAC_V3;
3fc24d85 4999 break;
5d5d3bc3
IZ
5000 case 0x106b1a00:
5001 case 0x00000100:
5002 spec->board_config = STAC_INTEL_MAC_V4;
f16928fb 5003 break;
5d5d3bc3
IZ
5004 case 0x106b0a00:
5005 case 0x106b2200:
5006 spec->board_config = STAC_INTEL_MAC_V5;
0dae0f83 5007 break;
536319af
NB
5008 default:
5009 spec->board_config = STAC_INTEL_MAC_V3;
5010 break;
3fc24d85
TI
5011 }
5012 }
5013
9e507abd 5014 again:
11b44bbd
RF
5015 if (spec->board_config < 0) {
5016 snd_printdd(KERN_INFO "hda_codec: Unknown model for STAC922x, "
5017 "using BIOS defaults\n");
5018 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
5019 } else
5020 err = stac_save_pin_cfgs(codec,
5021 stac922x_brd_tbl[spec->board_config]);
5022 if (err < 0) {
5023 stac92xx_free(codec);
5024 return err;
403d1944 5025 }
2f2f4251 5026
c7d4b2fa
M
5027 spec->adc_nids = stac922x_adc_nids;
5028 spec->mux_nids = stac922x_mux_nids;
2549413e 5029 spec->num_muxes = ARRAY_SIZE(stac922x_mux_nids);
9e05b7a3 5030 spec->num_adcs = ARRAY_SIZE(stac922x_adc_nids);
8b65727b 5031 spec->num_dmics = 0;
a64135a2 5032 spec->num_pwrs = 0;
c7d4b2fa
M
5033
5034 spec->init = stac922x_core_init;
2f2f4251 5035 spec->mixer = stac922x_mixer;
c7d4b2fa
M
5036
5037 spec->multiout.dac_nids = spec->dac_nids;
19039bd0 5038
3cc08dc6 5039 err = stac92xx_parse_auto_config(codec, 0x08, 0x09);
9e507abd
TI
5040 if (!err) {
5041 if (spec->board_config < 0) {
5042 printk(KERN_WARNING "hda_codec: No auto-config is "
5043 "available, default to model=ref\n");
5044 spec->board_config = STAC_D945_REF;
5045 goto again;
5046 }
5047 err = -EINVAL;
5048 }
3cc08dc6
MP
5049 if (err < 0) {
5050 stac92xx_free(codec);
5051 return err;
5052 }
5053
5054 codec->patch_ops = stac92xx_patch_ops;
5055
807a4636
TI
5056 /* Fix Mux capture level; max to 2 */
5057 snd_hda_override_amp_caps(codec, 0x12, HDA_OUTPUT,
5058 (0 << AC_AMPCAP_OFFSET_SHIFT) |
5059 (2 << AC_AMPCAP_NUM_STEPS_SHIFT) |
5060 (0x27 << AC_AMPCAP_STEP_SIZE_SHIFT) |
5061 (0 << AC_AMPCAP_MUTE_SHIFT));
5062
3cc08dc6
MP
5063 return 0;
5064}
5065
5066static int patch_stac927x(struct hda_codec *codec)
5067{
5068 struct sigmatel_spec *spec;
5069 int err;
5070
5071 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
5072 if (spec == NULL)
5073 return -ENOMEM;
5074
5075 codec->spec = spec;
a4eed138 5076 spec->num_pins = ARRAY_SIZE(stac927x_pin_nids);
11b44bbd 5077 spec->pin_nids = stac927x_pin_nids;
f5fcc13c
TI
5078 spec->board_config = snd_hda_check_board_config(codec, STAC_927X_MODELS,
5079 stac927x_models,
5080 stac927x_cfg_tbl);
9e507abd 5081 again:
8e9068b1
MR
5082 if (spec->board_config < 0 || !stac927x_brd_tbl[spec->board_config]) {
5083 if (spec->board_config < 0)
5084 snd_printdd(KERN_INFO "hda_codec: Unknown model for"
5085 "STAC927x, using BIOS defaults\n");
11b44bbd 5086 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
5087 } else
5088 err = stac_save_pin_cfgs(codec,
5089 stac927x_brd_tbl[spec->board_config]);
5090 if (err < 0) {
5091 stac92xx_free(codec);
5092 return err;
3cc08dc6
MP
5093 }
5094
1cd2224c 5095 spec->digbeep_nid = 0x23;
8e9068b1
MR
5096 spec->adc_nids = stac927x_adc_nids;
5097 spec->num_adcs = ARRAY_SIZE(stac927x_adc_nids);
5098 spec->mux_nids = stac927x_mux_nids;
5099 spec->num_muxes = ARRAY_SIZE(stac927x_mux_nids);
d9737751
MR
5100 spec->smux_nids = stac927x_smux_nids;
5101 spec->num_smuxes = ARRAY_SIZE(stac927x_smux_nids);
65973632 5102 spec->spdif_labels = stac927x_spdif_labels;
b76c850f 5103 spec->dac_list = stac927x_dac_nids;
8e9068b1
MR
5104 spec->multiout.dac_nids = spec->dac_nids;
5105
81d3dbde 5106 switch (spec->board_config) {
93ed1503 5107 case STAC_D965_3ST:
93ed1503 5108 case STAC_D965_5ST:
8e9068b1 5109 /* GPIO0 High = Enable EAPD */
0fc9dec4 5110 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x01;
4fe5195c 5111 spec->gpio_data = 0x01;
8e9068b1
MR
5112 spec->num_dmics = 0;
5113
93ed1503 5114 spec->init = d965_core_init;
9e05b7a3 5115 spec->mixer = stac927x_mixer;
81d3dbde 5116 break;
8e9068b1 5117 case STAC_DELL_BIOS:
780c8be4
MR
5118 switch (codec->subsystem_id) {
5119 case 0x10280209:
5120 case 0x1028022e:
5121 /* correct the device field to SPDIF out */
af9f341a 5122 stac_change_pin_config(codec, 0x21, 0x01442070);
780c8be4
MR
5123 break;
5124 };
03d7ca17 5125 /* configure the analog microphone on some laptops */
af9f341a 5126 stac_change_pin_config(codec, 0x0c, 0x90a79130);
2f32d909 5127 /* correct the front output jack as a hp out */
af9f341a 5128 stac_change_pin_config(codec, 0x0f, 0x0227011f);
c481fca3 5129 /* correct the front input jack as a mic */
af9f341a 5130 stac_change_pin_config(codec, 0x0e, 0x02a79130);
c481fca3 5131 /* fallthru */
8e9068b1
MR
5132 case STAC_DELL_3ST:
5133 /* GPIO2 High = Enable EAPD */
0fc9dec4 5134 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x04;
4fe5195c 5135 spec->gpio_data = 0x04;
7f16859a
MR
5136 spec->dmic_nids = stac927x_dmic_nids;
5137 spec->num_dmics = STAC927X_NUM_DMICS;
f1f208d0 5138
8e9068b1
MR
5139 spec->init = d965_core_init;
5140 spec->mixer = stac927x_mixer;
5141 spec->dmux_nids = stac927x_dmux_nids;
1697055e 5142 spec->num_dmuxes = ARRAY_SIZE(stac927x_dmux_nids);
7f16859a
MR
5143 break;
5144 default:
b2c4f4d7
MR
5145 if (spec->board_config > STAC_D965_REF) {
5146 /* GPIO0 High = Enable EAPD */
5147 spec->eapd_mask = spec->gpio_mask = 0x01;
5148 spec->gpio_dir = spec->gpio_data = 0x01;
5149 }
8e9068b1
MR
5150 spec->num_dmics = 0;
5151
5152 spec->init = stac927x_core_init;
5153 spec->mixer = stac927x_mixer;
7f16859a
MR
5154 }
5155
a64135a2 5156 spec->num_pwrs = 0;
e1f0d669
MR
5157 spec->aloopback_mask = 0x40;
5158 spec->aloopback_shift = 0;
c0cea0d0 5159 spec->eapd_switch = 1;
8e9068b1 5160
3cc08dc6 5161 err = stac92xx_parse_auto_config(codec, 0x1e, 0x20);
9e507abd
TI
5162 if (!err) {
5163 if (spec->board_config < 0) {
5164 printk(KERN_WARNING "hda_codec: No auto-config is "
5165 "available, default to model=ref\n");
5166 spec->board_config = STAC_D965_REF;
5167 goto again;
5168 }
5169 err = -EINVAL;
5170 }
c7d4b2fa
M
5171 if (err < 0) {
5172 stac92xx_free(codec);
5173 return err;
5174 }
2f2f4251
M
5175
5176 codec->patch_ops = stac92xx_patch_ops;
5177
52987656
TI
5178 /*
5179 * !!FIXME!!
5180 * The STAC927x seem to require fairly long delays for certain
5181 * command sequences. With too short delays (even if the answer
5182 * is set to RIRB properly), it results in the silence output
5183 * on some hardwares like Dell.
5184 *
5185 * The below flag enables the longer delay (see get_response
5186 * in hda_intel.c).
5187 */
5188 codec->bus->needs_damn_long_delay = 1;
5189
2f2f4251
M
5190 return 0;
5191}
5192
f3302a59
MP
5193static int patch_stac9205(struct hda_codec *codec)
5194{
5195 struct sigmatel_spec *spec;
8259980e 5196 int err;
f3302a59
MP
5197
5198 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
5199 if (spec == NULL)
5200 return -ENOMEM;
5201
5202 codec->spec = spec;
a4eed138 5203 spec->num_pins = ARRAY_SIZE(stac9205_pin_nids);
11b44bbd 5204 spec->pin_nids = stac9205_pin_nids;
f5fcc13c
TI
5205 spec->board_config = snd_hda_check_board_config(codec, STAC_9205_MODELS,
5206 stac9205_models,
5207 stac9205_cfg_tbl);
9e507abd 5208 again:
11b44bbd
RF
5209 if (spec->board_config < 0) {
5210 snd_printdd(KERN_INFO "hda_codec: Unknown model for STAC9205, using BIOS defaults\n");
5211 err = stac92xx_save_bios_config_regs(codec);
af9f341a
TI
5212 } else
5213 err = stac_save_pin_cfgs(codec,
5214 stac9205_brd_tbl[spec->board_config]);
5215 if (err < 0) {
5216 stac92xx_free(codec);
5217 return err;
f3302a59
MP
5218 }
5219
1cd2224c 5220 spec->digbeep_nid = 0x23;
f3302a59 5221 spec->adc_nids = stac9205_adc_nids;
9e05b7a3 5222 spec->num_adcs = ARRAY_SIZE(stac9205_adc_nids);
f3302a59 5223 spec->mux_nids = stac9205_mux_nids;
2549413e 5224 spec->num_muxes = ARRAY_SIZE(stac9205_mux_nids);
d9737751
MR
5225 spec->smux_nids = stac9205_smux_nids;
5226 spec->num_smuxes = ARRAY_SIZE(stac9205_smux_nids);
8b65727b 5227 spec->dmic_nids = stac9205_dmic_nids;
f6e9852a 5228 spec->num_dmics = STAC9205_NUM_DMICS;
e1f0d669 5229 spec->dmux_nids = stac9205_dmux_nids;
1697055e 5230 spec->num_dmuxes = ARRAY_SIZE(stac9205_dmux_nids);
a64135a2 5231 spec->num_pwrs = 0;
f3302a59
MP
5232
5233 spec->init = stac9205_core_init;
5234 spec->mixer = stac9205_mixer;
5235
e1f0d669
MR
5236 spec->aloopback_mask = 0x40;
5237 spec->aloopback_shift = 0;
c0cea0d0 5238 spec->eapd_switch = 1;
f3302a59 5239 spec->multiout.dac_nids = spec->dac_nids;
87d48363 5240
ae0a8ed8 5241 switch (spec->board_config){
ae0a8ed8 5242 case STAC_9205_DELL_M43:
87d48363 5243 /* Enable SPDIF in/out */
af9f341a
TI
5244 stac_change_pin_config(codec, 0x1f, 0x01441030);
5245 stac_change_pin_config(codec, 0x20, 0x1c410030);
87d48363 5246
4fe5195c 5247 /* Enable unsol response for GPIO4/Dock HP connection */
c6e4c666
TI
5248 err = stac_add_event(spec, codec->afg, STAC_VREF_EVENT, 0x01);
5249 if (err < 0)
5250 return err;
c5d08bb5 5251 snd_hda_codec_write_cache(codec, codec->afg, 0,
4fe5195c
MR
5252 AC_VERB_SET_GPIO_UNSOLICITED_RSP_MASK, 0x10);
5253 snd_hda_codec_write_cache(codec, codec->afg, 0,
c6e4c666
TI
5254 AC_VERB_SET_UNSOLICITED_ENABLE,
5255 AC_USRSP_EN | err);
4fe5195c
MR
5256
5257 spec->gpio_dir = 0x0b;
0fc9dec4 5258 spec->eapd_mask = 0x01;
4fe5195c
MR
5259 spec->gpio_mask = 0x1b;
5260 spec->gpio_mute = 0x10;
e2e7d624 5261 /* GPIO0 High = EAPD, GPIO1 Low = Headphone Mute,
4fe5195c 5262 * GPIO3 Low = DRM
87d48363 5263 */
4fe5195c 5264 spec->gpio_data = 0x01;
ae0a8ed8 5265 break;
b2c4f4d7
MR
5266 case STAC_9205_REF:
5267 /* SPDIF-In enabled */
5268 break;
ae0a8ed8
TD
5269 default:
5270 /* GPIO0 High = EAPD */
0fc9dec4 5271 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x1;
4fe5195c 5272 spec->gpio_data = 0x01;
ae0a8ed8
TD
5273 break;
5274 }
33382403 5275
f3302a59 5276 err = stac92xx_parse_auto_config(codec, 0x1f, 0x20);
9e507abd
TI
5277 if (!err) {
5278 if (spec->board_config < 0) {
5279 printk(KERN_WARNING "hda_codec: No auto-config is "
5280 "available, default to model=ref\n");
5281 spec->board_config = STAC_9205_REF;
5282 goto again;
5283 }
5284 err = -EINVAL;
5285 }
f3302a59
MP
5286 if (err < 0) {
5287 stac92xx_free(codec);
5288 return err;
5289 }
5290
5291 codec->patch_ops = stac92xx_patch_ops;
5292
5293 return 0;
5294}
5295
db064e50 5296/*
6d859065 5297 * STAC9872 hack
db064e50
TI
5298 */
5299
99ccc560 5300/* static config for Sony VAIO FE550G and Sony VAIO AR */
db064e50
TI
5301static hda_nid_t vaio_dacs[] = { 0x2 };
5302#define VAIO_HP_DAC 0x5
5303static hda_nid_t vaio_adcs[] = { 0x8 /*,0x6*/ };
5304static hda_nid_t vaio_mux_nids[] = { 0x15 };
5305
5306static struct hda_input_mux vaio_mux = {
a3a2f429 5307 .num_items = 3,
db064e50 5308 .items = {
d773781c 5309 /* { "HP", 0x0 }, */
1624cb9a
TI
5310 { "Mic Jack", 0x1 },
5311 { "Internal Mic", 0x2 },
db064e50
TI
5312 { "PCM", 0x3 },
5313 }
5314};
5315
5316static struct hda_verb vaio_init[] = {
5317 {0x0a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP }, /* HP <- 0x2 */
72e7b0dd 5318 {0x0a, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | STAC_HP_EVENT},
db064e50
TI
5319 {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT }, /* Speaker <- 0x5 */
5320 {0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* Mic? (<- 0x2) */
5321 {0x0e, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN }, /* CD */
5322 {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* Mic? */
1624cb9a 5323 {0x15, AC_VERB_SET_CONNECT_SEL, 0x1}, /* mic-sel: 0a,0d,14,02 */
db064e50
TI
5324 {0x02, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, /* HP */
5325 {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, /* Speaker */
5326 {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, /* capture sw/vol -> 0x8 */
5327 {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, /* CD-in -> 0x6 */
5328 {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, /* Mic-in -> 0x9 */
5329 {}
5330};
5331
6d859065
GM
5332static struct hda_verb vaio_ar_init[] = {
5333 {0x0a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP }, /* HP <- 0x2 */
5334 {0x0f, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT }, /* Speaker <- 0x5 */
5335 {0x0d, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* Mic? (<- 0x2) */
5336 {0x0e, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN }, /* CD */
5337/* {0x11, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_OUT },*/ /* Optical Out */
5338 {0x14, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80 }, /* Mic? */
1624cb9a 5339 {0x15, AC_VERB_SET_CONNECT_SEL, 0x1}, /* mic-sel: 0a,0d,14,02 */
6d859065
GM
5340 {0x02, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, /* HP */
5341 {0x05, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE}, /* Speaker */
5342/* {0x10, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE},*/ /* Optical Out */
5343 {0x09, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(0)}, /* capture sw/vol -> 0x8 */
5344 {0x07, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)}, /* CD-in -> 0x6 */
5345 {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, /* Mic-in -> 0x9 */
5346 {}
5347};
5348
db064e50 5349static struct snd_kcontrol_new vaio_mixer[] = {
127e82e3
TI
5350 HDA_CODEC_VOLUME("Headphone Playback Volume", 0x02, 0, HDA_OUTPUT),
5351 HDA_CODEC_MUTE("Headphone Playback Switch", 0x02, 0, HDA_OUTPUT),
5352 HDA_CODEC_VOLUME("Speaker Playback Volume", 0x05, 0, HDA_OUTPUT),
5353 HDA_CODEC_MUTE("Speaker Playback Switch", 0x05, 0, HDA_OUTPUT),
db064e50
TI
5354 /* HDA_CODEC_VOLUME("CD Capture Volume", 0x07, 0, HDA_INPUT), */
5355 HDA_CODEC_VOLUME("Capture Volume", 0x09, 0, HDA_INPUT),
5356 HDA_CODEC_MUTE("Capture Switch", 0x09, 0, HDA_INPUT),
5357 {
5358 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
5359 .name = "Capture Source",
5360 .count = 1,
5361 .info = stac92xx_mux_enum_info,
5362 .get = stac92xx_mux_enum_get,
5363 .put = stac92xx_mux_enum_put,
5364 },
5365 {}
5366};
5367
6d859065 5368static struct snd_kcontrol_new vaio_ar_mixer[] = {
127e82e3
TI
5369 HDA_CODEC_VOLUME("Headphone Playback Volume", 0x02, 0, HDA_OUTPUT),
5370 HDA_CODEC_MUTE("Headphone Playback Switch", 0x02, 0, HDA_OUTPUT),
5371 HDA_CODEC_VOLUME("Speaker Playback Volume", 0x05, 0, HDA_OUTPUT),
5372 HDA_CODEC_MUTE("Speaker Playback Switch", 0x05, 0, HDA_OUTPUT),
6d859065
GM
5373 /* HDA_CODEC_VOLUME("CD Capture Volume", 0x07, 0, HDA_INPUT), */
5374 HDA_CODEC_VOLUME("Capture Volume", 0x09, 0, HDA_INPUT),
5375 HDA_CODEC_MUTE("Capture Switch", 0x09, 0, HDA_INPUT),
5376 /*HDA_CODEC_MUTE("Optical Out Switch", 0x10, 0, HDA_OUTPUT),
5377 HDA_CODEC_VOLUME("Optical Out Volume", 0x10, 0, HDA_OUTPUT),*/
5378 {
5379 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
5380 .name = "Capture Source",
5381 .count = 1,
5382 .info = stac92xx_mux_enum_info,
5383 .get = stac92xx_mux_enum_get,
5384 .put = stac92xx_mux_enum_put,
5385 },
5386 {}
5387};
5388
5389static struct hda_codec_ops stac9872_patch_ops = {
db064e50
TI
5390 .build_controls = stac92xx_build_controls,
5391 .build_pcms = stac92xx_build_pcms,
5392 .init = stac92xx_init,
5393 .free = stac92xx_free,
cb53c626 5394#ifdef SND_HDA_NEEDS_RESUME
db064e50
TI
5395 .resume = stac92xx_resume,
5396#endif
5397};
5398
72e7b0dd
TI
5399static int stac9872_vaio_init(struct hda_codec *codec)
5400{
5401 int err;
5402
5403 err = stac92xx_init(codec);
5404 if (err < 0)
5405 return err;
5406 if (codec->patch_ops.unsol_event)
5407 codec->patch_ops.unsol_event(codec, STAC_HP_EVENT << 26);
5408 return 0;
5409}
5410
5411static void stac9872_vaio_hp_detect(struct hda_codec *codec, unsigned int res)
5412{
40c1d308 5413 if (get_hp_pin_presence(codec, 0x0a)) {
72e7b0dd
TI
5414 stac92xx_reset_pinctl(codec, 0x0f, AC_PINCTL_OUT_EN);
5415 stac92xx_set_pinctl(codec, 0x0a, AC_PINCTL_OUT_EN);
5416 } else {
5417 stac92xx_reset_pinctl(codec, 0x0a, AC_PINCTL_OUT_EN);
5418 stac92xx_set_pinctl(codec, 0x0f, AC_PINCTL_OUT_EN);
5419 }
5420}
5421
5422static void stac9872_vaio_unsol_event(struct hda_codec *codec, unsigned int res)
5423{
5424 switch (res >> 26) {
5425 case STAC_HP_EVENT:
5426 stac9872_vaio_hp_detect(codec, res);
5427 break;
5428 }
5429}
5430
5431static struct hda_codec_ops stac9872_vaio_patch_ops = {
5432 .build_controls = stac92xx_build_controls,
5433 .build_pcms = stac92xx_build_pcms,
5434 .init = stac9872_vaio_init,
5435 .free = stac92xx_free,
5436 .unsol_event = stac9872_vaio_unsol_event,
5437#ifdef CONFIG_PM
5438 .resume = stac92xx_resume,
5439#endif
5440};
5441
6d859065
GM
5442enum { /* FE and SZ series. id=0x83847661 and subsys=0x104D0700 or 104D1000. */
5443 CXD9872RD_VAIO,
5444 /* Unknown. id=0x83847662 and subsys=0x104D1200 or 104D1000. */
5445 STAC9872AK_VAIO,
5446 /* Unknown. id=0x83847661 and subsys=0x104D1200. */
5447 STAC9872K_VAIO,
5448 /* AR Series. id=0x83847664 and subsys=104D1300 */
f5fcc13c
TI
5449 CXD9872AKD_VAIO,
5450 STAC_9872_MODELS,
5451};
5452
5453static const char *stac9872_models[STAC_9872_MODELS] = {
5454 [CXD9872RD_VAIO] = "vaio",
5455 [CXD9872AKD_VAIO] = "vaio-ar",
5456};
5457
5458static struct snd_pci_quirk stac9872_cfg_tbl[] = {
5459 SND_PCI_QUIRK(0x104d, 0x81e6, "Sony VAIO F/S", CXD9872RD_VAIO),
5460 SND_PCI_QUIRK(0x104d, 0x81ef, "Sony VAIO F/S", CXD9872RD_VAIO),
5461 SND_PCI_QUIRK(0x104d, 0x81fd, "Sony VAIO AR", CXD9872AKD_VAIO),
68e22543 5462 SND_PCI_QUIRK(0x104d, 0x8205, "Sony VAIO AR", CXD9872AKD_VAIO),
db064e50
TI
5463 {}
5464};
5465
6d859065 5466static int patch_stac9872(struct hda_codec *codec)
db064e50
TI
5467{
5468 struct sigmatel_spec *spec;
5469 int board_config;
5470
f5fcc13c
TI
5471 board_config = snd_hda_check_board_config(codec, STAC_9872_MODELS,
5472 stac9872_models,
5473 stac9872_cfg_tbl);
db064e50
TI
5474 if (board_config < 0)
5475 /* unknown config, let generic-parser do its job... */
5476 return snd_hda_parse_generic_codec(codec);
5477
5478 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
5479 if (spec == NULL)
5480 return -ENOMEM;
5481
5482 codec->spec = spec;
5483 switch (board_config) {
6d859065
GM
5484 case CXD9872RD_VAIO:
5485 case STAC9872AK_VAIO:
5486 case STAC9872K_VAIO:
db064e50
TI
5487 spec->mixer = vaio_mixer;
5488 spec->init = vaio_init;
5489 spec->multiout.max_channels = 2;
5490 spec->multiout.num_dacs = ARRAY_SIZE(vaio_dacs);
5491 spec->multiout.dac_nids = vaio_dacs;
5492 spec->multiout.hp_nid = VAIO_HP_DAC;
5493 spec->num_adcs = ARRAY_SIZE(vaio_adcs);
5494 spec->adc_nids = vaio_adcs;
a64135a2 5495 spec->num_pwrs = 0;
db064e50
TI
5496 spec->input_mux = &vaio_mux;
5497 spec->mux_nids = vaio_mux_nids;
72e7b0dd 5498 codec->patch_ops = stac9872_vaio_patch_ops;
db064e50 5499 break;
6d859065
GM
5500
5501 case CXD9872AKD_VAIO:
5502 spec->mixer = vaio_ar_mixer;
5503 spec->init = vaio_ar_init;
5504 spec->multiout.max_channels = 2;
5505 spec->multiout.num_dacs = ARRAY_SIZE(vaio_dacs);
5506 spec->multiout.dac_nids = vaio_dacs;
5507 spec->multiout.hp_nid = VAIO_HP_DAC;
5508 spec->num_adcs = ARRAY_SIZE(vaio_adcs);
a64135a2 5509 spec->num_pwrs = 0;
6d859065
GM
5510 spec->adc_nids = vaio_adcs;
5511 spec->input_mux = &vaio_mux;
5512 spec->mux_nids = vaio_mux_nids;
72e7b0dd 5513 codec->patch_ops = stac9872_patch_ops;
6d859065 5514 break;
db064e50
TI
5515 }
5516
db064e50
TI
5517 return 0;
5518}
5519
5520
2f2f4251
M
5521/*
5522 * patch entries
5523 */
1289e9e8 5524static struct hda_codec_preset snd_hda_preset_sigmatel[] = {
2f2f4251
M
5525 { .id = 0x83847690, .name = "STAC9200", .patch = patch_stac9200 },
5526 { .id = 0x83847882, .name = "STAC9220 A1", .patch = patch_stac922x },
5527 { .id = 0x83847680, .name = "STAC9221 A1", .patch = patch_stac922x },
5528 { .id = 0x83847880, .name = "STAC9220 A2", .patch = patch_stac922x },
5529 { .id = 0x83847681, .name = "STAC9220D/9223D A2", .patch = patch_stac922x },
5530 { .id = 0x83847682, .name = "STAC9221 A2", .patch = patch_stac922x },
5531 { .id = 0x83847683, .name = "STAC9221D A2", .patch = patch_stac922x },
22a27c7f
MP
5532 { .id = 0x83847618, .name = "STAC9227", .patch = patch_stac927x },
5533 { .id = 0x83847619, .name = "STAC9227", .patch = patch_stac927x },
5534 { .id = 0x83847616, .name = "STAC9228", .patch = patch_stac927x },
5535 { .id = 0x83847617, .name = "STAC9228", .patch = patch_stac927x },
5536 { .id = 0x83847614, .name = "STAC9229", .patch = patch_stac927x },
5537 { .id = 0x83847615, .name = "STAC9229", .patch = patch_stac927x },
3cc08dc6
MP
5538 { .id = 0x83847620, .name = "STAC9274", .patch = patch_stac927x },
5539 { .id = 0x83847621, .name = "STAC9274D", .patch = patch_stac927x },
5540 { .id = 0x83847622, .name = "STAC9273X", .patch = patch_stac927x },
5541 { .id = 0x83847623, .name = "STAC9273D", .patch = patch_stac927x },
5542 { .id = 0x83847624, .name = "STAC9272X", .patch = patch_stac927x },
5543 { .id = 0x83847625, .name = "STAC9272D", .patch = patch_stac927x },
5544 { .id = 0x83847626, .name = "STAC9271X", .patch = patch_stac927x },
5545 { .id = 0x83847627, .name = "STAC9271D", .patch = patch_stac927x },
5546 { .id = 0x83847628, .name = "STAC9274X5NH", .patch = patch_stac927x },
5547 { .id = 0x83847629, .name = "STAC9274D5NH", .patch = patch_stac927x },
8e21c34c
TD
5548 { .id = 0x83847632, .name = "STAC9202", .patch = patch_stac925x },
5549 { .id = 0x83847633, .name = "STAC9202D", .patch = patch_stac925x },
5550 { .id = 0x83847634, .name = "STAC9250", .patch = patch_stac925x },
5551 { .id = 0x83847635, .name = "STAC9250D", .patch = patch_stac925x },
5552 { .id = 0x83847636, .name = "STAC9251", .patch = patch_stac925x },
5553 { .id = 0x83847637, .name = "STAC9250D", .patch = patch_stac925x },
7bd3c0f7
TI
5554 { .id = 0x83847645, .name = "92HD206X", .patch = patch_stac927x },
5555 { .id = 0x83847646, .name = "92HD206D", .patch = patch_stac927x },
6d859065
GM
5556 /* The following does not take into account .id=0x83847661 when subsys =
5557 * 104D0C00 which is STAC9225s. Because of this, some SZ Notebooks are
5558 * currently not fully supported.
5559 */
5560 { .id = 0x83847661, .name = "CXD9872RD/K", .patch = patch_stac9872 },
5561 { .id = 0x83847662, .name = "STAC9872AK", .patch = patch_stac9872 },
5562 { .id = 0x83847664, .name = "CXD9872AKD", .patch = patch_stac9872 },
f3302a59
MP
5563 { .id = 0x838476a0, .name = "STAC9205", .patch = patch_stac9205 },
5564 { .id = 0x838476a1, .name = "STAC9205D", .patch = patch_stac9205 },
5565 { .id = 0x838476a2, .name = "STAC9204", .patch = patch_stac9205 },
5566 { .id = 0x838476a3, .name = "STAC9204D", .patch = patch_stac9205 },
5567 { .id = 0x838476a4, .name = "STAC9255", .patch = patch_stac9205 },
5568 { .id = 0x838476a5, .name = "STAC9255D", .patch = patch_stac9205 },
5569 { .id = 0x838476a6, .name = "STAC9254", .patch = patch_stac9205 },
5570 { .id = 0x838476a7, .name = "STAC9254D", .patch = patch_stac9205 },
aafc4412 5571 { .id = 0x111d7603, .name = "92HD75B3X5", .patch = patch_stac92hd71bxx},
d0513fc6
MR
5572 { .id = 0x111d7604, .name = "92HD83C1X5", .patch = patch_stac92hd83xxx},
5573 { .id = 0x111d7605, .name = "92HD81B1X5", .patch = patch_stac92hd83xxx},
aafc4412 5574 { .id = 0x111d7608, .name = "92HD75B2X5", .patch = patch_stac92hd71bxx},
541eee87
MR
5575 { .id = 0x111d7674, .name = "92HD73D1X5", .patch = patch_stac92hd73xx },
5576 { .id = 0x111d7675, .name = "92HD73C1X5", .patch = patch_stac92hd73xx },
e1f0d669 5577 { .id = 0x111d7676, .name = "92HD73E1X5", .patch = patch_stac92hd73xx },
541eee87
MR
5578 { .id = 0x111d76b0, .name = "92HD71B8X", .patch = patch_stac92hd71bxx },
5579 { .id = 0x111d76b1, .name = "92HD71B8X", .patch = patch_stac92hd71bxx },
5580 { .id = 0x111d76b2, .name = "92HD71B7X", .patch = patch_stac92hd71bxx },
5581 { .id = 0x111d76b3, .name = "92HD71B7X", .patch = patch_stac92hd71bxx },
5582 { .id = 0x111d76b4, .name = "92HD71B6X", .patch = patch_stac92hd71bxx },
5583 { .id = 0x111d76b5, .name = "92HD71B6X", .patch = patch_stac92hd71bxx },
5584 { .id = 0x111d76b6, .name = "92HD71B5X", .patch = patch_stac92hd71bxx },
5585 { .id = 0x111d76b7, .name = "92HD71B5X", .patch = patch_stac92hd71bxx },
2f2f4251
M
5586 {} /* terminator */
5587};
1289e9e8
TI
5588
5589MODULE_ALIAS("snd-hda-codec-id:8384*");
5590MODULE_ALIAS("snd-hda-codec-id:111d*");
5591
5592MODULE_LICENSE("GPL");
5593MODULE_DESCRIPTION("IDT/Sigmatel HD-audio codec");
5594
5595static struct hda_codec_preset_list sigmatel_list = {
5596 .preset = snd_hda_preset_sigmatel,
5597 .owner = THIS_MODULE,
5598};
5599
5600static int __init patch_sigmatel_init(void)
5601{
5602 return snd_hda_add_codec_preset(&sigmatel_list);
5603}
5604
5605static void __exit patch_sigmatel_exit(void)
5606{
5607 snd_hda_delete_codec_preset(&sigmatel_list);
5608}
5609
5610module_init(patch_sigmatel_init)
5611module_exit(patch_sigmatel_exit)