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