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