ALSA: hda - Make the ALC269 pin quirk table shorter
[linux-2.6-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>
45a6ac16 34#include <sound/jack.h>
a74ccea5 35#include <sound/tlv.h>
2f2f4251
M
36#include "hda_codec.h"
37#include "hda_local.h"
128bc4ba 38#include "hda_auto_parser.h"
1cd2224c 39#include "hda_beep.h"
1835a0f9 40#include "hda_jack.h"
36c9db7a 41#include "hda_generic.h"
2f2f4251 42
c6e4c666 43enum {
36c9db7a 44 STAC_VREF_EVENT = 8,
c6e4c666 45 STAC_PWR_EVENT,
c6e4c666 46};
4e55096e 47
f5fcc13c
TI
48enum {
49 STAC_REF,
bf277785 50 STAC_9200_OQO,
dfe495d0
TI
51 STAC_9200_DELL_D21,
52 STAC_9200_DELL_D22,
53 STAC_9200_DELL_D23,
54 STAC_9200_DELL_M21,
55 STAC_9200_DELL_M22,
56 STAC_9200_DELL_M23,
57 STAC_9200_DELL_M24,
58 STAC_9200_DELL_M25,
59 STAC_9200_DELL_M26,
60 STAC_9200_DELL_M27,
58eec423
MCC
61 STAC_9200_M4,
62 STAC_9200_M4_2,
117f257d 63 STAC_9200_PANASONIC,
d39a3ae8 64 STAC_9200_EAPD_INIT,
f5fcc13c
TI
65 STAC_9200_MODELS
66};
67
68enum {
69 STAC_9205_REF,
dfe495d0 70 STAC_9205_DELL_M42,
ae0a8ed8
TD
71 STAC_9205_DELL_M43,
72 STAC_9205_DELL_M44,
d9a4268e 73 STAC_9205_EAPD,
f5fcc13c
TI
74 STAC_9205_MODELS
75};
76
e1f0d669 77enum {
9e43f0de 78 STAC_92HD73XX_NO_JD, /* no jack-detection */
e1f0d669 79 STAC_92HD73XX_REF,
ae709440 80 STAC_92HD73XX_INTEL,
661cd8fb
TI
81 STAC_DELL_M6_AMIC,
82 STAC_DELL_M6_DMIC,
83 STAC_DELL_M6_BOTH,
6b3ab21e 84 STAC_DELL_EQ,
842ae638 85 STAC_ALIENWARE_M17X,
1de7ca5e 86 STAC_92HD89XX_HP_FRONT_JACK,
7440850c 87 STAC_92HD89XX_HP_Z1_G2_RIGHT_MIC_JACK,
e1f0d669
MR
88 STAC_92HD73XX_MODELS
89};
90
d0513fc6
MR
91enum {
92 STAC_92HD83XXX_REF,
32ed3f46 93 STAC_92HD83XXX_PWR_REF,
8bb0ac55 94 STAC_DELL_S14,
f7f9bdfa 95 STAC_DELL_VOSTRO_3500,
0c27c180 96 STAC_92HD83XXX_HP_cNB11_INTQUAD,
48315590 97 STAC_HP_DV7_4000,
5556e147 98 STAC_HP_ZEPHYR,
a3e19973 99 STAC_92HD83XXX_HP_LED,
ff8a1e27 100 STAC_92HD83XXX_HP_INV_LED,
62cbde18 101 STAC_92HD83XXX_HP_MIC_LED,
37c367ec 102 STAC_HP_LED_GPIO10,
8d032a8f 103 STAC_92HD83XXX_HEADSET_JACK,
372f8c75 104 STAC_92HD83XXX_HP,
49920427 105 STAC_HP_ENVY_BASS,
d009f3de 106 STAC_HP_BNB13_EQ,
8695a003 107 STAC_HP_ENVY_TS_BASS,
d0513fc6
MR
108 STAC_92HD83XXX_MODELS
109};
110
e035b841
MR
111enum {
112 STAC_92HD71BXX_REF,
a7662640
MR
113 STAC_DELL_M4_1,
114 STAC_DELL_M4_2,
3a7abfd2 115 STAC_DELL_M4_3,
6a14f585 116 STAC_HP_M4,
2a6ce6e5 117 STAC_HP_DV4,
1b0652eb 118 STAC_HP_DV5,
ae6241fb 119 STAC_HP_HDX,
0f6fcb73
TI
120 STAC_92HD71BXX_HP,
121 STAC_92HD71BXX_NO_DMIC,
122 STAC_92HD71BXX_NO_SMUX,
e035b841
MR
123 STAC_92HD71BXX_MODELS
124};
125
8b3dfdaf
TI
126enum {
127 STAC_92HD95_HP_LED,
128 STAC_92HD95_HP_BASS,
129 STAC_92HD95_MODELS
130};
131
8e21c34c
TD
132enum {
133 STAC_925x_REF,
9cb36c2a
MCC
134 STAC_M1,
135 STAC_M1_2,
136 STAC_M2,
8e21c34c 137 STAC_M2_2,
9cb36c2a
MCC
138 STAC_M3,
139 STAC_M5,
140 STAC_M6,
8e21c34c
TD
141 STAC_925x_MODELS
142};
143
f5fcc13c
TI
144enum {
145 STAC_D945_REF,
146 STAC_D945GTP3,
147 STAC_D945GTP5,
5d5d3bc3
IZ
148 STAC_INTEL_MAC_V1,
149 STAC_INTEL_MAC_V2,
150 STAC_INTEL_MAC_V3,
151 STAC_INTEL_MAC_V4,
152 STAC_INTEL_MAC_V5,
0a427846 153 STAC_INTEL_MAC_AUTO,
8c650087 154 STAC_ECS_202,
dfe495d0
TI
155 STAC_922X_DELL_D81,
156 STAC_922X_DELL_D82,
157 STAC_922X_DELL_M81,
158 STAC_922X_DELL_M82,
0a427846 159 STAC_922X_INTEL_MAC_GPIO,
f5fcc13c
TI
160 STAC_922X_MODELS
161};
162
163enum {
e28d8322 164 STAC_D965_REF_NO_JD, /* no jack-detection */
f5fcc13c
TI
165 STAC_D965_REF,
166 STAC_D965_3ST,
167 STAC_D965_5ST,
679d92ed 168 STAC_D965_5ST_NO_FP,
29ac8363 169 STAC_D965_VERBS,
4ff076e5 170 STAC_DELL_3ST,
8e9068b1 171 STAC_DELL_BIOS,
eefb8be4 172 STAC_DELL_BIOS_AMIC,
29ac8363
TI
173 STAC_DELL_BIOS_SPDIF,
174 STAC_927X_DELL_DMIC,
54930531 175 STAC_927X_VOLKNOB,
f5fcc13c
TI
176 STAC_927X_MODELS
177};
403d1944 178
307282c8 179enum {
307282c8
TI
180 STAC_9872_VAIO,
181 STAC_9872_MODELS
182};
183
2f2f4251 184struct sigmatel_spec {
36c9db7a 185 struct hda_gen_spec gen;
c7d4b2fa 186
c0cea0d0 187 unsigned int eapd_switch: 1;
1b0e372d 188 unsigned int linear_tone_beep:1;
8d032a8f 189 unsigned int headset_jack:1; /* 4-pin headset jack (hp + mono mic) */
29ac8363 190 unsigned int volknob_init:1; /* special volume-knob initialization */
36c9db7a 191 unsigned int powerdown_adcs:1;
42875479 192 unsigned int have_spdif_mux:1;
c7d4b2fa 193
4fe5195c 194 /* gpio lines */
0fc9dec4 195 unsigned int eapd_mask;
4fe5195c
MR
196 unsigned int gpio_mask;
197 unsigned int gpio_dir;
198 unsigned int gpio_data;
199 unsigned int gpio_mute;
86d190e7 200 unsigned int gpio_led;
c357aab0 201 unsigned int gpio_led_polarity;
f1a73746 202 unsigned int vref_mute_led_nid; /* pin NID for mute-LED vref control */
45eebda7 203 unsigned int vref_led;
372f8c75 204 int default_polarity;
4fe5195c 205
62cbde18 206 unsigned int mic_mute_led_gpio; /* capture mute LED GPIO */
7fe30711 207 unsigned int mic_enabled; /* current mic mute state (bitmask) */
62cbde18 208
8daaaa97
MR
209 /* stream */
210 unsigned int stream_delay;
211
4fe5195c 212 /* analog loopback */
2b63536f 213 const struct snd_kcontrol_new *aloopback_ctl;
36c9db7a 214 unsigned int aloopback;
e1f0d669
MR
215 unsigned char aloopback_mask;
216 unsigned char aloopback_shift;
8259980e 217
a64135a2 218 /* power management */
c882246d 219 unsigned int power_map_bits;
a64135a2 220 unsigned int num_pwrs;
2b63536f 221 const hda_nid_t *pwr_nids;
36c9db7a
TI
222 unsigned int active_adcs;
223
224 /* beep widgets */
1cd2224c 225 hda_nid_t anabeep_nid;
42875479
TI
226
227 /* SPDIF-out mux */
228 const char * const *spdif_labels;
229 struct hda_input_mux spdif_mux;
230 unsigned int cur_smux[2];
2f2f4251
M
231};
232
c882246d
TI
233#define AC_VERB_IDT_SET_POWER_MAP 0x7ec
234#define AC_VERB_IDT_GET_POWER_MAP 0xfec
235
2b63536f 236static const hda_nid_t stac92hd73xx_pwr_nids[8] = {
a64135a2
MR
237 0x0a, 0x0b, 0x0c, 0xd, 0x0e,
238 0x0f, 0x10, 0x11
239};
240
afef2cfa
CC
241static const hda_nid_t stac92hd83xxx_pwr_nids[7] = {
242 0x0a, 0x0b, 0x0c, 0xd, 0x0e,
243 0x0f, 0x10
d0513fc6
MR
244};
245
2b63536f 246static const hda_nid_t stac92hd71bxx_pwr_nids[3] = {
a64135a2
MR
247 0x0a, 0x0d, 0x0f
248};
249
f3302a59 250
36c9db7a
TI
251/*
252 * PCM hooks
253 */
254static void stac_playback_pcm_hook(struct hda_pcm_stream *hinfo,
255 struct hda_codec *codec,
256 struct snd_pcm_substream *substream,
257 int action)
8b65727b 258{
8b65727b 259 struct sigmatel_spec *spec = codec->spec;
36c9db7a
TI
260 if (action == HDA_GEN_PCM_ACT_OPEN && spec->stream_delay)
261 msleep(spec->stream_delay);
8b65727b
MP
262}
263
36c9db7a
TI
264static void stac_capture_pcm_hook(struct hda_pcm_stream *hinfo,
265 struct hda_codec *codec,
266 struct snd_pcm_substream *substream,
267 int action)
8b65727b 268{
8b65727b 269 struct sigmatel_spec *spec = codec->spec;
36c9db7a 270 int i, idx = 0;
8b65727b 271
36c9db7a
TI
272 if (!spec->powerdown_adcs)
273 return;
8b65727b 274
36c9db7a
TI
275 for (i = 0; i < spec->gen.num_all_adcs; i++) {
276 if (spec->gen.all_adcs[i] == hinfo->nid) {
277 idx = i;
278 break;
279 }
280 }
8b65727b 281
36c9db7a
TI
282 switch (action) {
283 case HDA_GEN_PCM_ACT_OPEN:
284 msleep(40);
285 snd_hda_codec_write(codec, hinfo->nid, 0,
286 AC_VERB_SET_POWER_STATE, AC_PWRST_D0);
287 spec->active_adcs |= (1 << idx);
288 break;
289 case HDA_GEN_PCM_ACT_CLOSE:
290 snd_hda_codec_write(codec, hinfo->nid, 0,
291 AC_VERB_SET_POWER_STATE, AC_PWRST_D3);
292 spec->active_adcs &= ~(1 << idx);
293 break;
294 }
8b65727b
MP
295}
296
36c9db7a
TI
297/*
298 * Early 2006 Intel Macintoshes with STAC9220X5 codecs seem to have a
299 * funky external mute control using GPIO pins.
300 */
d9737751 301
36c9db7a
TI
302static void stac_gpio_set(struct hda_codec *codec, unsigned int mask,
303 unsigned int dir_mask, unsigned int data)
d9737751 304{
36c9db7a 305 unsigned int gpiostate, gpiomask, gpiodir;
d9737751 306
4e76a883 307 codec_dbg(codec, "%s msk %x dir %x gpio %x\n", __func__, mask, dir_mask, data);
36c9db7a
TI
308
309 gpiostate = snd_hda_codec_read(codec, codec->afg, 0,
310 AC_VERB_GET_GPIO_DATA, 0);
311 gpiostate = (gpiostate & ~dir_mask) | (data & dir_mask);
312
313 gpiomask = snd_hda_codec_read(codec, codec->afg, 0,
314 AC_VERB_GET_GPIO_MASK, 0);
315 gpiomask |= mask;
316
317 gpiodir = snd_hda_codec_read(codec, codec->afg, 0,
318 AC_VERB_GET_GPIO_DIRECTION, 0);
319 gpiodir |= dir_mask;
320
321 /* Configure GPIOx as CMOS */
322 snd_hda_codec_write(codec, codec->afg, 0, 0x7e7, 0);
323
324 snd_hda_codec_write(codec, codec->afg, 0,
325 AC_VERB_SET_GPIO_MASK, gpiomask);
326 snd_hda_codec_read(codec, codec->afg, 0,
327 AC_VERB_SET_GPIO_DIRECTION, gpiodir); /* sync */
328
329 msleep(1);
330
331 snd_hda_codec_read(codec, codec->afg, 0,
332 AC_VERB_SET_GPIO_DATA, gpiostate); /* sync */
d9737751
MR
333}
334
36c9db7a 335/* hook for controlling mic-mute LED GPIO */
a90229e0 336static void stac_capture_led_hook(struct hda_codec *codec,
7fe30711
TI
337 struct snd_kcontrol *kcontrol,
338 struct snd_ctl_elem_value *ucontrol)
d9737751 339{
d9737751 340 struct sigmatel_spec *spec = codec->spec;
7fe30711
TI
341 unsigned int mask;
342 bool cur_mute, prev_mute;
00ef50c2 343
7fe30711 344 if (!kcontrol || !ucontrol)
a90229e0
TI
345 return;
346
7fe30711
TI
347 mask = 1U << snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
348 prev_mute = !spec->mic_enabled;
349 if (ucontrol->value.integer.value[0] ||
350 ucontrol->value.integer.value[1])
351 spec->mic_enabled |= mask;
352 else
353 spec->mic_enabled &= ~mask;
354 cur_mute = !spec->mic_enabled;
355 if (cur_mute != prev_mute) {
356 if (cur_mute)
36c9db7a 357 spec->gpio_data |= spec->mic_mute_led_gpio;
00ef50c2 358 else
36c9db7a
TI
359 spec->gpio_data &= ~spec->mic_mute_led_gpio;
360 stac_gpio_set(codec, spec->gpio_mask,
361 spec->gpio_dir, spec->gpio_data);
00ef50c2 362 }
d9737751
MR
363}
364
45eebda7
VK
365static int stac_vrefout_set(struct hda_codec *codec,
366 hda_nid_t nid, unsigned int new_vref)
367{
368 int error, pinctl;
369
4e76a883 370 codec_dbg(codec, "%s, nid %x ctl %x\n", __func__, nid, new_vref);
45eebda7
VK
371 pinctl = snd_hda_codec_read(codec, nid, 0,
372 AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
373
374 if (pinctl < 0)
375 return pinctl;
376
377 pinctl &= 0xff;
378 pinctl &= ~AC_PINCTL_VREFEN;
379 pinctl |= (new_vref & AC_PINCTL_VREFEN);
380
cdd03ced 381 error = snd_hda_set_pin_ctl_cache(codec, nid, pinctl);
45eebda7
VK
382 if (error < 0)
383 return error;
384
385 return 1;
386}
387
dfc6e469
TI
388/* prevent codec AFG to D3 state when vref-out pin is used for mute LED */
389/* this hook is set in stac_setup_gpio() */
390static unsigned int stac_vref_led_power_filter(struct hda_codec *codec,
391 hda_nid_t nid,
392 unsigned int power_state)
393{
394 if (nid == codec->afg && power_state == AC_PWRST_D3)
395 return AC_PWRST_D1;
396 return snd_hda_gen_path_power_filter(codec, nid, power_state);
397}
398
36c9db7a
TI
399/* update mute-LED accoring to the master switch */
400static void stac_update_led_status(struct hda_codec *codec, int enabled)
2f2f4251 401{
2f2f4251 402 struct sigmatel_spec *spec = codec->spec;
36c9db7a 403 int muted = !enabled;
2f2f4251 404
36c9db7a
TI
405 if (!spec->gpio_led)
406 return;
2f2f4251 407
36c9db7a
TI
408 /* LED state is inverted on these systems */
409 if (spec->gpio_led_polarity)
410 muted = !muted;
2f2f4251 411
36c9db7a
TI
412 if (!spec->vref_mute_led_nid) {
413 if (muted)
414 spec->gpio_data |= spec->gpio_led;
415 else
416 spec->gpio_data &= ~spec->gpio_led;
417 stac_gpio_set(codec, spec->gpio_mask,
418 spec->gpio_dir, spec->gpio_data);
5207e10e 419 } else {
36c9db7a
TI
420 spec->vref_led = muted ? AC_PINCTL_VREF_50 : AC_PINCTL_VREF_GRD;
421 stac_vrefout_set(codec, spec->vref_mute_led_nid,
422 spec->vref_led);
5207e10e 423 }
2f2f4251
M
424}
425
36c9db7a
TI
426/* vmaster hook to update mute LED */
427static void stac_vmaster_hook(void *private_data, int val)
b22b4821 428{
36c9db7a 429 stac_update_led_status(private_data, val);
b22b4821
MR
430}
431
36c9db7a
TI
432/* automute hook to handle GPIO mute and EAPD updates */
433static void stac_update_outputs(struct hda_codec *codec)
b22b4821 434{
b22b4821
MR
435 struct sigmatel_spec *spec = codec->spec;
436
36c9db7a
TI
437 if (spec->gpio_mute)
438 spec->gen.master_mute =
439 !(snd_hda_codec_read(codec, codec->afg, 0,
440 AC_VERB_GET_GPIO_DATA, 0) & spec->gpio_mute);
b22b4821 441
36c9db7a 442 snd_hda_gen_update_outputs(codec);
b22b4821 443
36c9db7a
TI
444 if (spec->eapd_mask && spec->eapd_switch) {
445 unsigned int val = spec->gpio_data;
446 if (spec->gen.speaker_muted)
447 val &= ~spec->eapd_mask;
448 else
449 val |= spec->eapd_mask;
1ea9a69d
TI
450 if (spec->gpio_data != val) {
451 spec->gpio_data = val;
36c9db7a
TI
452 stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir,
453 val);
1ea9a69d 454 }
36c9db7a 455 }
b22b4821
MR
456}
457
36c9db7a
TI
458static void stac_toggle_power_map(struct hda_codec *codec, hda_nid_t nid,
459 bool enable, bool do_write)
5f10c4a9 460{
5f10c4a9 461 struct sigmatel_spec *spec = codec->spec;
36c9db7a 462 unsigned int idx, val;
5f10c4a9 463
36c9db7a
TI
464 for (idx = 0; idx < spec->num_pwrs; idx++) {
465 if (spec->pwr_nids[idx] == nid)
466 break;
467 }
468 if (idx >= spec->num_pwrs)
469 return;
470
471 idx = 1 << idx;
472
473 val = spec->power_map_bits;
474 if (enable)
475 val &= ~idx;
476 else
477 val |= idx;
478
479 /* power down unused output ports */
480 if (val != spec->power_map_bits) {
481 spec->power_map_bits = val;
482 if (do_write)
483 snd_hda_codec_write(codec, codec->afg, 0,
484 AC_VERB_IDT_SET_POWER_MAP, val);
485 }
486}
487
488/* update power bit per jack plug/unplug */
489static void jack_update_power(struct hda_codec *codec,
490 struct hda_jack_tbl *jack)
491{
492 struct sigmatel_spec *spec = codec->spec;
493 int i;
494
495 if (!spec->num_pwrs)
496 return;
497
498 if (jack && jack->nid) {
499 stac_toggle_power_map(codec, jack->nid,
500 snd_hda_jack_detect(codec, jack->nid),
501 true);
502 return;
503 }
504
505 /* update all jacks */
506 for (i = 0; i < spec->num_pwrs; i++) {
507 hda_nid_t nid = spec->pwr_nids[i];
508 jack = snd_hda_jack_tbl_get(codec, nid);
509 if (!jack || !jack->action)
510 continue;
511 if (jack->action == STAC_PWR_EVENT ||
512 jack->action <= HDA_GEN_LAST_EVENT)
513 stac_toggle_power_map(codec, nid,
514 snd_hda_jack_detect(codec, nid),
515 false);
516 }
517
518 snd_hda_codec_write(codec, codec->afg, 0, AC_VERB_IDT_SET_POWER_MAP,
519 spec->power_map_bits);
520}
521
522static void stac_hp_automute(struct hda_codec *codec,
523 struct hda_jack_tbl *jack)
524{
525 snd_hda_gen_hp_automute(codec, jack);
526 jack_update_power(codec, jack);
527}
528
529static void stac_line_automute(struct hda_codec *codec,
530 struct hda_jack_tbl *jack)
531{
532 snd_hda_gen_line_automute(codec, jack);
533 jack_update_power(codec, jack);
534}
535
664389db
DH
536static void stac_mic_autoswitch(struct hda_codec *codec,
537 struct hda_jack_tbl *jack)
538{
539 snd_hda_gen_mic_autoswitch(codec, jack);
540 jack_update_power(codec, jack);
541}
542
36c9db7a
TI
543static void stac_vref_event(struct hda_codec *codec, struct hda_jack_tbl *event)
544{
545 unsigned int data;
546
547 data = snd_hda_codec_read(codec, codec->afg, 0,
548 AC_VERB_GET_GPIO_DATA, 0);
549 /* toggle VREF state based on GPIOx status */
550 snd_hda_codec_write(codec, codec->afg, 0, 0x7e0,
551 !!(data & (1 << event->private_data)));
552}
553
554/* initialize the power map and enable the power event to jacks that
555 * haven't been assigned to automute
556 */
557static void stac_init_power_map(struct hda_codec *codec)
558{
559 struct sigmatel_spec *spec = codec->spec;
560 int i;
561
562 for (i = 0; i < spec->num_pwrs; i++) {
563 hda_nid_t nid = spec->pwr_nids[i];
564 unsigned int def_conf = snd_hda_codec_get_pincfg(codec, nid);
565 def_conf = get_defcfg_connect(def_conf);
566 if (snd_hda_jack_tbl_get(codec, nid))
567 continue;
568 if (def_conf == AC_JACK_PORT_COMPLEX &&
569 !(spec->vref_mute_led_nid == nid ||
570 is_jack_detectable(codec, nid))) {
571 snd_hda_jack_detect_enable_callback(codec, nid,
572 STAC_PWR_EVENT,
573 jack_update_power);
574 } else {
575 if (def_conf == AC_JACK_PORT_NONE)
576 stac_toggle_power_map(codec, nid, false, false);
577 else
578 stac_toggle_power_map(codec, nid, true, false);
579 }
580 }
581}
582
583/*
584 */
585
586static inline bool get_int_hint(struct hda_codec *codec, const char *key,
587 int *valp)
588{
589 return !snd_hda_get_int_hint(codec, key, valp);
590}
591
592/* override some hints from the hwdep entry */
593static void stac_store_hints(struct hda_codec *codec)
594{
595 struct sigmatel_spec *spec = codec->spec;
596 int val;
597
598 if (get_int_hint(codec, "gpio_mask", &spec->gpio_mask)) {
599 spec->eapd_mask = spec->gpio_dir = spec->gpio_data =
600 spec->gpio_mask;
601 }
602 if (get_int_hint(codec, "gpio_dir", &spec->gpio_dir))
603 spec->gpio_mask &= spec->gpio_mask;
604 if (get_int_hint(codec, "gpio_data", &spec->gpio_data))
605 spec->gpio_dir &= spec->gpio_mask;
606 if (get_int_hint(codec, "eapd_mask", &spec->eapd_mask))
607 spec->eapd_mask &= spec->gpio_mask;
608 if (get_int_hint(codec, "gpio_mute", &spec->gpio_mute))
609 spec->gpio_mute &= spec->gpio_mask;
610 val = snd_hda_get_bool_hint(codec, "eapd_switch");
611 if (val >= 0)
612 spec->eapd_switch = val;
613}
614
615/*
616 * loopback controls
617 */
618
619#define stac_aloopback_info snd_ctl_boolean_mono_info
620
621static int stac_aloopback_get(struct snd_kcontrol *kcontrol,
622 struct snd_ctl_elem_value *ucontrol)
623{
624 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
625 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
626 struct sigmatel_spec *spec = codec->spec;
627
628 ucontrol->value.integer.value[0] = !!(spec->aloopback &
629 (spec->aloopback_mask << idx));
630 return 0;
5f10c4a9
ML
631}
632
36c9db7a
TI
633static int stac_aloopback_put(struct snd_kcontrol *kcontrol,
634 struct snd_ctl_elem_value *ucontrol)
5f10c4a9
ML
635{
636 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
637 struct sigmatel_spec *spec = codec->spec;
e1f0d669 638 unsigned int idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
5f10c4a9 639 unsigned int dac_mode;
e1f0d669 640 unsigned int val, idx_val;
5f10c4a9 641
e1f0d669
MR
642 idx_val = spec->aloopback_mask << idx;
643 if (ucontrol->value.integer.value[0])
644 val = spec->aloopback | idx_val;
645 else
646 val = spec->aloopback & ~idx_val;
68ea7b2f 647 if (spec->aloopback == val)
5f10c4a9
ML
648 return 0;
649
68ea7b2f 650 spec->aloopback = val;
5f10c4a9 651
e1f0d669
MR
652 /* Only return the bits defined by the shift value of the
653 * first two bytes of the mask
654 */
5f10c4a9 655 dac_mode = snd_hda_codec_read(codec, codec->afg, 0,
e1f0d669
MR
656 kcontrol->private_value & 0xFFFF, 0x0);
657 dac_mode >>= spec->aloopback_shift;
5f10c4a9 658
e1f0d669 659 if (spec->aloopback & idx_val) {
5f10c4a9 660 snd_hda_power_up(codec);
e1f0d669 661 dac_mode |= idx_val;
5f10c4a9
ML
662 } else {
663 snd_hda_power_down(codec);
e1f0d669 664 dac_mode &= ~idx_val;
5f10c4a9
ML
665 }
666
667 snd_hda_codec_write_cache(codec, codec->afg, 0,
668 kcontrol->private_value >> 16, dac_mode);
669
670 return 1;
671}
672
e1f0d669 673#define STAC_ANALOG_LOOPBACK(verb_read, verb_write, cnt) \
5f10c4a9
ML
674 { \
675 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
676 .name = "Analog Loopback", \
e1f0d669 677 .count = cnt, \
36c9db7a
TI
678 .info = stac_aloopback_info, \
679 .get = stac_aloopback_get, \
680 .put = stac_aloopback_put, \
5f10c4a9
ML
681 .private_value = verb_read | (verb_write << 16), \
682 }
683
36c9db7a
TI
684/*
685 * Mute LED handling on HP laptops
686 */
2fc99890 687
36c9db7a
TI
688/* check whether it's a HP laptop with a docking port */
689static bool hp_bnb2011_with_dock(struct hda_codec *codec)
690{
691 if (codec->vendor_id != 0x111d7605 &&
692 codec->vendor_id != 0x111d76d1)
693 return false;
2f2f4251 694
36c9db7a
TI
695 switch (codec->subsystem_id) {
696 case 0x103c1618:
697 case 0x103c1619:
698 case 0x103c161a:
699 case 0x103c161b:
700 case 0x103c161c:
701 case 0x103c161d:
702 case 0x103c161e:
703 case 0x103c161f:
d78d7a90 704
36c9db7a
TI
705 case 0x103c162a:
706 case 0x103c162b:
e1f0d669 707
36c9db7a
TI
708 case 0x103c1630:
709 case 0x103c1631:
d78d7a90 710
36c9db7a
TI
711 case 0x103c1633:
712 case 0x103c1634:
713 case 0x103c1635:
d0513fc6 714
36c9db7a
TI
715 case 0x103c3587:
716 case 0x103c3588:
717 case 0x103c3589:
718 case 0x103c358a:
541eee87 719
36c9db7a
TI
720 case 0x103c3667:
721 case 0x103c3668:
722 case 0x103c3669:
2f2f4251 723
36c9db7a
TI
724 return true;
725 }
726 return false;
727}
1697055e 728
36c9db7a
TI
729static bool hp_blike_system(u32 subsystem_id)
730{
731 switch (subsystem_id) {
732 case 0x103c1520:
733 case 0x103c1521:
734 case 0x103c1523:
735 case 0x103c1524:
736 case 0x103c1525:
737 case 0x103c1722:
738 case 0x103c1723:
739 case 0x103c1724:
740 case 0x103c1725:
741 case 0x103c1726:
742 case 0x103c1727:
743 case 0x103c1728:
744 case 0x103c1729:
745 case 0x103c172a:
746 case 0x103c172b:
747 case 0x103c307e:
748 case 0x103c307f:
749 case 0x103c3080:
750 case 0x103c3081:
751 case 0x103c7007:
752 case 0x103c7008:
753 return true;
754 }
755 return false;
756}
d9737751 757
36c9db7a
TI
758static void set_hp_led_gpio(struct hda_codec *codec)
759{
760 struct sigmatel_spec *spec = codec->spec;
761 unsigned int gpio;
2134ea4f 762
36c9db7a
TI
763 if (spec->gpio_led)
764 return;
2faa3bf1 765
36c9db7a
TI
766 gpio = snd_hda_param_read(codec, codec->afg, AC_PAR_GPIO_CAP);
767 gpio &= AC_GPIO_IO_COUNT;
768 if (gpio > 3)
769 spec->gpio_led = 0x08; /* GPIO 3 */
770 else
771 spec->gpio_led = 0x01; /* GPIO 0 */
2faa3bf1
TI
772}
773
36c9db7a
TI
774/*
775 * This method searches for the mute LED GPIO configuration
776 * provided as OEM string in SMBIOS. The format of that string
777 * is HP_Mute_LED_P_G or HP_Mute_LED_P
778 * where P can be 0 or 1 and defines mute LED GPIO control state (low/high)
779 * that corresponds to the NOT muted state of the master volume
780 * and G is the index of the GPIO to use as the mute LED control (0..9)
781 * If _G portion is missing it is assigned based on the codec ID
782 *
783 * So, HP B-series like systems may have HP_Mute_LED_0 (current models)
784 * or HP_Mute_LED_0_3 (future models) OEM SMBIOS strings
785 *
786 *
787 * The dv-series laptops don't seem to have the HP_Mute_LED* strings in
788 * SMBIOS - at least the ones I have seen do not have them - which include
789 * my own system (HP Pavilion dv6-1110ax) and my cousin's
790 * HP Pavilion dv9500t CTO.
791 * Need more information on whether it is true across the entire series.
792 * -- kunal
793 */
794static int find_mute_led_cfg(struct hda_codec *codec, int default_polarity)
2f2f4251
M
795{
796 struct sigmatel_spec *spec = codec->spec;
36c9db7a 797 const struct dmi_device *dev = NULL;
2f2f4251 798
36c9db7a
TI
799 if (get_int_hint(codec, "gpio_led", &spec->gpio_led)) {
800 get_int_hint(codec, "gpio_led_polarity",
801 &spec->gpio_led_polarity);
802 return 1;
6479c631 803 }
c7d4b2fa 804
36c9db7a 805 while ((dev = dmi_find_device(DMI_DEV_TYPE_OEM_STRING, NULL, dev))) {
e7fc4960 806 if (sscanf(dev->name, "HP_Mute_LED_%u_%x",
36c9db7a
TI
807 &spec->gpio_led_polarity,
808 &spec->gpio_led) == 2) {
809 unsigned int max_gpio;
810 max_gpio = snd_hda_param_read(codec, codec->afg,
811 AC_PAR_GPIO_CAP);
812 max_gpio &= AC_GPIO_IO_COUNT;
813 if (spec->gpio_led < max_gpio)
814 spec->gpio_led = 1 << spec->gpio_led;
815 else
816 spec->vref_mute_led_nid = spec->gpio_led;
817 return 1;
818 }
e7fc4960 819 if (sscanf(dev->name, "HP_Mute_LED_%u",
36c9db7a
TI
820 &spec->gpio_led_polarity) == 1) {
821 set_hp_led_gpio(codec);
822 return 1;
823 }
824 /* BIOS bug: unfilled OEM string */
825 if (strstr(dev->name, "HP_Mute_LED_P_G")) {
826 set_hp_led_gpio(codec);
827 if (default_polarity >= 0)
828 spec->gpio_led_polarity = default_polarity;
829 else
830 spec->gpio_led_polarity = 1;
831 return 1;
00ef50c2 832 }
d9737751 833 }
c7d4b2fa 834
36c9db7a
TI
835 /*
836 * Fallback case - if we don't find the DMI strings,
837 * we statically set the GPIO - if not a B-series system
838 * and default polarity is provided
839 */
840 if (!hp_blike_system(codec->subsystem_id) &&
841 (default_polarity == 0 || default_polarity == 1)) {
842 set_hp_led_gpio(codec);
843 spec->gpio_led_polarity = default_polarity;
844 return 1;
dabbed6f 845 }
36c9db7a
TI
846 return 0;
847}
2134ea4f 848
303985f8
DH
849/* check whether a built-in speaker is included in parsed pins */
850static bool has_builtin_speaker(struct hda_codec *codec)
851{
852 struct sigmatel_spec *spec = codec->spec;
853 hda_nid_t *nid_pin;
854 int nids, i;
855
856 if (spec->gen.autocfg.line_out_type == AUTO_PIN_SPEAKER_OUT) {
857 nid_pin = spec->gen.autocfg.line_out_pins;
858 nids = spec->gen.autocfg.line_outs;
859 } else {
860 nid_pin = spec->gen.autocfg.speaker_pins;
861 nids = spec->gen.autocfg.speaker_outs;
862 }
863
864 for (i = 0; i < nids; i++) {
865 unsigned int def_conf = snd_hda_codec_get_pincfg(codec, nid_pin[i]);
866 if (snd_hda_get_input_pin_attr(def_conf) == INPUT_PIN_ATTR_INT)
867 return true;
868 }
869 return false;
870}
871
36c9db7a
TI
872/*
873 * PC beep controls
874 */
2faa3bf1 875
36c9db7a
TI
876/* create PC beep volume controls */
877static int stac_auto_create_beep_ctls(struct hda_codec *codec,
878 hda_nid_t nid)
879{
880 struct sigmatel_spec *spec = codec->spec;
881 u32 caps = query_amp_caps(codec, nid, HDA_OUTPUT);
882 struct snd_kcontrol_new *knew;
883 static struct snd_kcontrol_new abeep_mute_ctl =
884 HDA_CODEC_MUTE(NULL, 0, 0, 0);
885 static struct snd_kcontrol_new dbeep_mute_ctl =
886 HDA_CODEC_MUTE_BEEP(NULL, 0, 0, 0);
887 static struct snd_kcontrol_new beep_vol_ctl =
888 HDA_CODEC_VOLUME(NULL, 0, 0, 0);
2faa3bf1 889
36c9db7a
TI
890 /* check for mute support for the the amp */
891 if ((caps & AC_AMPCAP_MUTE) >> AC_AMPCAP_MUTE_SHIFT) {
892 const struct snd_kcontrol_new *temp;
893 if (spec->anabeep_nid == nid)
894 temp = &abeep_mute_ctl;
895 else
896 temp = &dbeep_mute_ctl;
897 knew = snd_hda_gen_add_kctl(&spec->gen,
898 "Beep Playback Switch", temp);
899 if (!knew)
900 return -ENOMEM;
901 knew->private_value =
902 HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT);
2134ea4f
TI
903 }
904
36c9db7a
TI
905 /* check to see if there is volume support for the amp */
906 if ((caps & AC_AMPCAP_NUM_STEPS) >> AC_AMPCAP_NUM_STEPS_SHIFT) {
907 knew = snd_hda_gen_add_kctl(&spec->gen,
908 "Beep Playback Volume",
909 &beep_vol_ctl);
910 if (!knew)
911 return -ENOMEM;
912 knew->private_value =
913 HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT);
d78d7a90 914 }
36c9db7a
TI
915 return 0;
916}
d78d7a90 917
36c9db7a
TI
918#ifdef CONFIG_SND_HDA_INPUT_BEEP
919#define stac_dig_beep_switch_info snd_ctl_boolean_mono_info
e4973e1e 920
36c9db7a
TI
921static int stac_dig_beep_switch_get(struct snd_kcontrol *kcontrol,
922 struct snd_ctl_elem_value *ucontrol)
923{
924 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
925 ucontrol->value.integer.value[0] = codec->beep->enabled;
926 return 0;
927}
e4973e1e 928
36c9db7a
TI
929static int stac_dig_beep_switch_put(struct snd_kcontrol *kcontrol,
930 struct snd_ctl_elem_value *ucontrol)
931{
932 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
933 return snd_hda_enable_beep_device(codec, ucontrol->value.integer.value[0]);
2f2f4251
M
934}
935
36c9db7a
TI
936static const struct snd_kcontrol_new stac_dig_beep_ctrl = {
937 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
938 .name = "Beep Playback Switch",
939 .info = stac_dig_beep_switch_info,
940 .get = stac_dig_beep_switch_get,
941 .put = stac_dig_beep_switch_put,
2f2f4251
M
942};
943
36c9db7a
TI
944static int stac_beep_switch_ctl(struct hda_codec *codec)
945{
946 struct sigmatel_spec *spec = codec->spec;
947
948 if (!snd_hda_gen_add_kctl(&spec->gen, NULL, &stac_dig_beep_ctrl))
949 return -ENOMEM;
950 return 0;
951}
952#endif
953
42875479
TI
954/*
955 * SPDIF-out mux controls
956 */
957
958static int stac_smux_enum_info(struct snd_kcontrol *kcontrol,
959 struct snd_ctl_elem_info *uinfo)
960{
961 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
962 struct sigmatel_spec *spec = codec->spec;
963 return snd_hda_input_mux_info(&spec->spdif_mux, uinfo);
964}
965
966static int stac_smux_enum_get(struct snd_kcontrol *kcontrol,
967 struct snd_ctl_elem_value *ucontrol)
968{
969 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
970 struct sigmatel_spec *spec = codec->spec;
971 unsigned int smux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
972
973 ucontrol->value.enumerated.item[0] = spec->cur_smux[smux_idx];
974 return 0;
975}
976
977static int stac_smux_enum_put(struct snd_kcontrol *kcontrol,
978 struct snd_ctl_elem_value *ucontrol)
979{
980 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
981 struct sigmatel_spec *spec = codec->spec;
982 unsigned int smux_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
983
984 return snd_hda_input_mux_put(codec, &spec->spdif_mux, ucontrol,
985 spec->gen.autocfg.dig_out_pins[smux_idx],
986 &spec->cur_smux[smux_idx]);
987}
988
989static struct snd_kcontrol_new stac_smux_mixer = {
990 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
991 .name = "IEC958 Playback Source",
992 /* count set later */
993 .info = stac_smux_enum_info,
994 .get = stac_smux_enum_get,
995 .put = stac_smux_enum_put,
996};
997
998static const char * const stac_spdif_labels[] = {
999 "Digital Playback", "Analog Mux 1", "Analog Mux 2", NULL
1000};
1001
1002static int stac_create_spdif_mux_ctls(struct hda_codec *codec)
1003{
1004 struct sigmatel_spec *spec = codec->spec;
1005 struct auto_pin_cfg *cfg = &spec->gen.autocfg;
1006 const char * const *labels = spec->spdif_labels;
1007 struct snd_kcontrol_new *kctl;
1008 int i, num_cons;
1009
1010 if (cfg->dig_outs < 1)
1011 return 0;
1012
1013 num_cons = snd_hda_get_num_conns(codec, cfg->dig_out_pins[0]);
1014 if (num_cons <= 1)
1015 return 0;
1016
1017 if (!labels)
1018 labels = stac_spdif_labels;
1019 for (i = 0; i < num_cons; i++) {
1020 if (snd_BUG_ON(!labels[i]))
1021 return -EINVAL;
6194b99d 1022 snd_hda_add_imux_item(codec, &spec->spdif_mux, labels[i], i, NULL);
42875479
TI
1023 }
1024
1025 kctl = snd_hda_gen_add_kctl(&spec->gen, NULL, &stac_smux_mixer);
1026 if (!kctl)
1027 return -ENOMEM;
1028 kctl->count = cfg->dig_outs;
1029
1030 return 0;
1031}
1032
36c9db7a
TI
1033/*
1034 */
1035
1036static const struct hda_verb stac9200_core_init[] = {
1037 /* set dac0mux for dac converter */
1038 { 0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
d39a3ae8 1039 {}
58eec423 1040};
d39a3ae8 1041
36c9db7a
TI
1042static const struct hda_verb stac9200_eapd_init[] = {
1043 /* set dac0mux for dac converter */
1044 {0x07, AC_VERB_SET_CONNECT_SEL, 0x00},
1045 {0x08, AC_VERB_SET_EAPD_BTLENABLE, 0x02},
d39a3ae8 1046 {}
58eec423
MCC
1047};
1048
36c9db7a
TI
1049static const struct hda_verb dell_eq_core_init[] = {
1050 /* set master volume to max value without distortion
1051 * and direct control */
1052 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xec},
d39a3ae8 1053 {}
dfe495d0
TI
1054};
1055
36c9db7a
TI
1056static const struct hda_verb stac92hd73xx_core_init[] = {
1057 /* set master volume and direct control */
1058 { 0x1f, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
d39a3ae8 1059 {}
dfe495d0
TI
1060};
1061
36c9db7a
TI
1062static const struct hda_verb stac92hd83xxx_core_init[] = {
1063 /* power state controls amps */
1064 { 0x01, AC_VERB_SET_EAPD, 1 << 2},
1065 {}
1066};
1067
1068static const struct hda_verb stac92hd83xxx_hp_zephyr_init[] = {
1069 { 0x22, 0x785, 0x43 },
1070 { 0x22, 0x782, 0xe0 },
1071 { 0x22, 0x795, 0x00 },
1072 {}
1073};
1074
1075static const struct hda_verb stac92hd71bxx_core_init[] = {
1076 /* set master volume and direct control */
1077 { 0x28, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
1078 {}
1079};
1080
1081static const struct hda_verb stac92hd71bxx_unmute_core_init[] = {
1082 /* unmute right and left channels for nodes 0x0f, 0xa, 0x0d */
1083 { 0x0f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1084 { 0x0a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1085 { 0x0d, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
1086 {}
1087};
1088
1089static const struct hda_verb stac925x_core_init[] = {
1090 /* set dac0mux for dac converter */
1091 { 0x06, AC_VERB_SET_CONNECT_SEL, 0x00},
1092 /* mute the master volume */
1093 { 0x0e, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE },
1094 {}
1095};
1096
1097static const struct hda_verb stac922x_core_init[] = {
1098 /* set master volume and direct control */
1099 { 0x16, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
1100 {}
1101};
1102
1103static const struct hda_verb d965_core_init[] = {
1104 /* unmute node 0x1b */
1105 { 0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1106 /* select node 0x03 as DAC */
1107 { 0x0b, AC_VERB_SET_CONNECT_SEL, 0x01},
1108 {}
1109};
1110
1111static const struct hda_verb dell_3st_core_init[] = {
1112 /* don't set delta bit */
1113 {0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0x7f},
1114 /* unmute node 0x1b */
1115 {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000},
1116 /* select node 0x03 as DAC */
1117 {0x0b, AC_VERB_SET_CONNECT_SEL, 0x01},
1118 {}
1119};
1120
1121static const struct hda_verb stac927x_core_init[] = {
1122 /* set master volume and direct control */
1123 { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
1124 /* enable analog pc beep path */
1125 { 0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5},
1126 {}
1127};
1128
1129static const struct hda_verb stac927x_volknob_core_init[] = {
1130 /* don't set delta bit */
1131 {0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0x7f},
1132 /* enable analog pc beep path */
1133 {0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5},
1134 {}
1135};
1136
1137static const struct hda_verb stac9205_core_init[] = {
1138 /* set master volume and direct control */
1139 { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff},
1140 /* enable analog pc beep path */
1141 { 0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5},
1142 {}
1143};
1144
1145static const struct snd_kcontrol_new stac92hd73xx_6ch_loopback =
1146 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 3);
1147
1148static const struct snd_kcontrol_new stac92hd73xx_8ch_loopback =
1149 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 4);
1150
1151static const struct snd_kcontrol_new stac92hd73xx_10ch_loopback =
1152 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A1, 5);
1153
1154static const struct snd_kcontrol_new stac92hd71bxx_loopback =
1155 STAC_ANALOG_LOOPBACK(0xFA0, 0x7A0, 2);
1156
1157static const struct snd_kcontrol_new stac9205_loopback =
1158 STAC_ANALOG_LOOPBACK(0xFE0, 0x7E0, 1);
1159
1160static const struct snd_kcontrol_new stac927x_loopback =
1161 STAC_ANALOG_LOOPBACK(0xFEB, 0x7EB, 1);
1162
1163static const struct hda_pintbl ref9200_pin_configs[] = {
1164 { 0x08, 0x01c47010 },
1165 { 0x09, 0x01447010 },
1166 { 0x0d, 0x0221401f },
1167 { 0x0e, 0x01114010 },
1168 { 0x0f, 0x02a19020 },
1169 { 0x10, 0x01a19021 },
1170 { 0x11, 0x90100140 },
1171 { 0x12, 0x01813122 },
1172 {}
1173};
1174
1175static const struct hda_pintbl gateway9200_m4_pin_configs[] = {
1176 { 0x08, 0x400000fe },
1177 { 0x09, 0x404500f4 },
1178 { 0x0d, 0x400100f0 },
1179 { 0x0e, 0x90110010 },
1180 { 0x0f, 0x400100f1 },
1181 { 0x10, 0x02a1902e },
1182 { 0x11, 0x500000f2 },
1183 { 0x12, 0x500000f3 },
1184 {}
1185};
1186
1187static const struct hda_pintbl gateway9200_m4_2_pin_configs[] = {
1188 { 0x08, 0x400000fe },
1189 { 0x09, 0x404500f4 },
1190 { 0x0d, 0x400100f0 },
1191 { 0x0e, 0x90110010 },
1192 { 0x0f, 0x400100f1 },
1193 { 0x10, 0x02a1902e },
1194 { 0x11, 0x500000f2 },
1195 { 0x12, 0x500000f3 },
1196 {}
1197};
1198
1199/*
1200 STAC 9200 pin configs for
1201 102801A8
1202 102801DE
1203 102801E8
1204*/
1205static const struct hda_pintbl dell9200_d21_pin_configs[] = {
1206 { 0x08, 0x400001f0 },
1207 { 0x09, 0x400001f1 },
1208 { 0x0d, 0x02214030 },
1209 { 0x0e, 0x01014010 },
1210 { 0x0f, 0x02a19020 },
1211 { 0x10, 0x01a19021 },
1212 { 0x11, 0x90100140 },
1213 { 0x12, 0x01813122 },
1214 {}
1215};
1216
1217/*
1218 STAC 9200 pin configs for
1219 102801C0
1220 102801C1
1221*/
1222static const struct hda_pintbl dell9200_d22_pin_configs[] = {
1223 { 0x08, 0x400001f0 },
1224 { 0x09, 0x400001f1 },
1225 { 0x0d, 0x0221401f },
1226 { 0x0e, 0x01014010 },
1227 { 0x0f, 0x01813020 },
1228 { 0x10, 0x02a19021 },
1229 { 0x11, 0x90100140 },
1230 { 0x12, 0x400001f2 },
1231 {}
1232};
1233
1234/*
dfe495d0
TI
1235 STAC 9200 pin configs for
1236 102801C4 (Dell Dimension E310)
1237 102801C5
1238 102801C7
1239 102801D9
1240 102801DA
1241 102801E3
1242*/
d39a3ae8
TI
1243static const struct hda_pintbl dell9200_d23_pin_configs[] = {
1244 { 0x08, 0x400001f0 },
1245 { 0x09, 0x400001f1 },
1246 { 0x0d, 0x0221401f },
1247 { 0x0e, 0x01014010 },
1248 { 0x0f, 0x01813020 },
1249 { 0x10, 0x01a19021 },
1250 { 0x11, 0x90100140 },
1251 { 0x12, 0x400001f2 },
1252 {}
dfe495d0
TI
1253};
1254
1255
1256/*
1257 STAC 9200-32 pin configs for
1258 102801B5 (Dell Inspiron 630m)
1259 102801D8 (Dell Inspiron 640m)
1260*/
d39a3ae8
TI
1261static const struct hda_pintbl dell9200_m21_pin_configs[] = {
1262 { 0x08, 0x40c003fa },
1263 { 0x09, 0x03441340 },
1264 { 0x0d, 0x0321121f },
1265 { 0x0e, 0x90170310 },
1266 { 0x0f, 0x408003fb },
1267 { 0x10, 0x03a11020 },
1268 { 0x11, 0x401003fc },
1269 { 0x12, 0x403003fd },
1270 {}
dfe495d0
TI
1271};
1272
1273/*
1274 STAC 9200-32 pin configs for
1275 102801C2 (Dell Latitude D620)
1276 102801C8
1277 102801CC (Dell Latitude D820)
1278 102801D4
1279 102801D6
1280*/
d39a3ae8
TI
1281static const struct hda_pintbl dell9200_m22_pin_configs[] = {
1282 { 0x08, 0x40c003fa },
1283 { 0x09, 0x0144131f },
1284 { 0x0d, 0x0321121f },
1285 { 0x0e, 0x90170310 },
1286 { 0x0f, 0x90a70321 },
1287 { 0x10, 0x03a11020 },
1288 { 0x11, 0x401003fb },
1289 { 0x12, 0x40f000fc },
1290 {}
dfe495d0
TI
1291};
1292
1293/*
1294 STAC 9200-32 pin configs for
1295 102801CE (Dell XPS M1710)
1296 102801CF (Dell Precision M90)
1297*/
d39a3ae8
TI
1298static const struct hda_pintbl dell9200_m23_pin_configs[] = {
1299 { 0x08, 0x40c003fa },
1300 { 0x09, 0x01441340 },
1301 { 0x0d, 0x0421421f },
1302 { 0x0e, 0x90170310 },
1303 { 0x0f, 0x408003fb },
1304 { 0x10, 0x04a1102e },
1305 { 0x11, 0x90170311 },
1306 { 0x12, 0x403003fc },
1307 {}
dfe495d0
TI
1308};
1309
1310/*
1311 STAC 9200-32 pin configs for
1312 102801C9
1313 102801CA
1314 102801CB (Dell Latitude 120L)
1315 102801D3
1316*/
d39a3ae8
TI
1317static const struct hda_pintbl dell9200_m24_pin_configs[] = {
1318 { 0x08, 0x40c003fa },
1319 { 0x09, 0x404003fb },
1320 { 0x0d, 0x0321121f },
1321 { 0x0e, 0x90170310 },
1322 { 0x0f, 0x408003fc },
1323 { 0x10, 0x03a11020 },
1324 { 0x11, 0x401003fd },
1325 { 0x12, 0x403003fe },
1326 {}
dfe495d0
TI
1327};
1328
1329/*
1330 STAC 9200-32 pin configs for
1331 102801BD (Dell Inspiron E1505n)
1332 102801EE
1333 102801EF
1334*/
d39a3ae8
TI
1335static const struct hda_pintbl dell9200_m25_pin_configs[] = {
1336 { 0x08, 0x40c003fa },
1337 { 0x09, 0x01441340 },
1338 { 0x0d, 0x0421121f },
1339 { 0x0e, 0x90170310 },
1340 { 0x0f, 0x408003fb },
1341 { 0x10, 0x04a11020 },
1342 { 0x11, 0x401003fc },
1343 { 0x12, 0x403003fd },
1344 {}
dfe495d0
TI
1345};
1346
1347/*
1348 STAC 9200-32 pin configs for
1349 102801F5 (Dell Inspiron 1501)
1350 102801F6
1351*/
d39a3ae8
TI
1352static const struct hda_pintbl dell9200_m26_pin_configs[] = {
1353 { 0x08, 0x40c003fa },
1354 { 0x09, 0x404003fb },
1355 { 0x0d, 0x0421121f },
1356 { 0x0e, 0x90170310 },
1357 { 0x0f, 0x408003fc },
1358 { 0x10, 0x04a11020 },
1359 { 0x11, 0x401003fd },
1360 { 0x12, 0x403003fe },
1361 {}
dfe495d0
TI
1362};
1363
1364/*
1365 STAC 9200-32
1366 102801CD (Dell Inspiron E1705/9400)
1367*/
d39a3ae8
TI
1368static const struct hda_pintbl dell9200_m27_pin_configs[] = {
1369 { 0x08, 0x40c003fa },
1370 { 0x09, 0x01441340 },
1371 { 0x0d, 0x0421121f },
1372 { 0x0e, 0x90170310 },
1373 { 0x0f, 0x90170310 },
1374 { 0x10, 0x04a11020 },
1375 { 0x11, 0x90170310 },
1376 { 0x12, 0x40f003fc },
1377 {}
dfe495d0
TI
1378};
1379
d39a3ae8
TI
1380static const struct hda_pintbl oqo9200_pin_configs[] = {
1381 { 0x08, 0x40c000f0 },
1382 { 0x09, 0x404000f1 },
1383 { 0x0d, 0x0221121f },
1384 { 0x0e, 0x02211210 },
1385 { 0x0f, 0x90170111 },
1386 { 0x10, 0x90a70120 },
1387 { 0x11, 0x400000f2 },
1388 { 0x12, 0x400000f3 },
1389 {}
bf277785
TD
1390};
1391
dfe495d0 1392
d39a3ae8
TI
1393static void stac9200_fixup_panasonic(struct hda_codec *codec,
1394 const struct hda_fixup *fix, int action)
1395{
1396 struct sigmatel_spec *spec = codec->spec;
1397
36c9db7a 1398 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
d39a3ae8
TI
1399 spec->gpio_mask = spec->gpio_dir = 0x09;
1400 spec->gpio_data = 0x00;
d39a3ae8
TI
1401 /* CF-74 has no headphone detection, and the driver should *NOT*
1402 * do detection and HP/speaker toggle because the hardware does it.
1403 */
36c9db7a 1404 spec->gen.suppress_auto_mute = 1;
d39a3ae8
TI
1405 }
1406}
1407
1408
1409static const struct hda_fixup stac9200_fixups[] = {
1410 [STAC_REF] = {
1411 .type = HDA_FIXUP_PINS,
1412 .v.pins = ref9200_pin_configs,
1413 },
1414 [STAC_9200_OQO] = {
1415 .type = HDA_FIXUP_PINS,
1416 .v.pins = oqo9200_pin_configs,
1417 .chained = true,
1418 .chain_id = STAC_9200_EAPD_INIT,
1419 },
1420 [STAC_9200_DELL_D21] = {
1421 .type = HDA_FIXUP_PINS,
1422 .v.pins = dell9200_d21_pin_configs,
1423 },
1424 [STAC_9200_DELL_D22] = {
1425 .type = HDA_FIXUP_PINS,
1426 .v.pins = dell9200_d22_pin_configs,
1427 },
1428 [STAC_9200_DELL_D23] = {
1429 .type = HDA_FIXUP_PINS,
1430 .v.pins = dell9200_d23_pin_configs,
1431 },
1432 [STAC_9200_DELL_M21] = {
1433 .type = HDA_FIXUP_PINS,
1434 .v.pins = dell9200_m21_pin_configs,
1435 },
1436 [STAC_9200_DELL_M22] = {
1437 .type = HDA_FIXUP_PINS,
1438 .v.pins = dell9200_m22_pin_configs,
1439 },
1440 [STAC_9200_DELL_M23] = {
1441 .type = HDA_FIXUP_PINS,
1442 .v.pins = dell9200_m23_pin_configs,
1443 },
1444 [STAC_9200_DELL_M24] = {
1445 .type = HDA_FIXUP_PINS,
1446 .v.pins = dell9200_m24_pin_configs,
1447 },
1448 [STAC_9200_DELL_M25] = {
1449 .type = HDA_FIXUP_PINS,
1450 .v.pins = dell9200_m25_pin_configs,
1451 },
1452 [STAC_9200_DELL_M26] = {
1453 .type = HDA_FIXUP_PINS,
1454 .v.pins = dell9200_m26_pin_configs,
1455 },
1456 [STAC_9200_DELL_M27] = {
1457 .type = HDA_FIXUP_PINS,
1458 .v.pins = dell9200_m27_pin_configs,
1459 },
1460 [STAC_9200_M4] = {
1461 .type = HDA_FIXUP_PINS,
1462 .v.pins = gateway9200_m4_pin_configs,
1463 .chained = true,
1464 .chain_id = STAC_9200_EAPD_INIT,
1465 },
1466 [STAC_9200_M4_2] = {
1467 .type = HDA_FIXUP_PINS,
1468 .v.pins = gateway9200_m4_2_pin_configs,
1469 .chained = true,
1470 .chain_id = STAC_9200_EAPD_INIT,
1471 },
1472 [STAC_9200_PANASONIC] = {
1473 .type = HDA_FIXUP_FUNC,
1474 .v.func = stac9200_fixup_panasonic,
1475 },
1476 [STAC_9200_EAPD_INIT] = {
1477 .type = HDA_FIXUP_VERBS,
1478 .v.verbs = (const struct hda_verb[]) {
1479 {0x08, AC_VERB_SET_EAPD_BTLENABLE, 0x02},
1480 {}
1481 },
1482 },
403d1944
MP
1483};
1484
d39a3ae8
TI
1485static const struct hda_model_fixup stac9200_models[] = {
1486 { .id = STAC_REF, .name = "ref" },
1487 { .id = STAC_9200_OQO, .name = "oqo" },
1488 { .id = STAC_9200_DELL_D21, .name = "dell-d21" },
1489 { .id = STAC_9200_DELL_D22, .name = "dell-d22" },
1490 { .id = STAC_9200_DELL_D23, .name = "dell-d23" },
1491 { .id = STAC_9200_DELL_M21, .name = "dell-m21" },
1492 { .id = STAC_9200_DELL_M22, .name = "dell-m22" },
1493 { .id = STAC_9200_DELL_M23, .name = "dell-m23" },
1494 { .id = STAC_9200_DELL_M24, .name = "dell-m24" },
1495 { .id = STAC_9200_DELL_M25, .name = "dell-m25" },
1496 { .id = STAC_9200_DELL_M26, .name = "dell-m26" },
1497 { .id = STAC_9200_DELL_M27, .name = "dell-m27" },
1498 { .id = STAC_9200_M4, .name = "gateway-m4" },
1499 { .id = STAC_9200_M4_2, .name = "gateway-m4-2" },
1500 { .id = STAC_9200_PANASONIC, .name = "panasonic" },
1501 {}
1502};
1503
1504static const struct snd_pci_quirk stac9200_fixup_tbl[] = {
f5fcc13c
TI
1505 /* SigmaTel reference board */
1506 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
1507 "DFI LanParty", STAC_REF),
577aa2c1
MR
1508 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
1509 "DFI LanParty", STAC_REF),
e7377071 1510 /* Dell laptops have BIOS problem */
dfe495d0
TI
1511 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a8,
1512 "unknown Dell", STAC_9200_DELL_D21),
f5fcc13c 1513 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01b5,
dfe495d0
TI
1514 "Dell Inspiron 630m", STAC_9200_DELL_M21),
1515 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01bd,
1516 "Dell Inspiron E1505n", STAC_9200_DELL_M25),
1517 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c0,
1518 "unknown Dell", STAC_9200_DELL_D22),
1519 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c1,
1520 "unknown Dell", STAC_9200_DELL_D22),
f5fcc13c 1521 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c2,
dfe495d0
TI
1522 "Dell Latitude D620", STAC_9200_DELL_M22),
1523 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c5,
1524 "unknown Dell", STAC_9200_DELL_D23),
1525 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c7,
1526 "unknown Dell", STAC_9200_DELL_D23),
1527 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c8,
1528 "unknown Dell", STAC_9200_DELL_M22),
1529 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01c9,
1530 "unknown Dell", STAC_9200_DELL_M24),
1531 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ca,
1532 "unknown Dell", STAC_9200_DELL_M24),
f5fcc13c 1533 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cb,
dfe495d0 1534 "Dell Latitude 120L", STAC_9200_DELL_M24),
877b866d 1535 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cc,
dfe495d0 1536 "Dell Latitude D820", STAC_9200_DELL_M22),
46f02ca3 1537 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cd,
dfe495d0 1538 "Dell Inspiron E1705/9400", STAC_9200_DELL_M27),
46f02ca3 1539 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ce,
dfe495d0 1540 "Dell XPS M1710", STAC_9200_DELL_M23),
f0f96745 1541 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01cf,
dfe495d0
TI
1542 "Dell Precision M90", STAC_9200_DELL_M23),
1543 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d3,
1544 "unknown Dell", STAC_9200_DELL_M22),
1545 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d4,
1546 "unknown Dell", STAC_9200_DELL_M22),
8286c53e 1547 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d6,
dfe495d0 1548 "unknown Dell", STAC_9200_DELL_M22),
49c605db 1549 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d8,
dfe495d0
TI
1550 "Dell Inspiron 640m", STAC_9200_DELL_M21),
1551 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d9,
1552 "unknown Dell", STAC_9200_DELL_D23),
1553 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01da,
1554 "unknown Dell", STAC_9200_DELL_D23),
1555 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01de,
1556 "unknown Dell", STAC_9200_DELL_D21),
1557 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01e3,
1558 "unknown Dell", STAC_9200_DELL_D23),
1559 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01e8,
1560 "unknown Dell", STAC_9200_DELL_D21),
1561 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ee,
1562 "unknown Dell", STAC_9200_DELL_M25),
1563 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ef,
1564 "unknown Dell", STAC_9200_DELL_M25),
49c605db 1565 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f5,
dfe495d0
TI
1566 "Dell Inspiron 1501", STAC_9200_DELL_M26),
1567 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f6,
1568 "unknown Dell", STAC_9200_DELL_M26),
49c605db 1569 /* Panasonic */
117f257d 1570 SND_PCI_QUIRK(0x10f7, 0x8338, "Panasonic CF-74", STAC_9200_PANASONIC),
1194b5b7 1571 /* Gateway machines needs EAPD to be set on resume */
58eec423
MCC
1572 SND_PCI_QUIRK(0x107b, 0x0205, "Gateway S-7110M", STAC_9200_M4),
1573 SND_PCI_QUIRK(0x107b, 0x0317, "Gateway MT3423, MX341*", STAC_9200_M4_2),
1574 SND_PCI_QUIRK(0x107b, 0x0318, "Gateway ML3019, MT3707", STAC_9200_M4_2),
bf277785
TD
1575 /* OQO Mobile */
1576 SND_PCI_QUIRK(0x1106, 0x3288, "OQO Model 2", STAC_9200_OQO),
403d1944
MP
1577 {} /* terminator */
1578};
1579
d2077d40
TI
1580static const struct hda_pintbl ref925x_pin_configs[] = {
1581 { 0x07, 0x40c003f0 },
1582 { 0x08, 0x424503f2 },
1583 { 0x0a, 0x01813022 },
1584 { 0x0b, 0x02a19021 },
1585 { 0x0c, 0x90a70320 },
1586 { 0x0d, 0x02214210 },
1587 { 0x10, 0x01019020 },
1588 { 0x11, 0x9033032e },
1589 {}
8e21c34c
TD
1590};
1591
d2077d40
TI
1592static const struct hda_pintbl stac925xM1_pin_configs[] = {
1593 { 0x07, 0x40c003f4 },
1594 { 0x08, 0x424503f2 },
1595 { 0x0a, 0x400000f3 },
1596 { 0x0b, 0x02a19020 },
1597 { 0x0c, 0x40a000f0 },
1598 { 0x0d, 0x90100210 },
1599 { 0x10, 0x400003f1 },
1600 { 0x11, 0x9033032e },
1601 {}
8e21c34c
TD
1602};
1603
d2077d40
TI
1604static const struct hda_pintbl stac925xM1_2_pin_configs[] = {
1605 { 0x07, 0x40c003f4 },
1606 { 0x08, 0x424503f2 },
1607 { 0x0a, 0x400000f3 },
1608 { 0x0b, 0x02a19020 },
1609 { 0x0c, 0x40a000f0 },
1610 { 0x0d, 0x90100210 },
1611 { 0x10, 0x400003f1 },
1612 { 0x11, 0x9033032e },
1613 {}
9cb36c2a 1614};
58eec423 1615
d2077d40
TI
1616static const struct hda_pintbl stac925xM2_pin_configs[] = {
1617 { 0x07, 0x40c003f4 },
1618 { 0x08, 0x424503f2 },
1619 { 0x0a, 0x400000f3 },
1620 { 0x0b, 0x02a19020 },
1621 { 0x0c, 0x40a000f0 },
1622 { 0x0d, 0x90100210 },
1623 { 0x10, 0x400003f1 },
1624 { 0x11, 0x9033032e },
1625 {}
2c11f955
TD
1626};
1627
d2077d40
TI
1628static const struct hda_pintbl stac925xM2_2_pin_configs[] = {
1629 { 0x07, 0x40c003f4 },
1630 { 0x08, 0x424503f2 },
1631 { 0x0a, 0x400000f3 },
1632 { 0x0b, 0x02a19020 },
1633 { 0x0c, 0x40a000f0 },
1634 { 0x0d, 0x90100210 },
1635 { 0x10, 0x400003f1 },
1636 { 0x11, 0x9033032e },
1637 {}
58eec423
MCC
1638};
1639
d2077d40
TI
1640static const struct hda_pintbl stac925xM3_pin_configs[] = {
1641 { 0x07, 0x40c003f4 },
1642 { 0x08, 0x424503f2 },
1643 { 0x0a, 0x400000f3 },
1644 { 0x0b, 0x02a19020 },
1645 { 0x0c, 0x40a000f0 },
1646 { 0x0d, 0x90100210 },
1647 { 0x10, 0x400003f1 },
1648 { 0x11, 0x503303f3 },
1649 {}
9cb36c2a 1650};
58eec423 1651
d2077d40
TI
1652static const struct hda_pintbl stac925xM5_pin_configs[] = {
1653 { 0x07, 0x40c003f4 },
1654 { 0x08, 0x424503f2 },
1655 { 0x0a, 0x400000f3 },
1656 { 0x0b, 0x02a19020 },
1657 { 0x0c, 0x40a000f0 },
1658 { 0x0d, 0x90100210 },
1659 { 0x10, 0x400003f1 },
1660 { 0x11, 0x9033032e },
1661 {}
9cb36c2a
MCC
1662};
1663
d2077d40
TI
1664static const struct hda_pintbl stac925xM6_pin_configs[] = {
1665 { 0x07, 0x40c003f4 },
1666 { 0x08, 0x424503f2 },
1667 { 0x0a, 0x400000f3 },
1668 { 0x0b, 0x02a19020 },
1669 { 0x0c, 0x40a000f0 },
1670 { 0x0d, 0x90100210 },
1671 { 0x10, 0x400003f1 },
1672 { 0x11, 0x90330320 },
1673 {}
8e21c34c
TD
1674};
1675
d2077d40
TI
1676static const struct hda_fixup stac925x_fixups[] = {
1677 [STAC_REF] = {
1678 .type = HDA_FIXUP_PINS,
1679 .v.pins = ref925x_pin_configs,
1680 },
1681 [STAC_M1] = {
1682 .type = HDA_FIXUP_PINS,
1683 .v.pins = stac925xM1_pin_configs,
1684 },
1685 [STAC_M1_2] = {
1686 .type = HDA_FIXUP_PINS,
1687 .v.pins = stac925xM1_2_pin_configs,
1688 },
1689 [STAC_M2] = {
1690 .type = HDA_FIXUP_PINS,
1691 .v.pins = stac925xM2_pin_configs,
1692 },
1693 [STAC_M2_2] = {
1694 .type = HDA_FIXUP_PINS,
1695 .v.pins = stac925xM2_2_pin_configs,
1696 },
1697 [STAC_M3] = {
1698 .type = HDA_FIXUP_PINS,
1699 .v.pins = stac925xM3_pin_configs,
1700 },
1701 [STAC_M5] = {
1702 .type = HDA_FIXUP_PINS,
1703 .v.pins = stac925xM5_pin_configs,
1704 },
1705 [STAC_M6] = {
1706 .type = HDA_FIXUP_PINS,
1707 .v.pins = stac925xM6_pin_configs,
1708 },
8e21c34c
TD
1709};
1710
d2077d40
TI
1711static const struct hda_model_fixup stac925x_models[] = {
1712 { .id = STAC_REF, .name = "ref" },
1713 { .id = STAC_M1, .name = "m1" },
1714 { .id = STAC_M1_2, .name = "m1-2" },
1715 { .id = STAC_M2, .name = "m2" },
1716 { .id = STAC_M2_2, .name = "m2-2" },
1717 { .id = STAC_M3, .name = "m3" },
1718 { .id = STAC_M5, .name = "m5" },
1719 { .id = STAC_M6, .name = "m6" },
1720 {}
8e21c34c
TD
1721};
1722
d2077d40
TI
1723static const struct snd_pci_quirk stac925x_fixup_tbl[] = {
1724 /* SigmaTel reference board */
1725 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668, "DFI LanParty", STAC_REF),
1726 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101, "DFI LanParty", STAC_REF),
1727 SND_PCI_QUIRK(0x8384, 0x7632, "Stac9202 Reference Board", STAC_REF),
1728
1729 /* Default table for unknown ID */
1730 SND_PCI_QUIRK(0x1002, 0x437b, "Gateway mobile", STAC_M2_2),
1731
1732 /* gateway machines are checked via codec ssid */
58eec423
MCC
1733 SND_PCI_QUIRK(0x107b, 0x0316, "Gateway M255", STAC_M2),
1734 SND_PCI_QUIRK(0x107b, 0x0366, "Gateway MP6954", STAC_M5),
1735 SND_PCI_QUIRK(0x107b, 0x0461, "Gateway NX560XL", STAC_M1),
1736 SND_PCI_QUIRK(0x107b, 0x0681, "Gateway NX860", STAC_M2),
9cb36c2a 1737 SND_PCI_QUIRK(0x107b, 0x0367, "Gateway MX6453", STAC_M1_2),
9cb36c2a
MCC
1738 /* Not sure about the brand name for those */
1739 SND_PCI_QUIRK(0x107b, 0x0281, "Gateway mobile", STAC_M1),
1740 SND_PCI_QUIRK(0x107b, 0x0507, "Gateway mobile", STAC_M3),
1741 SND_PCI_QUIRK(0x107b, 0x0281, "Gateway mobile", STAC_M6),
1742 SND_PCI_QUIRK(0x107b, 0x0685, "Gateway mobile", STAC_M2_2),
9cb36c2a 1743 {} /* terminator */
8e21c34c
TD
1744};
1745
55e30141
TI
1746static const struct hda_pintbl ref92hd73xx_pin_configs[] = {
1747 { 0x0a, 0x02214030 },
1748 { 0x0b, 0x02a19040 },
1749 { 0x0c, 0x01a19020 },
1750 { 0x0d, 0x02214030 },
1751 { 0x0e, 0x0181302e },
1752 { 0x0f, 0x01014010 },
1753 { 0x10, 0x01014020 },
1754 { 0x11, 0x01014030 },
1755 { 0x12, 0x02319040 },
1756 { 0x13, 0x90a000f0 },
1757 { 0x14, 0x90a000f0 },
1758 { 0x22, 0x01452050 },
1759 { 0x23, 0x01452050 },
1760 {}
a7662640
MR
1761};
1762
55e30141
TI
1763static const struct hda_pintbl dell_m6_pin_configs[] = {
1764 { 0x0a, 0x0321101f },
1765 { 0x0b, 0x4f00000f },
1766 { 0x0c, 0x4f0000f0 },
1767 { 0x0d, 0x90170110 },
1768 { 0x0e, 0x03a11020 },
1769 { 0x0f, 0x0321101f },
1770 { 0x10, 0x4f0000f0 },
1771 { 0x11, 0x4f0000f0 },
1772 { 0x12, 0x4f0000f0 },
1773 { 0x13, 0x90a60160 },
1774 { 0x14, 0x4f0000f0 },
1775 { 0x22, 0x4f0000f0 },
1776 { 0x23, 0x4f0000f0 },
1777 {}
e1f0d669
MR
1778};
1779
55e30141
TI
1780static const struct hda_pintbl alienware_m17x_pin_configs[] = {
1781 { 0x0a, 0x0321101f },
1782 { 0x0b, 0x0321101f },
1783 { 0x0c, 0x03a11020 },
1784 { 0x0d, 0x03014020 },
1785 { 0x0e, 0x90170110 },
1786 { 0x0f, 0x4f0000f0 },
1787 { 0x10, 0x4f0000f0 },
1788 { 0x11, 0x4f0000f0 },
1789 { 0x12, 0x4f0000f0 },
1790 { 0x13, 0x90a60160 },
1791 { 0x14, 0x4f0000f0 },
1792 { 0x22, 0x4f0000f0 },
1793 { 0x23, 0x904601b0 },
1794 {}
842ae638
TI
1795};
1796
55e30141
TI
1797static const struct hda_pintbl intel_dg45id_pin_configs[] = {
1798 { 0x0a, 0x02214230 },
1799 { 0x0b, 0x02A19240 },
1800 { 0x0c, 0x01013214 },
1801 { 0x0d, 0x01014210 },
1802 { 0x0e, 0x01A19250 },
1803 { 0x0f, 0x01011212 },
1804 { 0x10, 0x01016211 },
1805 {}
52dc4386
AF
1806};
1807
1de7ca5e
HW
1808static const struct hda_pintbl stac92hd89xx_hp_front_jack_pin_configs[] = {
1809 { 0x0a, 0x02214030 },
1810 { 0x0b, 0x02A19010 },
1811 {}
1812};
1813
7440850c
HW
1814static const struct hda_pintbl stac92hd89xx_hp_z1_g2_right_mic_jack_pin_configs[] = {
1815 { 0x0e, 0x400000f0 },
1816 {}
1817};
1818
55e30141
TI
1819static void stac92hd73xx_fixup_ref(struct hda_codec *codec,
1820 const struct hda_fixup *fix, int action)
1821{
1822 struct sigmatel_spec *spec = codec->spec;
1823
1824 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1825 return;
1826
1827 snd_hda_apply_pincfgs(codec, ref92hd73xx_pin_configs);
1828 spec->gpio_mask = spec->gpio_dir = spec->gpio_data = 0;
1829}
1830
1831static void stac92hd73xx_fixup_dell(struct hda_codec *codec)
1832{
1833 struct sigmatel_spec *spec = codec->spec;
1834
1835 snd_hda_apply_pincfgs(codec, dell_m6_pin_configs);
55e30141
TI
1836 spec->eapd_switch = 0;
1837}
1838
1839static void stac92hd73xx_fixup_dell_eq(struct hda_codec *codec,
1840 const struct hda_fixup *fix, int action)
1841{
1842 struct sigmatel_spec *spec = codec->spec;
1843
1844 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1845 return;
1846
1847 stac92hd73xx_fixup_dell(codec);
1848 snd_hda_add_verbs(codec, dell_eq_core_init);
1849 spec->volknob_init = 1;
1850}
1851
1852/* Analog Mics */
1853static void stac92hd73xx_fixup_dell_m6_amic(struct hda_codec *codec,
1854 const struct hda_fixup *fix, int action)
1855{
55e30141
TI
1856 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1857 return;
1858
1859 stac92hd73xx_fixup_dell(codec);
1860 snd_hda_codec_set_pincfg(codec, 0x0b, 0x90A70170);
55e30141
TI
1861}
1862
1863/* Digital Mics */
1864static void stac92hd73xx_fixup_dell_m6_dmic(struct hda_codec *codec,
1865 const struct hda_fixup *fix, int action)
1866{
55e30141
TI
1867 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1868 return;
1869
1870 stac92hd73xx_fixup_dell(codec);
1871 snd_hda_codec_set_pincfg(codec, 0x13, 0x90A60160);
55e30141
TI
1872}
1873
1874/* Both */
1875static void stac92hd73xx_fixup_dell_m6_both(struct hda_codec *codec,
1876 const struct hda_fixup *fix, int action)
1877{
55e30141
TI
1878 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1879 return;
1880
1881 stac92hd73xx_fixup_dell(codec);
1882 snd_hda_codec_set_pincfg(codec, 0x0b, 0x90A70170);
1883 snd_hda_codec_set_pincfg(codec, 0x13, 0x90A60160);
55e30141
TI
1884}
1885
1886static void stac92hd73xx_fixup_alienware_m17x(struct hda_codec *codec,
1887 const struct hda_fixup *fix, int action)
1888{
1889 struct sigmatel_spec *spec = codec->spec;
1890
1891 if (action != HDA_FIXUP_ACT_PRE_PROBE)
1892 return;
1893
1894 snd_hda_apply_pincfgs(codec, alienware_m17x_pin_configs);
55e30141
TI
1895 spec->eapd_switch = 0;
1896}
1897
1898static void stac92hd73xx_fixup_no_jd(struct hda_codec *codec,
1899 const struct hda_fixup *fix, int action)
1900{
36c9db7a
TI
1901 if (action == HDA_FIXUP_ACT_PRE_PROBE)
1902 codec->no_jack_detect = 1;
55e30141
TI
1903}
1904
1905static const struct hda_fixup stac92hd73xx_fixups[] = {
1906 [STAC_92HD73XX_REF] = {
1907 .type = HDA_FIXUP_FUNC,
1908 .v.func = stac92hd73xx_fixup_ref,
1909 },
1910 [STAC_DELL_M6_AMIC] = {
1911 .type = HDA_FIXUP_FUNC,
1912 .v.func = stac92hd73xx_fixup_dell_m6_amic,
1913 },
1914 [STAC_DELL_M6_DMIC] = {
1915 .type = HDA_FIXUP_FUNC,
1916 .v.func = stac92hd73xx_fixup_dell_m6_dmic,
1917 },
1918 [STAC_DELL_M6_BOTH] = {
1919 .type = HDA_FIXUP_FUNC,
1920 .v.func = stac92hd73xx_fixup_dell_m6_both,
1921 },
1922 [STAC_DELL_EQ] = {
1923 .type = HDA_FIXUP_FUNC,
1924 .v.func = stac92hd73xx_fixup_dell_eq,
1925 },
1926 [STAC_ALIENWARE_M17X] = {
1927 .type = HDA_FIXUP_FUNC,
1928 .v.func = stac92hd73xx_fixup_alienware_m17x,
1929 },
1930 [STAC_92HD73XX_INTEL] = {
1931 .type = HDA_FIXUP_PINS,
1932 .v.pins = intel_dg45id_pin_configs,
1933 },
1934 [STAC_92HD73XX_NO_JD] = {
1935 .type = HDA_FIXUP_FUNC,
1936 .v.func = stac92hd73xx_fixup_no_jd,
1de7ca5e
HW
1937 },
1938 [STAC_92HD89XX_HP_FRONT_JACK] = {
1939 .type = HDA_FIXUP_PINS,
1940 .v.pins = stac92hd89xx_hp_front_jack_pin_configs,
7440850c
HW
1941 },
1942 [STAC_92HD89XX_HP_Z1_G2_RIGHT_MIC_JACK] = {
1943 .type = HDA_FIXUP_PINS,
1944 .v.pins = stac92hd89xx_hp_z1_g2_right_mic_jack_pin_configs,
55e30141 1945 }
e1f0d669
MR
1946};
1947
55e30141
TI
1948static const struct hda_model_fixup stac92hd73xx_models[] = {
1949 { .id = STAC_92HD73XX_NO_JD, .name = "no-jd" },
1950 { .id = STAC_92HD73XX_REF, .name = "ref" },
1951 { .id = STAC_92HD73XX_INTEL, .name = "intel" },
1952 { .id = STAC_DELL_M6_AMIC, .name = "dell-m6-amic" },
1953 { .id = STAC_DELL_M6_DMIC, .name = "dell-m6-dmic" },
1954 { .id = STAC_DELL_M6_BOTH, .name = "dell-m6" },
1955 { .id = STAC_DELL_EQ, .name = "dell-eq" },
1956 { .id = STAC_ALIENWARE_M17X, .name = "alienware" },
1957 {}
e1f0d669
MR
1958};
1959
55e30141 1960static const struct snd_pci_quirk stac92hd73xx_fixup_tbl[] = {
e1f0d669
MR
1961 /* SigmaTel reference board */
1962 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
a7662640 1963 "DFI LanParty", STAC_92HD73XX_REF),
577aa2c1
MR
1964 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
1965 "DFI LanParty", STAC_92HD73XX_REF),
ae709440
WF
1966 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5002,
1967 "Intel DG45ID", STAC_92HD73XX_INTEL),
1968 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5003,
1969 "Intel DG45FC", STAC_92HD73XX_INTEL),
a7662640 1970 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0254,
661cd8fb 1971 "Dell Studio 1535", STAC_DELL_M6_DMIC),
a7662640 1972 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0255,
661cd8fb 1973 "unknown Dell", STAC_DELL_M6_DMIC),
a7662640 1974 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0256,
661cd8fb 1975 "unknown Dell", STAC_DELL_M6_BOTH),
a7662640 1976 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0257,
661cd8fb 1977 "unknown Dell", STAC_DELL_M6_BOTH),
a7662640 1978 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x025e,
661cd8fb 1979 "unknown Dell", STAC_DELL_M6_AMIC),
a7662640 1980 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x025f,
661cd8fb 1981 "unknown Dell", STAC_DELL_M6_AMIC),
a7662640 1982 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0271,
661cd8fb
TI
1983 "unknown Dell", STAC_DELL_M6_DMIC),
1984 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0272,
1985 "unknown Dell", STAC_DELL_M6_DMIC),
b0fc5e04 1986 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x029f,
661cd8fb 1987 "Dell Studio 1537", STAC_DELL_M6_DMIC),
fa620e97
JS
1988 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02a0,
1989 "Dell Studio 17", STAC_DELL_M6_DMIC),
626f5cef
TI
1990 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02be,
1991 "Dell Studio 1555", STAC_DELL_M6_DMIC),
8ef5837a
DB
1992 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02bd,
1993 "Dell Studio 1557", STAC_DELL_M6_DMIC),
aac78daf 1994 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02fe,
ffe535ed 1995 "Dell Studio XPS 1645", STAC_DELL_M6_DMIC),
5c1bccf6 1996 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0413,
e033ebfb 1997 "Dell Studio 1558", STAC_DELL_M6_DMIC),
55e30141 1998 /* codec SSID matching */
842ae638
TI
1999 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02a1,
2000 "Alienware M17x", STAC_ALIENWARE_M17X),
0defe09c
DC
2001 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x043a,
2002 "Alienware M17x", STAC_ALIENWARE_M17X),
dbd1b547 2003 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0490,
b9ecc4ee 2004 "Alienware M17x R3", STAC_DELL_EQ),
7440850c
HW
2005 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1927,
2006 "HP Z1 G2", STAC_92HD89XX_HP_Z1_G2_RIGHT_MIC_JACK),
1de7ca5e
HW
2007 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2b17,
2008 "unknown HP", STAC_92HD89XX_HP_FRONT_JACK),
842ae638
TI
2009 {} /* terminator */
2010};
2011
372f8c75
TI
2012static const struct hda_pintbl ref92hd83xxx_pin_configs[] = {
2013 { 0x0a, 0x02214030 },
2014 { 0x0b, 0x02211010 },
2015 { 0x0c, 0x02a19020 },
2016 { 0x0d, 0x02170130 },
2017 { 0x0e, 0x01014050 },
2018 { 0x0f, 0x01819040 },
2019 { 0x10, 0x01014020 },
2020 { 0x11, 0x90a3014e },
2021 { 0x1f, 0x01451160 },
2022 { 0x20, 0x98560170 },
2023 {}
d0513fc6
MR
2024};
2025
372f8c75
TI
2026static const struct hda_pintbl dell_s14_pin_configs[] = {
2027 { 0x0a, 0x0221403f },
2028 { 0x0b, 0x0221101f },
2029 { 0x0c, 0x02a19020 },
2030 { 0x0d, 0x90170110 },
2031 { 0x0e, 0x40f000f0 },
2032 { 0x0f, 0x40f000f0 },
2033 { 0x10, 0x40f000f0 },
2034 { 0x11, 0x90a60160 },
2035 { 0x1f, 0x40f000f0 },
2036 { 0x20, 0x40f000f0 },
2037 {}
8bb0ac55
MR
2038};
2039
372f8c75
TI
2040static const struct hda_pintbl dell_vostro_3500_pin_configs[] = {
2041 { 0x0a, 0x02a11020 },
2042 { 0x0b, 0x0221101f },
2043 { 0x0c, 0x400000f0 },
2044 { 0x0d, 0x90170110 },
2045 { 0x0e, 0x400000f1 },
2046 { 0x0f, 0x400000f2 },
2047 { 0x10, 0x400000f3 },
2048 { 0x11, 0x90a60160 },
2049 { 0x1f, 0x400000f4 },
2050 { 0x20, 0x400000f5 },
2051 {}
f7f9bdfa
JW
2052};
2053
372f8c75
TI
2054static const struct hda_pintbl hp_dv7_4000_pin_configs[] = {
2055 { 0x0a, 0x03a12050 },
2056 { 0x0b, 0x0321201f },
2057 { 0x0c, 0x40f000f0 },
2058 { 0x0d, 0x90170110 },
2059 { 0x0e, 0x40f000f0 },
2060 { 0x0f, 0x40f000f0 },
2061 { 0x10, 0x90170110 },
2062 { 0x11, 0xd5a30140 },
2063 { 0x1f, 0x40f000f0 },
2064 { 0x20, 0x40f000f0 },
2065 {}
48315590
SE
2066};
2067
372f8c75
TI
2068static const struct hda_pintbl hp_zephyr_pin_configs[] = {
2069 { 0x0a, 0x01813050 },
2070 { 0x0b, 0x0421201f },
2071 { 0x0c, 0x04a1205e },
2072 { 0x0d, 0x96130310 },
2073 { 0x0e, 0x96130310 },
2074 { 0x0f, 0x0101401f },
2075 { 0x10, 0x1111611f },
2076 { 0x11, 0xd5a30130 },
2077 {}
5556e147
VK
2078};
2079
372f8c75
TI
2080static const struct hda_pintbl hp_cNB11_intquad_pin_configs[] = {
2081 { 0x0a, 0x40f000f0 },
2082 { 0x0b, 0x0221101f },
2083 { 0x0c, 0x02a11020 },
2084 { 0x0d, 0x92170110 },
2085 { 0x0e, 0x40f000f0 },
2086 { 0x0f, 0x92170110 },
2087 { 0x10, 0x40f000f0 },
2088 { 0x11, 0xd5a30130 },
2089 { 0x1f, 0x40f000f0 },
2090 { 0x20, 0x40f000f0 },
2091 {}
0c27c180
VK
2092};
2093
372f8c75
TI
2094static void stac92hd83xxx_fixup_hp(struct hda_codec *codec,
2095 const struct hda_fixup *fix, int action)
2096{
2097 struct sigmatel_spec *spec = codec->spec;
2098
2099 if (action != HDA_FIXUP_ACT_PRE_PROBE)
2100 return;
2101
2102 if (hp_bnb2011_with_dock(codec)) {
2103 snd_hda_codec_set_pincfg(codec, 0xa, 0x2101201f);
2104 snd_hda_codec_set_pincfg(codec, 0xf, 0x2181205e);
2105 }
2106
2107 if (find_mute_led_cfg(codec, spec->default_polarity))
4e76a883 2108 codec_dbg(codec, "mute LED gpio %d polarity %d\n",
372f8c75
TI
2109 spec->gpio_led,
2110 spec->gpio_led_polarity);
e8b99a1d
TI
2111
2112 /* allow auto-switching of dock line-in */
2113 spec->gen.line_in_auto_switch = true;
372f8c75
TI
2114}
2115
2116static void stac92hd83xxx_fixup_hp_zephyr(struct hda_codec *codec,
2117 const struct hda_fixup *fix, int action)
2118{
2119 if (action != HDA_FIXUP_ACT_PRE_PROBE)
2120 return;
2121
2122 snd_hda_apply_pincfgs(codec, hp_zephyr_pin_configs);
2123 snd_hda_add_verbs(codec, stac92hd83xxx_hp_zephyr_init);
2124}
2125
2126static void stac92hd83xxx_fixup_hp_led(struct hda_codec *codec,
2127 const struct hda_fixup *fix, int action)
2128{
2129 struct sigmatel_spec *spec = codec->spec;
2130
2131 if (action == HDA_FIXUP_ACT_PRE_PROBE)
2132 spec->default_polarity = 0;
2133}
2134
2135static void stac92hd83xxx_fixup_hp_inv_led(struct hda_codec *codec,
2136 const struct hda_fixup *fix, int action)
2137{
2138 struct sigmatel_spec *spec = codec->spec;
2139
2140 if (action == HDA_FIXUP_ACT_PRE_PROBE)
2141 spec->default_polarity = 1;
2142}
2143
2144static void stac92hd83xxx_fixup_hp_mic_led(struct hda_codec *codec,
2145 const struct hda_fixup *fix, int action)
2146{
2147 struct sigmatel_spec *spec = codec->spec;
2148
95f74c41 2149 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
372f8c75 2150 spec->mic_mute_led_gpio = 0x08; /* GPIO3 */
873ce8ad
TI
2151 /* resetting controller clears GPIO, so we need to keep on */
2152 codec->bus->power_keep_link_on = 1;
95f74c41 2153 }
372f8c75
TI
2154}
2155
37c367ec
TI
2156static void stac92hd83xxx_fixup_hp_led_gpio10(struct hda_codec *codec,
2157 const struct hda_fixup *fix, int action)
2158{
2159 struct sigmatel_spec *spec = codec->spec;
2160
2161 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
2162 spec->gpio_led = 0x10; /* GPIO4 */
2163 spec->default_polarity = 0;
2164 }
2165}
2166
372f8c75
TI
2167static void stac92hd83xxx_fixup_headset_jack(struct hda_codec *codec,
2168 const struct hda_fixup *fix, int action)
2169{
2170 struct sigmatel_spec *spec = codec->spec;
2171
2172 if (action == HDA_FIXUP_ACT_PRE_PROBE)
2173 spec->headset_jack = 1;
2174}
2175
d009f3de
VK
2176static const struct hda_verb hp_bnb13_eq_verbs[] = {
2177 /* 44.1KHz base */
2178 { 0x22, 0x7A6, 0x3E },
2179 { 0x22, 0x7A7, 0x68 },
2180 { 0x22, 0x7A8, 0x17 },
2181 { 0x22, 0x7A9, 0x3E },
2182 { 0x22, 0x7AA, 0x68 },
2183 { 0x22, 0x7AB, 0x17 },
2184 { 0x22, 0x7AC, 0x00 },
2185 { 0x22, 0x7AD, 0x80 },
2186 { 0x22, 0x7A6, 0x83 },
2187 { 0x22, 0x7A7, 0x2F },
2188 { 0x22, 0x7A8, 0xD1 },
2189 { 0x22, 0x7A9, 0x83 },
2190 { 0x22, 0x7AA, 0x2F },
2191 { 0x22, 0x7AB, 0xD1 },
2192 { 0x22, 0x7AC, 0x01 },
2193 { 0x22, 0x7AD, 0x80 },
2194 { 0x22, 0x7A6, 0x3E },
2195 { 0x22, 0x7A7, 0x68 },
2196 { 0x22, 0x7A8, 0x17 },
2197 { 0x22, 0x7A9, 0x3E },
2198 { 0x22, 0x7AA, 0x68 },
2199 { 0x22, 0x7AB, 0x17 },
2200 { 0x22, 0x7AC, 0x02 },
2201 { 0x22, 0x7AD, 0x80 },
2202 { 0x22, 0x7A6, 0x7C },
2203 { 0x22, 0x7A7, 0xC6 },
2204 { 0x22, 0x7A8, 0x0C },
2205 { 0x22, 0x7A9, 0x7C },
2206 { 0x22, 0x7AA, 0xC6 },
2207 { 0x22, 0x7AB, 0x0C },
2208 { 0x22, 0x7AC, 0x03 },
2209 { 0x22, 0x7AD, 0x80 },
2210 { 0x22, 0x7A6, 0xC3 },
2211 { 0x22, 0x7A7, 0x25 },
2212 { 0x22, 0x7A8, 0xAF },
2213 { 0x22, 0x7A9, 0xC3 },
2214 { 0x22, 0x7AA, 0x25 },
2215 { 0x22, 0x7AB, 0xAF },
2216 { 0x22, 0x7AC, 0x04 },
2217 { 0x22, 0x7AD, 0x80 },
2218 { 0x22, 0x7A6, 0x3E },
2219 { 0x22, 0x7A7, 0x85 },
2220 { 0x22, 0x7A8, 0x73 },
2221 { 0x22, 0x7A9, 0x3E },
2222 { 0x22, 0x7AA, 0x85 },
2223 { 0x22, 0x7AB, 0x73 },
2224 { 0x22, 0x7AC, 0x05 },
2225 { 0x22, 0x7AD, 0x80 },
2226 { 0x22, 0x7A6, 0x85 },
2227 { 0x22, 0x7A7, 0x39 },
2228 { 0x22, 0x7A8, 0xC7 },
2229 { 0x22, 0x7A9, 0x85 },
2230 { 0x22, 0x7AA, 0x39 },
2231 { 0x22, 0x7AB, 0xC7 },
2232 { 0x22, 0x7AC, 0x06 },
2233 { 0x22, 0x7AD, 0x80 },
2234 { 0x22, 0x7A6, 0x3C },
2235 { 0x22, 0x7A7, 0x90 },
2236 { 0x22, 0x7A8, 0xB0 },
2237 { 0x22, 0x7A9, 0x3C },
2238 { 0x22, 0x7AA, 0x90 },
2239 { 0x22, 0x7AB, 0xB0 },
2240 { 0x22, 0x7AC, 0x07 },
2241 { 0x22, 0x7AD, 0x80 },
2242 { 0x22, 0x7A6, 0x7A },
2243 { 0x22, 0x7A7, 0xC6 },
2244 { 0x22, 0x7A8, 0x39 },
2245 { 0x22, 0x7A9, 0x7A },
2246 { 0x22, 0x7AA, 0xC6 },
2247 { 0x22, 0x7AB, 0x39 },
2248 { 0x22, 0x7AC, 0x08 },
2249 { 0x22, 0x7AD, 0x80 },
2250 { 0x22, 0x7A6, 0xC4 },
2251 { 0x22, 0x7A7, 0xE9 },
2252 { 0x22, 0x7A8, 0xDC },
2253 { 0x22, 0x7A9, 0xC4 },
2254 { 0x22, 0x7AA, 0xE9 },
2255 { 0x22, 0x7AB, 0xDC },
2256 { 0x22, 0x7AC, 0x09 },
2257 { 0x22, 0x7AD, 0x80 },
2258 { 0x22, 0x7A6, 0x3D },
2259 { 0x22, 0x7A7, 0xE1 },
2260 { 0x22, 0x7A8, 0x0D },
2261 { 0x22, 0x7A9, 0x3D },
2262 { 0x22, 0x7AA, 0xE1 },
2263 { 0x22, 0x7AB, 0x0D },
2264 { 0x22, 0x7AC, 0x0A },
2265 { 0x22, 0x7AD, 0x80 },
2266 { 0x22, 0x7A6, 0x89 },
2267 { 0x22, 0x7A7, 0xB6 },
2268 { 0x22, 0x7A8, 0xEB },
2269 { 0x22, 0x7A9, 0x89 },
2270 { 0x22, 0x7AA, 0xB6 },
2271 { 0x22, 0x7AB, 0xEB },
2272 { 0x22, 0x7AC, 0x0B },
2273 { 0x22, 0x7AD, 0x80 },
2274 { 0x22, 0x7A6, 0x39 },
2275 { 0x22, 0x7A7, 0x9D },
2276 { 0x22, 0x7A8, 0xFE },
2277 { 0x22, 0x7A9, 0x39 },
2278 { 0x22, 0x7AA, 0x9D },
2279 { 0x22, 0x7AB, 0xFE },
2280 { 0x22, 0x7AC, 0x0C },
2281 { 0x22, 0x7AD, 0x80 },
2282 { 0x22, 0x7A6, 0x76 },
2283 { 0x22, 0x7A7, 0x49 },
2284 { 0x22, 0x7A8, 0x15 },
2285 { 0x22, 0x7A9, 0x76 },
2286 { 0x22, 0x7AA, 0x49 },
2287 { 0x22, 0x7AB, 0x15 },
2288 { 0x22, 0x7AC, 0x0D },
2289 { 0x22, 0x7AD, 0x80 },
2290 { 0x22, 0x7A6, 0xC8 },
2291 { 0x22, 0x7A7, 0x80 },
2292 { 0x22, 0x7A8, 0xF5 },
2293 { 0x22, 0x7A9, 0xC8 },
2294 { 0x22, 0x7AA, 0x80 },
2295 { 0x22, 0x7AB, 0xF5 },
2296 { 0x22, 0x7AC, 0x0E },
2297 { 0x22, 0x7AD, 0x80 },
2298 { 0x22, 0x7A6, 0x40 },
2299 { 0x22, 0x7A7, 0x00 },
2300 { 0x22, 0x7A8, 0x00 },
2301 { 0x22, 0x7A9, 0x40 },
2302 { 0x22, 0x7AA, 0x00 },
2303 { 0x22, 0x7AB, 0x00 },
2304 { 0x22, 0x7AC, 0x0F },
2305 { 0x22, 0x7AD, 0x80 },
2306 { 0x22, 0x7A6, 0x90 },
2307 { 0x22, 0x7A7, 0x68 },
2308 { 0x22, 0x7A8, 0xF1 },
2309 { 0x22, 0x7A9, 0x90 },
2310 { 0x22, 0x7AA, 0x68 },
2311 { 0x22, 0x7AB, 0xF1 },
2312 { 0x22, 0x7AC, 0x10 },
2313 { 0x22, 0x7AD, 0x80 },
2314 { 0x22, 0x7A6, 0x34 },
2315 { 0x22, 0x7A7, 0x47 },
2316 { 0x22, 0x7A8, 0x6C },
2317 { 0x22, 0x7A9, 0x34 },
2318 { 0x22, 0x7AA, 0x47 },
2319 { 0x22, 0x7AB, 0x6C },
2320 { 0x22, 0x7AC, 0x11 },
2321 { 0x22, 0x7AD, 0x80 },
2322 { 0x22, 0x7A6, 0x6F },
2323 { 0x22, 0x7A7, 0x97 },
2324 { 0x22, 0x7A8, 0x0F },
2325 { 0x22, 0x7A9, 0x6F },
2326 { 0x22, 0x7AA, 0x97 },
2327 { 0x22, 0x7AB, 0x0F },
2328 { 0x22, 0x7AC, 0x12 },
2329 { 0x22, 0x7AD, 0x80 },
2330 { 0x22, 0x7A6, 0xCB },
2331 { 0x22, 0x7A7, 0xB8 },
2332 { 0x22, 0x7A8, 0x94 },
2333 { 0x22, 0x7A9, 0xCB },
2334 { 0x22, 0x7AA, 0xB8 },
2335 { 0x22, 0x7AB, 0x94 },
2336 { 0x22, 0x7AC, 0x13 },
2337 { 0x22, 0x7AD, 0x80 },
2338 { 0x22, 0x7A6, 0x40 },
2339 { 0x22, 0x7A7, 0x00 },
2340 { 0x22, 0x7A8, 0x00 },
2341 { 0x22, 0x7A9, 0x40 },
2342 { 0x22, 0x7AA, 0x00 },
2343 { 0x22, 0x7AB, 0x00 },
2344 { 0x22, 0x7AC, 0x14 },
2345 { 0x22, 0x7AD, 0x80 },
2346 { 0x22, 0x7A6, 0x95 },
2347 { 0x22, 0x7A7, 0x76 },
2348 { 0x22, 0x7A8, 0x5B },
2349 { 0x22, 0x7A9, 0x95 },
2350 { 0x22, 0x7AA, 0x76 },
2351 { 0x22, 0x7AB, 0x5B },
2352 { 0x22, 0x7AC, 0x15 },
2353 { 0x22, 0x7AD, 0x80 },
2354 { 0x22, 0x7A6, 0x31 },
2355 { 0x22, 0x7A7, 0xAC },
2356 { 0x22, 0x7A8, 0x31 },
2357 { 0x22, 0x7A9, 0x31 },
2358 { 0x22, 0x7AA, 0xAC },
2359 { 0x22, 0x7AB, 0x31 },
2360 { 0x22, 0x7AC, 0x16 },
2361 { 0x22, 0x7AD, 0x80 },
2362 { 0x22, 0x7A6, 0x6A },
2363 { 0x22, 0x7A7, 0x89 },
2364 { 0x22, 0x7A8, 0xA5 },
2365 { 0x22, 0x7A9, 0x6A },
2366 { 0x22, 0x7AA, 0x89 },
2367 { 0x22, 0x7AB, 0xA5 },
2368 { 0x22, 0x7AC, 0x17 },
2369 { 0x22, 0x7AD, 0x80 },
2370 { 0x22, 0x7A6, 0xCE },
2371 { 0x22, 0x7A7, 0x53 },
2372 { 0x22, 0x7A8, 0xCF },
2373 { 0x22, 0x7A9, 0xCE },
2374 { 0x22, 0x7AA, 0x53 },
2375 { 0x22, 0x7AB, 0xCF },
2376 { 0x22, 0x7AC, 0x18 },
2377 { 0x22, 0x7AD, 0x80 },
2378 { 0x22, 0x7A6, 0x40 },
2379 { 0x22, 0x7A7, 0x00 },
2380 { 0x22, 0x7A8, 0x00 },
2381 { 0x22, 0x7A9, 0x40 },
2382 { 0x22, 0x7AA, 0x00 },
2383 { 0x22, 0x7AB, 0x00 },
2384 { 0x22, 0x7AC, 0x19 },
2385 { 0x22, 0x7AD, 0x80 },
2386 /* 48KHz base */
2387 { 0x22, 0x7A6, 0x3E },
2388 { 0x22, 0x7A7, 0x88 },
2389 { 0x22, 0x7A8, 0xDC },
2390 { 0x22, 0x7A9, 0x3E },
2391 { 0x22, 0x7AA, 0x88 },
2392 { 0x22, 0x7AB, 0xDC },
2393 { 0x22, 0x7AC, 0x1A },
2394 { 0x22, 0x7AD, 0x80 },
2395 { 0x22, 0x7A6, 0x82 },
2396 { 0x22, 0x7A7, 0xEE },
2397 { 0x22, 0x7A8, 0x46 },
2398 { 0x22, 0x7A9, 0x82 },
2399 { 0x22, 0x7AA, 0xEE },
2400 { 0x22, 0x7AB, 0x46 },
2401 { 0x22, 0x7AC, 0x1B },
2402 { 0x22, 0x7AD, 0x80 },
2403 { 0x22, 0x7A6, 0x3E },
2404 { 0x22, 0x7A7, 0x88 },
2405 { 0x22, 0x7A8, 0xDC },
2406 { 0x22, 0x7A9, 0x3E },
2407 { 0x22, 0x7AA, 0x88 },
2408 { 0x22, 0x7AB, 0xDC },
2409 { 0x22, 0x7AC, 0x1C },
2410 { 0x22, 0x7AD, 0x80 },
2411 { 0x22, 0x7A6, 0x7D },
2412 { 0x22, 0x7A7, 0x09 },
2413 { 0x22, 0x7A8, 0x28 },
2414 { 0x22, 0x7A9, 0x7D },
2415 { 0x22, 0x7AA, 0x09 },
2416 { 0x22, 0x7AB, 0x28 },
2417 { 0x22, 0x7AC, 0x1D },
2418 { 0x22, 0x7AD, 0x80 },
2419 { 0x22, 0x7A6, 0xC2 },
2420 { 0x22, 0x7A7, 0xE5 },
2421 { 0x22, 0x7A8, 0xB4 },
2422 { 0x22, 0x7A9, 0xC2 },
2423 { 0x22, 0x7AA, 0xE5 },
2424 { 0x22, 0x7AB, 0xB4 },
2425 { 0x22, 0x7AC, 0x1E },
2426 { 0x22, 0x7AD, 0x80 },
2427 { 0x22, 0x7A6, 0x3E },
2428 { 0x22, 0x7A7, 0xA3 },
2429 { 0x22, 0x7A8, 0x1F },
2430 { 0x22, 0x7A9, 0x3E },
2431 { 0x22, 0x7AA, 0xA3 },
2432 { 0x22, 0x7AB, 0x1F },
2433 { 0x22, 0x7AC, 0x1F },
2434 { 0x22, 0x7AD, 0x80 },
2435 { 0x22, 0x7A6, 0x84 },
2436 { 0x22, 0x7A7, 0xCA },
2437 { 0x22, 0x7A8, 0xF1 },
2438 { 0x22, 0x7A9, 0x84 },
2439 { 0x22, 0x7AA, 0xCA },
2440 { 0x22, 0x7AB, 0xF1 },
2441 { 0x22, 0x7AC, 0x20 },
2442 { 0x22, 0x7AD, 0x80 },
2443 { 0x22, 0x7A6, 0x3C },
2444 { 0x22, 0x7A7, 0xD5 },
2445 { 0x22, 0x7A8, 0x9C },
2446 { 0x22, 0x7A9, 0x3C },
2447 { 0x22, 0x7AA, 0xD5 },
2448 { 0x22, 0x7AB, 0x9C },
2449 { 0x22, 0x7AC, 0x21 },
2450 { 0x22, 0x7AD, 0x80 },
2451 { 0x22, 0x7A6, 0x7B },
2452 { 0x22, 0x7A7, 0x35 },
2453 { 0x22, 0x7A8, 0x0F },
2454 { 0x22, 0x7A9, 0x7B },
2455 { 0x22, 0x7AA, 0x35 },
2456 { 0x22, 0x7AB, 0x0F },
2457 { 0x22, 0x7AC, 0x22 },
2458 { 0x22, 0x7AD, 0x80 },
2459 { 0x22, 0x7A6, 0xC4 },
2460 { 0x22, 0x7A7, 0x87 },
2461 { 0x22, 0x7A8, 0x45 },
2462 { 0x22, 0x7A9, 0xC4 },
2463 { 0x22, 0x7AA, 0x87 },
2464 { 0x22, 0x7AB, 0x45 },
2465 { 0x22, 0x7AC, 0x23 },
2466 { 0x22, 0x7AD, 0x80 },
2467 { 0x22, 0x7A6, 0x3E },
2468 { 0x22, 0x7A7, 0x0A },
2469 { 0x22, 0x7A8, 0x78 },
2470 { 0x22, 0x7A9, 0x3E },
2471 { 0x22, 0x7AA, 0x0A },
2472 { 0x22, 0x7AB, 0x78 },
2473 { 0x22, 0x7AC, 0x24 },
2474 { 0x22, 0x7AD, 0x80 },
2475 { 0x22, 0x7A6, 0x88 },
2476 { 0x22, 0x7A7, 0xE2 },
2477 { 0x22, 0x7A8, 0x05 },
2478 { 0x22, 0x7A9, 0x88 },
2479 { 0x22, 0x7AA, 0xE2 },
2480 { 0x22, 0x7AB, 0x05 },
2481 { 0x22, 0x7AC, 0x25 },
2482 { 0x22, 0x7AD, 0x80 },
2483 { 0x22, 0x7A6, 0x3A },
2484 { 0x22, 0x7A7, 0x1A },
2485 { 0x22, 0x7A8, 0xA3 },
2486 { 0x22, 0x7A9, 0x3A },
2487 { 0x22, 0x7AA, 0x1A },
2488 { 0x22, 0x7AB, 0xA3 },
2489 { 0x22, 0x7AC, 0x26 },
2490 { 0x22, 0x7AD, 0x80 },
2491 { 0x22, 0x7A6, 0x77 },
2492 { 0x22, 0x7A7, 0x1D },
2493 { 0x22, 0x7A8, 0xFB },
2494 { 0x22, 0x7A9, 0x77 },
2495 { 0x22, 0x7AA, 0x1D },
2496 { 0x22, 0x7AB, 0xFB },
2497 { 0x22, 0x7AC, 0x27 },
2498 { 0x22, 0x7AD, 0x80 },
2499 { 0x22, 0x7A6, 0xC7 },
2500 { 0x22, 0x7A7, 0xDA },
2501 { 0x22, 0x7A8, 0xE5 },
2502 { 0x22, 0x7A9, 0xC7 },
2503 { 0x22, 0x7AA, 0xDA },
2504 { 0x22, 0x7AB, 0xE5 },
2505 { 0x22, 0x7AC, 0x28 },
2506 { 0x22, 0x7AD, 0x80 },
2507 { 0x22, 0x7A6, 0x40 },
2508 { 0x22, 0x7A7, 0x00 },
2509 { 0x22, 0x7A8, 0x00 },
2510 { 0x22, 0x7A9, 0x40 },
2511 { 0x22, 0x7AA, 0x00 },
2512 { 0x22, 0x7AB, 0x00 },
2513 { 0x22, 0x7AC, 0x29 },
2514 { 0x22, 0x7AD, 0x80 },
2515 { 0x22, 0x7A6, 0x8E },
2516 { 0x22, 0x7A7, 0xD7 },
2517 { 0x22, 0x7A8, 0x22 },
2518 { 0x22, 0x7A9, 0x8E },
2519 { 0x22, 0x7AA, 0xD7 },
2520 { 0x22, 0x7AB, 0x22 },
2521 { 0x22, 0x7AC, 0x2A },
2522 { 0x22, 0x7AD, 0x80 },
2523 { 0x22, 0x7A6, 0x35 },
2524 { 0x22, 0x7A7, 0x26 },
2525 { 0x22, 0x7A8, 0xC6 },
2526 { 0x22, 0x7A9, 0x35 },
2527 { 0x22, 0x7AA, 0x26 },
2528 { 0x22, 0x7AB, 0xC6 },
2529 { 0x22, 0x7AC, 0x2B },
2530 { 0x22, 0x7AD, 0x80 },
2531 { 0x22, 0x7A6, 0x71 },
2532 { 0x22, 0x7A7, 0x28 },
2533 { 0x22, 0x7A8, 0xDE },
2534 { 0x22, 0x7A9, 0x71 },
2535 { 0x22, 0x7AA, 0x28 },
2536 { 0x22, 0x7AB, 0xDE },
2537 { 0x22, 0x7AC, 0x2C },
2538 { 0x22, 0x7AD, 0x80 },
2539 { 0x22, 0x7A6, 0xCA },
2540 { 0x22, 0x7A7, 0xD9 },
2541 { 0x22, 0x7A8, 0x3A },
2542 { 0x22, 0x7A9, 0xCA },
2543 { 0x22, 0x7AA, 0xD9 },
2544 { 0x22, 0x7AB, 0x3A },
2545 { 0x22, 0x7AC, 0x2D },
2546 { 0x22, 0x7AD, 0x80 },
2547 { 0x22, 0x7A6, 0x40 },
2548 { 0x22, 0x7A7, 0x00 },
2549 { 0x22, 0x7A8, 0x00 },
2550 { 0x22, 0x7A9, 0x40 },
2551 { 0x22, 0x7AA, 0x00 },
2552 { 0x22, 0x7AB, 0x00 },
2553 { 0x22, 0x7AC, 0x2E },
2554 { 0x22, 0x7AD, 0x80 },
2555 { 0x22, 0x7A6, 0x93 },
2556 { 0x22, 0x7A7, 0x5E },
2557 { 0x22, 0x7A8, 0xD8 },
2558 { 0x22, 0x7A9, 0x93 },
2559 { 0x22, 0x7AA, 0x5E },
2560 { 0x22, 0x7AB, 0xD8 },
2561 { 0x22, 0x7AC, 0x2F },
2562 { 0x22, 0x7AD, 0x80 },
2563 { 0x22, 0x7A6, 0x32 },
2564 { 0x22, 0x7A7, 0xB7 },
2565 { 0x22, 0x7A8, 0xB1 },
2566 { 0x22, 0x7A9, 0x32 },
2567 { 0x22, 0x7AA, 0xB7 },
2568 { 0x22, 0x7AB, 0xB1 },
2569 { 0x22, 0x7AC, 0x30 },
2570 { 0x22, 0x7AD, 0x80 },
2571 { 0x22, 0x7A6, 0x6C },
2572 { 0x22, 0x7A7, 0xA1 },
2573 { 0x22, 0x7A8, 0x28 },
2574 { 0x22, 0x7A9, 0x6C },
2575 { 0x22, 0x7AA, 0xA1 },
2576 { 0x22, 0x7AB, 0x28 },
2577 { 0x22, 0x7AC, 0x31 },
2578 { 0x22, 0x7AD, 0x80 },
2579 { 0x22, 0x7A6, 0xCD },
2580 { 0x22, 0x7A7, 0x48 },
2581 { 0x22, 0x7A8, 0x4F },
2582 { 0x22, 0x7A9, 0xCD },
2583 { 0x22, 0x7AA, 0x48 },
2584 { 0x22, 0x7AB, 0x4F },
2585 { 0x22, 0x7AC, 0x32 },
2586 { 0x22, 0x7AD, 0x80 },
2587 { 0x22, 0x7A6, 0x40 },
2588 { 0x22, 0x7A7, 0x00 },
2589 { 0x22, 0x7A8, 0x00 },
2590 { 0x22, 0x7A9, 0x40 },
2591 { 0x22, 0x7AA, 0x00 },
2592 { 0x22, 0x7AB, 0x00 },
2593 { 0x22, 0x7AC, 0x33 },
2594 { 0x22, 0x7AD, 0x80 },
2595 /* common */
2596 { 0x22, 0x782, 0xC1 },
2597 { 0x22, 0x771, 0x2C },
2598 { 0x22, 0x772, 0x2C },
2599 { 0x22, 0x788, 0x04 },
2600 { 0x01, 0x7B0, 0x08 },
2601 {}
2602};
2603
372f8c75
TI
2604static const struct hda_fixup stac92hd83xxx_fixups[] = {
2605 [STAC_92HD83XXX_REF] = {
2606 .type = HDA_FIXUP_PINS,
2607 .v.pins = ref92hd83xxx_pin_configs,
2608 },
2609 [STAC_92HD83XXX_PWR_REF] = {
2610 .type = HDA_FIXUP_PINS,
2611 .v.pins = ref92hd83xxx_pin_configs,
2612 },
2613 [STAC_DELL_S14] = {
2614 .type = HDA_FIXUP_PINS,
2615 .v.pins = dell_s14_pin_configs,
2616 },
2617 [STAC_DELL_VOSTRO_3500] = {
2618 .type = HDA_FIXUP_PINS,
2619 .v.pins = dell_vostro_3500_pin_configs,
2620 },
2621 [STAC_92HD83XXX_HP_cNB11_INTQUAD] = {
2622 .type = HDA_FIXUP_PINS,
2623 .v.pins = hp_cNB11_intquad_pin_configs,
2624 .chained = true,
2625 .chain_id = STAC_92HD83XXX_HP,
2626 },
2627 [STAC_92HD83XXX_HP] = {
2628 .type = HDA_FIXUP_FUNC,
2629 .v.func = stac92hd83xxx_fixup_hp,
2630 },
2631 [STAC_HP_DV7_4000] = {
2632 .type = HDA_FIXUP_PINS,
2633 .v.pins = hp_dv7_4000_pin_configs,
2634 .chained = true,
2635 .chain_id = STAC_92HD83XXX_HP,
2636 },
2637 [STAC_HP_ZEPHYR] = {
2638 .type = HDA_FIXUP_FUNC,
2639 .v.func = stac92hd83xxx_fixup_hp_zephyr,
2640 .chained = true,
2641 .chain_id = STAC_92HD83XXX_HP,
2642 },
2643 [STAC_92HD83XXX_HP_LED] = {
2644 .type = HDA_FIXUP_FUNC,
2645 .v.func = stac92hd83xxx_fixup_hp_led,
2646 .chained = true,
2647 .chain_id = STAC_92HD83XXX_HP,
2648 },
2649 [STAC_92HD83XXX_HP_INV_LED] = {
2650 .type = HDA_FIXUP_FUNC,
2651 .v.func = stac92hd83xxx_fixup_hp_inv_led,
2652 .chained = true,
2653 .chain_id = STAC_92HD83XXX_HP,
2654 },
2655 [STAC_92HD83XXX_HP_MIC_LED] = {
2656 .type = HDA_FIXUP_FUNC,
2657 .v.func = stac92hd83xxx_fixup_hp_mic_led,
2658 .chained = true,
2659 .chain_id = STAC_92HD83XXX_HP,
2660 },
37c367ec
TI
2661 [STAC_HP_LED_GPIO10] = {
2662 .type = HDA_FIXUP_FUNC,
2663 .v.func = stac92hd83xxx_fixup_hp_led_gpio10,
2664 .chained = true,
2665 .chain_id = STAC_92HD83XXX_HP,
2666 },
372f8c75
TI
2667 [STAC_92HD83XXX_HEADSET_JACK] = {
2668 .type = HDA_FIXUP_FUNC,
2669 .v.func = stac92hd83xxx_fixup_headset_jack,
2670 },
49920427
TI
2671 [STAC_HP_ENVY_BASS] = {
2672 .type = HDA_FIXUP_PINS,
2673 .v.pins = (const struct hda_pintbl[]) {
2674 { 0x0f, 0x90170111 },
2675 {}
2676 },
2677 },
d009f3de
VK
2678 [STAC_HP_BNB13_EQ] = {
2679 .type = HDA_FIXUP_VERBS,
2680 .v.verbs = hp_bnb13_eq_verbs,
2681 .chained = true,
2682 .chain_id = STAC_92HD83XXX_HP_MIC_LED,
2683 },
8695a003
TI
2684 [STAC_HP_ENVY_TS_BASS] = {
2685 .type = HDA_FIXUP_PINS,
2686 .v.pins = (const struct hda_pintbl[]) {
2687 { 0x10, 0x92170111 },
2688 {}
2689 },
2690 },
d0513fc6
MR
2691};
2692
372f8c75
TI
2693static const struct hda_model_fixup stac92hd83xxx_models[] = {
2694 { .id = STAC_92HD83XXX_REF, .name = "ref" },
2695 { .id = STAC_92HD83XXX_PWR_REF, .name = "mic-ref" },
2696 { .id = STAC_DELL_S14, .name = "dell-s14" },
2697 { .id = STAC_DELL_VOSTRO_3500, .name = "dell-vostro-3500" },
2698 { .id = STAC_92HD83XXX_HP_cNB11_INTQUAD, .name = "hp_cNB11_intquad" },
2699 { .id = STAC_HP_DV7_4000, .name = "hp-dv7-4000" },
2700 { .id = STAC_HP_ZEPHYR, .name = "hp-zephyr" },
2701 { .id = STAC_92HD83XXX_HP_LED, .name = "hp-led" },
2702 { .id = STAC_92HD83XXX_HP_INV_LED, .name = "hp-inv-led" },
2703 { .id = STAC_92HD83XXX_HP_MIC_LED, .name = "hp-mic-led" },
2704 { .id = STAC_92HD83XXX_HEADSET_JACK, .name = "headset-jack" },
49920427 2705 { .id = STAC_HP_ENVY_BASS, .name = "hp-envy-bass" },
d009f3de 2706 { .id = STAC_HP_BNB13_EQ, .name = "hp-bnb13-eq" },
8695a003 2707 { .id = STAC_HP_ENVY_TS_BASS, .name = "hp-envy-ts-bass" },
372f8c75 2708 {}
d0513fc6
MR
2709};
2710
372f8c75 2711static const struct snd_pci_quirk stac92hd83xxx_fixup_tbl[] = {
d0513fc6
MR
2712 /* SigmaTel reference board */
2713 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
f9d088b2 2714 "DFI LanParty", STAC_92HD83XXX_REF),
577aa2c1
MR
2715 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
2716 "DFI LanParty", STAC_92HD83XXX_REF),
8bb0ac55
MR
2717 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02ba,
2718 "unknown Dell", STAC_DELL_S14),
8d032a8f
DH
2719 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0532,
2720 "Dell Latitude E6230", STAC_92HD83XXX_HEADSET_JACK),
2721 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0533,
2722 "Dell Latitude E6330", STAC_92HD83XXX_HEADSET_JACK),
2723 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0534,
2724 "Dell Latitude E6430", STAC_92HD83XXX_HEADSET_JACK),
2725 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0535,
2726 "Dell Latitude E6530", STAC_92HD83XXX_HEADSET_JACK),
2727 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x053c,
2728 "Dell Latitude E5430", STAC_92HD83XXX_HEADSET_JACK),
2729 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x053d,
2730 "Dell Latitude E5530", STAC_92HD83XXX_HEADSET_JACK),
2731 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0549,
2732 "Dell Latitude E5430", STAC_92HD83XXX_HEADSET_JACK),
2733 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x057d,
2734 "Dell Latitude E6430s", STAC_92HD83XXX_HEADSET_JACK),
2735 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0584,
2736 "Dell Latitude E6430U", STAC_92HD83XXX_HEADSET_JACK),
f7f9bdfa
JW
2737 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x1028,
2738 "Dell Vostro 3500", STAC_DELL_VOSTRO_3500),
0c27c180
VK
2739 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1656,
2740 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2741 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1657,
2742 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2743 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1658,
2744 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2745 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1659,
8ae5865e 2746 "HP Pavilion dv7", STAC_HP_DV7_4000),
0c27c180
VK
2747 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x165A,
2748 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2749 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x165B,
2750 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
49920427
TI
2751 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1888,
2752 "HP Envy Spectre", STAC_HP_ENVY_BASS),
37c367ec
TI
2753 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1899,
2754 "HP Folio 13", STAC_HP_LED_GPIO10),
62cbde18 2755 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x18df,
d009f3de
VK
2756 "HP Folio", STAC_HP_BNB13_EQ),
2757 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x18F8,
2758 "HP bNB13", STAC_HP_BNB13_EQ),
2759 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1909,
2760 "HP bNB13", STAC_HP_BNB13_EQ),
2761 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x190A,
2762 "HP bNB13", STAC_HP_BNB13_EQ),
8695a003
TI
2763 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x190e,
2764 "HP ENVY TS", STAC_HP_ENVY_TS_BASS),
d009f3de
VK
2765 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1940,
2766 "HP bNB13", STAC_HP_BNB13_EQ),
2767 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1941,
2768 "HP bNB13", STAC_HP_BNB13_EQ),
2769 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1942,
2770 "HP bNB13", STAC_HP_BNB13_EQ),
2771 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1943,
2772 "HP bNB13", STAC_HP_BNB13_EQ),
2773 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1944,
2774 "HP bNB13", STAC_HP_BNB13_EQ),
2775 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1945,
2776 "HP bNB13", STAC_HP_BNB13_EQ),
2777 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1946,
2778 "HP bNB13", STAC_HP_BNB13_EQ),
2779 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1948,
2780 "HP bNB13", STAC_HP_BNB13_EQ),
2781 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1949,
2782 "HP bNB13", STAC_HP_BNB13_EQ),
2783 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x194A,
2784 "HP bNB13", STAC_HP_BNB13_EQ),
2785 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x194B,
2786 "HP bNB13", STAC_HP_BNB13_EQ),
2787 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x194C,
2788 "HP bNB13", STAC_HP_BNB13_EQ),
2789 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x194E,
2790 "HP bNB13", STAC_HP_BNB13_EQ),
2791 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x194F,
2792 "HP bNB13", STAC_HP_BNB13_EQ),
2793 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1950,
2794 "HP bNB13", STAC_HP_BNB13_EQ),
2795 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1951,
2796 "HP bNB13", STAC_HP_BNB13_EQ),
2797 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x195A,
2798 "HP bNB13", STAC_HP_BNB13_EQ),
2799 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x195B,
2800 "HP bNB13", STAC_HP_BNB13_EQ),
2801 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x195C,
2802 "HP bNB13", STAC_HP_BNB13_EQ),
2803 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1991,
2804 "HP bNB13", STAC_HP_BNB13_EQ),
2805 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2103,
2806 "HP bNB13", STAC_HP_BNB13_EQ),
2807 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2104,
2808 "HP bNB13", STAC_HP_BNB13_EQ),
2809 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2105,
2810 "HP bNB13", STAC_HP_BNB13_EQ),
2811 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2106,
2812 "HP bNB13", STAC_HP_BNB13_EQ),
2813 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2107,
2814 "HP bNB13", STAC_HP_BNB13_EQ),
2815 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2108,
2816 "HP bNB13", STAC_HP_BNB13_EQ),
2817 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2109,
2818 "HP bNB13", STAC_HP_BNB13_EQ),
2819 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x210A,
2820 "HP bNB13", STAC_HP_BNB13_EQ),
2821 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x210B,
2822 "HP bNB13", STAC_HP_BNB13_EQ),
2823 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x211C,
2824 "HP bNB13", STAC_HP_BNB13_EQ),
2825 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x211D,
2826 "HP bNB13", STAC_HP_BNB13_EQ),
2827 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x211E,
2828 "HP bNB13", STAC_HP_BNB13_EQ),
2829 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x211F,
2830 "HP bNB13", STAC_HP_BNB13_EQ),
2831 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2120,
2832 "HP bNB13", STAC_HP_BNB13_EQ),
2833 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2121,
2834 "HP bNB13", STAC_HP_BNB13_EQ),
2835 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2122,
2836 "HP bNB13", STAC_HP_BNB13_EQ),
2837 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2123,
2838 "HP bNB13", STAC_HP_BNB13_EQ),
2839 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x213E,
2840 "HP bNB13", STAC_HP_BNB13_EQ),
2841 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x213F,
2842 "HP bNB13", STAC_HP_BNB13_EQ),
2843 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x2140,
2844 "HP bNB13", STAC_HP_BNB13_EQ),
2845 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x21B2,
2846 "HP bNB13", STAC_HP_BNB13_EQ),
2847 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x21B3,
2848 "HP bNB13", STAC_HP_BNB13_EQ),
2849 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x21B5,
2850 "HP bNB13", STAC_HP_BNB13_EQ),
2851 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x21B6,
2852 "HP bNB13", STAC_HP_BNB13_EQ),
f9afed1f
TI
2853 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xff00, 0x1900,
2854 "HP", STAC_92HD83XXX_HP_MIC_LED),
4059a42c
TI
2855 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xff00, 0x2000,
2856 "HP", STAC_92HD83XXX_HP_MIC_LED),
2857 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xff00, 0x2100,
2858 "HP", STAC_92HD83XXX_HP_MIC_LED),
0c27c180
VK
2859 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3388,
2860 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2861 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3389,
2862 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2863 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x355B,
2864 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2865 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x355C,
2866 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2867 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x355D,
2868 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2869 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x355E,
2870 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2871 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x355F,
2872 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2873 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3560,
2874 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2875 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x358B,
2876 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2877 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x358C,
2878 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2879 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x358D,
2880 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2881 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3591,
2882 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2883 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3592,
2884 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
2885 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3593,
2886 "HP", STAC_92HD83XXX_HP_cNB11_INTQUAD),
5556e147
VK
2887 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3561,
2888 "HP", STAC_HP_ZEPHYR),
a3e19973
TI
2889 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3660,
2890 "HP Mini", STAC_92HD83XXX_HP_LED),
5afc13af
GMDV
2891 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x144E,
2892 "HP Pavilion dv5", STAC_92HD83XXX_HP_INV_LED),
8c698fe2
TI
2893 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x148a,
2894 "HP Mini", STAC_92HD83XXX_HP_LED),
372f8c75 2895 SND_PCI_QUIRK_VENDOR(PCI_VENDOR_ID_HP, "HP", STAC_92HD83XXX_HP),
574f3c4f 2896 {} /* terminator */
d0513fc6
MR
2897};
2898
36c9db7a
TI
2899/* HP dv7 bass switch - GPIO5 */
2900#define stac_hp_bass_gpio_info snd_ctl_boolean_mono_info
2901static int stac_hp_bass_gpio_get(struct snd_kcontrol *kcontrol,
2902 struct snd_ctl_elem_value *ucontrol)
2903{
2904 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2905 struct sigmatel_spec *spec = codec->spec;
2906 ucontrol->value.integer.value[0] = !!(spec->gpio_data & 0x20);
2907 return 0;
2908}
2909
2910static int stac_hp_bass_gpio_put(struct snd_kcontrol *kcontrol,
2911 struct snd_ctl_elem_value *ucontrol)
2912{
2913 struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
2914 struct sigmatel_spec *spec = codec->spec;
2915 unsigned int gpio_data;
2916
2917 gpio_data = (spec->gpio_data & ~0x20) |
2918 (ucontrol->value.integer.value[0] ? 0x20 : 0);
2919 if (gpio_data == spec->gpio_data)
2920 return 0;
2921 spec->gpio_data = gpio_data;
2922 stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir, spec->gpio_data);
2923 return 1;
2924}
2925
2926static const struct snd_kcontrol_new stac_hp_bass_sw_ctrl = {
2927 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
2928 .info = stac_hp_bass_gpio_info,
2929 .get = stac_hp_bass_gpio_get,
2930 .put = stac_hp_bass_gpio_put,
2931};
2932
2933static int stac_add_hp_bass_switch(struct hda_codec *codec)
2934{
2935 struct sigmatel_spec *spec = codec->spec;
2936
2937 if (!snd_hda_gen_add_kctl(&spec->gen, "Bass Speaker Playback Switch",
2938 &stac_hp_bass_sw_ctrl))
2939 return -ENOMEM;
2940
2941 spec->gpio_mask |= 0x20;
2942 spec->gpio_dir |= 0x20;
2943 spec->gpio_data |= 0x20;
2944 return 0;
2945}
2946
0f6fcb73
TI
2947static const struct hda_pintbl ref92hd71bxx_pin_configs[] = {
2948 { 0x0a, 0x02214030 },
2949 { 0x0b, 0x02a19040 },
2950 { 0x0c, 0x01a19020 },
2951 { 0x0d, 0x01014010 },
2952 { 0x0e, 0x0181302e },
2953 { 0x0f, 0x01014010 },
2954 { 0x14, 0x01019020 },
2955 { 0x18, 0x90a000f0 },
2956 { 0x19, 0x90a000f0 },
2957 { 0x1e, 0x01452050 },
2958 { 0x1f, 0x01452050 },
2959 {}
e035b841
MR
2960};
2961
0f6fcb73
TI
2962static const struct hda_pintbl dell_m4_1_pin_configs[] = {
2963 { 0x0a, 0x0421101f },
2964 { 0x0b, 0x04a11221 },
2965 { 0x0c, 0x40f000f0 },
2966 { 0x0d, 0x90170110 },
2967 { 0x0e, 0x23a1902e },
2968 { 0x0f, 0x23014250 },
2969 { 0x14, 0x40f000f0 },
2970 { 0x18, 0x90a000f0 },
2971 { 0x19, 0x40f000f0 },
2972 { 0x1e, 0x4f0000f0 },
2973 { 0x1f, 0x4f0000f0 },
2974 {}
a7662640
MR
2975};
2976
0f6fcb73
TI
2977static const struct hda_pintbl dell_m4_2_pin_configs[] = {
2978 { 0x0a, 0x0421101f },
2979 { 0x0b, 0x04a11221 },
2980 { 0x0c, 0x90a70330 },
2981 { 0x0d, 0x90170110 },
2982 { 0x0e, 0x23a1902e },
2983 { 0x0f, 0x23014250 },
2984 { 0x14, 0x40f000f0 },
2985 { 0x18, 0x40f000f0 },
2986 { 0x19, 0x40f000f0 },
2987 { 0x1e, 0x044413b0 },
2988 { 0x1f, 0x044413b0 },
2989 {}
a7662640
MR
2990};
2991
0f6fcb73
TI
2992static const struct hda_pintbl dell_m4_3_pin_configs[] = {
2993 { 0x0a, 0x0421101f },
2994 { 0x0b, 0x04a11221 },
2995 { 0x0c, 0x90a70330 },
2996 { 0x0d, 0x90170110 },
2997 { 0x0e, 0x40f000f0 },
2998 { 0x0f, 0x40f000f0 },
2999 { 0x14, 0x40f000f0 },
3000 { 0x18, 0x90a000f0 },
3001 { 0x19, 0x40f000f0 },
3002 { 0x1e, 0x044413b0 },
3003 { 0x1f, 0x044413b0 },
3004 {}
3a7abfd2
MR
3005};
3006
0f6fcb73
TI
3007static void stac92hd71bxx_fixup_ref(struct hda_codec *codec,
3008 const struct hda_fixup *fix, int action)
3009{
3010 struct sigmatel_spec *spec = codec->spec;
3011
3012 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3013 return;
3014
3015 snd_hda_apply_pincfgs(codec, ref92hd71bxx_pin_configs);
3016 spec->gpio_mask = spec->gpio_dir = spec->gpio_data = 0;
3017}
3018
0f6fcb73
TI
3019static void stac92hd71bxx_fixup_hp_m4(struct hda_codec *codec,
3020 const struct hda_fixup *fix, int action)
3021{
3022 struct sigmatel_spec *spec = codec->spec;
36c9db7a 3023 struct hda_jack_tbl *jack;
0f6fcb73
TI
3024
3025 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3026 return;
3027
3028 /* Enable VREF power saving on GPIO1 detect */
0f6fcb73
TI
3029 snd_hda_codec_write_cache(codec, codec->afg, 0,
3030 AC_VERB_SET_GPIO_UNSOLICITED_RSP_MASK, 0x02);
36c9db7a
TI
3031 snd_hda_jack_detect_enable_callback(codec, codec->afg,
3032 STAC_VREF_EVENT,
3033 stac_vref_event);
3034 jack = snd_hda_jack_tbl_get(codec, codec->afg);
3035 if (jack)
3036 jack->private_data = 0x02;
3037
0f6fcb73
TI
3038 spec->gpio_mask |= 0x02;
3039
3040 /* enable internal microphone */
3041 snd_hda_codec_set_pincfg(codec, 0x0e, 0x01813040);
0f6fcb73
TI
3042}
3043
3044static void stac92hd71bxx_fixup_hp_dv4(struct hda_codec *codec,
3045 const struct hda_fixup *fix, int action)
3046{
3047 struct sigmatel_spec *spec = codec->spec;
3048
3049 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3050 return;
3051 spec->gpio_led = 0x01;
3052}
3053
3054static void stac92hd71bxx_fixup_hp_dv5(struct hda_codec *codec,
3055 const struct hda_fixup *fix, int action)
3056{
0f6fcb73
TI
3057 unsigned int cap;
3058
3059 switch (action) {
3060 case HDA_FIXUP_ACT_PRE_PROBE:
3061 snd_hda_codec_set_pincfg(codec, 0x0d, 0x90170010);
f6655d52
TI
3062 break;
3063
3064 case HDA_FIXUP_ACT_PROBE:
0f6fcb73
TI
3065 /* enable bass on HP dv7 */
3066 cap = snd_hda_param_read(codec, 0x1, AC_PAR_GPIO_CAP);
3067 cap &= AC_GPIO_IO_COUNT;
3068 if (cap >= 6)
3069 stac_add_hp_bass_switch(codec);
3070 break;
3071 }
3072}
3073
3074static void stac92hd71bxx_fixup_hp_hdx(struct hda_codec *codec,
3075 const struct hda_fixup *fix, int action)
3076{
3077 struct sigmatel_spec *spec = codec->spec;
3078
3079 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3080 return;
3081 spec->gpio_led = 0x08;
0f6fcb73
TI
3082}
3083
3084
3085static void stac92hd71bxx_fixup_hp(struct hda_codec *codec,
3086 const struct hda_fixup *fix, int action)
3087{
3088 struct sigmatel_spec *spec = codec->spec;
3089
3090 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3091 return;
3092
3093 if (hp_blike_system(codec->subsystem_id)) {
3094 unsigned int pin_cfg = snd_hda_codec_get_pincfg(codec, 0x0f);
3095 if (get_defcfg_device(pin_cfg) == AC_JACK_LINE_OUT ||
3096 get_defcfg_device(pin_cfg) == AC_JACK_SPEAKER ||
3097 get_defcfg_device(pin_cfg) == AC_JACK_HP_OUT) {
3098 /* It was changed in the BIOS to just satisfy MS DTM.
3099 * Lets turn it back into slaved HP
3100 */
3101 pin_cfg = (pin_cfg & (~AC_DEFCFG_DEVICE))
3102 | (AC_JACK_HP_OUT <<
3103 AC_DEFCFG_DEVICE_SHIFT);
3104 pin_cfg = (pin_cfg & (~(AC_DEFCFG_DEF_ASSOC
3105 | AC_DEFCFG_SEQUENCE)))
3106 | 0x1f;
3107 snd_hda_codec_set_pincfg(codec, 0x0f, pin_cfg);
3108 }
3109 }
3110
36c9db7a 3111 if (find_mute_led_cfg(codec, 1))
4e76a883 3112 codec_dbg(codec, "mute LED gpio %d polarity %d\n",
0f6fcb73
TI
3113 spec->gpio_led,
3114 spec->gpio_led_polarity);
3115
3116}
3117
3118static const struct hda_fixup stac92hd71bxx_fixups[] = {
3119 [STAC_92HD71BXX_REF] = {
3120 .type = HDA_FIXUP_FUNC,
3121 .v.func = stac92hd71bxx_fixup_ref,
3122 },
3123 [STAC_DELL_M4_1] = {
3124 .type = HDA_FIXUP_PINS,
3125 .v.pins = dell_m4_1_pin_configs,
0f6fcb73
TI
3126 },
3127 [STAC_DELL_M4_2] = {
3128 .type = HDA_FIXUP_PINS,
3129 .v.pins = dell_m4_2_pin_configs,
0f6fcb73
TI
3130 },
3131 [STAC_DELL_M4_3] = {
3132 .type = HDA_FIXUP_PINS,
3133 .v.pins = dell_m4_3_pin_configs,
0f6fcb73
TI
3134 },
3135 [STAC_HP_M4] = {
3136 .type = HDA_FIXUP_FUNC,
3137 .v.func = stac92hd71bxx_fixup_hp_m4,
3138 .chained = true,
3139 .chain_id = STAC_92HD71BXX_HP,
3140 },
3141 [STAC_HP_DV4] = {
3142 .type = HDA_FIXUP_FUNC,
3143 .v.func = stac92hd71bxx_fixup_hp_dv4,
3144 .chained = true,
3145 .chain_id = STAC_HP_DV5,
3146 },
3147 [STAC_HP_DV5] = {
3148 .type = HDA_FIXUP_FUNC,
3149 .v.func = stac92hd71bxx_fixup_hp_dv5,
3150 .chained = true,
3151 .chain_id = STAC_92HD71BXX_HP,
3152 },
3153 [STAC_HP_HDX] = {
3154 .type = HDA_FIXUP_FUNC,
3155 .v.func = stac92hd71bxx_fixup_hp_hdx,
3156 .chained = true,
3157 .chain_id = STAC_92HD71BXX_HP,
3158 },
36c9db7a 3159 [STAC_92HD71BXX_HP] = {
0f6fcb73 3160 .type = HDA_FIXUP_FUNC,
36c9db7a 3161 .v.func = stac92hd71bxx_fixup_hp,
0f6fcb73 3162 },
e035b841
MR
3163};
3164
0f6fcb73
TI
3165static const struct hda_model_fixup stac92hd71bxx_models[] = {
3166 { .id = STAC_92HD71BXX_REF, .name = "ref" },
3167 { .id = STAC_DELL_M4_1, .name = "dell-m4-1" },
3168 { .id = STAC_DELL_M4_2, .name = "dell-m4-2" },
3169 { .id = STAC_DELL_M4_3, .name = "dell-m4-3" },
3170 { .id = STAC_HP_M4, .name = "hp-m4" },
3171 { .id = STAC_HP_DV4, .name = "hp-dv4" },
3172 { .id = STAC_HP_DV5, .name = "hp-dv5" },
3173 { .id = STAC_HP_HDX, .name = "hp-hdx" },
36c9db7a 3174 { .id = STAC_HP_DV4, .name = "hp-dv4-1222nr" },
0f6fcb73 3175 {}
e035b841
MR
3176};
3177
0f6fcb73 3178static const struct snd_pci_quirk stac92hd71bxx_fixup_tbl[] = {
e035b841
MR
3179 /* SigmaTel reference board */
3180 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
3181 "DFI LanParty", STAC_92HD71BXX_REF),
577aa2c1
MR
3182 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
3183 "DFI LanParty", STAC_92HD71BXX_REF),
5bdaaada
VK
3184 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x1720,
3185 "HP", STAC_HP_DV5),
58d8395b
TI
3186 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x3080,
3187 "HP", STAC_HP_DV5),
2ae466f8 3188 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x30f0,
2a6ce6e5 3189 "HP dv4-7", STAC_HP_DV4),
2ae466f8
TI
3190 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x3600,
3191 "HP dv4-7", STAC_HP_DV5),
6fce61ae
TI
3192 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3610,
3193 "HP HDX", STAC_HP_HDX), /* HDX18 */
9a9e2359 3194 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x361a,
2ae466f8 3195 "HP mini 1000", STAC_HP_M4),
ae6241fb 3196 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x361b,
6fce61ae 3197 "HP HDX", STAC_HP_HDX), /* HDX16 */
6e34c033
TI
3198 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x3620,
3199 "HP dv6", STAC_HP_DV5),
e3d2530a
KG
3200 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x3061,
3201 "HP dv6", STAC_HP_DV5), /* HP dv6-1110ax */
9b2167d5
LY
3202 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x363e,
3203 "HP DV6", STAC_HP_DV5),
1972d025
TI
3204 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x7010,
3205 "HP", STAC_HP_DV5),
0f6fcb73 3206 SND_PCI_QUIRK_VENDOR(PCI_VENDOR_ID_HP, "HP", STAC_92HD71BXX_HP),
a7662640
MR
3207 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0233,
3208 "unknown Dell", STAC_DELL_M4_1),
3209 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0234,
3210 "unknown Dell", STAC_DELL_M4_1),
3211 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0250,
3212 "unknown Dell", STAC_DELL_M4_1),
3213 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x024f,
3214 "unknown Dell", STAC_DELL_M4_1),
3215 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x024d,
3216 "unknown Dell", STAC_DELL_M4_1),
3217 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0251,
3218 "unknown Dell", STAC_DELL_M4_1),
3219 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0277,
3220 "unknown Dell", STAC_DELL_M4_1),
3221 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0263,
3222 "unknown Dell", STAC_DELL_M4_2),
3223 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0265,
3224 "unknown Dell", STAC_DELL_M4_2),
3225 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0262,
3226 "unknown Dell", STAC_DELL_M4_2),
3227 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0264,
3228 "unknown Dell", STAC_DELL_M4_2),
3a7abfd2
MR
3229 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02aa,
3230 "unknown Dell", STAC_DELL_M4_3),
e035b841
MR
3231 {} /* terminator */
3232};
3233
0a427846
TI
3234static const struct hda_pintbl ref922x_pin_configs[] = {
3235 { 0x0a, 0x01014010 },
3236 { 0x0b, 0x01016011 },
3237 { 0x0c, 0x01012012 },
3238 { 0x0d, 0x0221401f },
3239 { 0x0e, 0x01813122 },
3240 { 0x0f, 0x01011014 },
3241 { 0x10, 0x01441030 },
3242 { 0x11, 0x01c41030 },
3243 { 0x15, 0x40000100 },
3244 { 0x1b, 0x40000100 },
3245 {}
2f2f4251
M
3246};
3247
dfe495d0
TI
3248/*
3249 STAC 922X pin configs for
3250 102801A7
3251 102801AB
3252 102801A9
3253 102801D1
3254 102801D2
3255*/
0a427846
TI
3256static const struct hda_pintbl dell_922x_d81_pin_configs[] = {
3257 { 0x0a, 0x02214030 },
3258 { 0x0b, 0x01a19021 },
3259 { 0x0c, 0x01111012 },
3260 { 0x0d, 0x01114010 },
3261 { 0x0e, 0x02a19020 },
3262 { 0x0f, 0x01117011 },
3263 { 0x10, 0x400001f0 },
3264 { 0x11, 0x400001f1 },
3265 { 0x15, 0x01813122 },
3266 { 0x1b, 0x400001f2 },
3267 {}
dfe495d0
TI
3268};
3269
3270/*
3271 STAC 922X pin configs for
3272 102801AC
3273 102801D0
3274*/
0a427846
TI
3275static const struct hda_pintbl dell_922x_d82_pin_configs[] = {
3276 { 0x0a, 0x02214030 },
3277 { 0x0b, 0x01a19021 },
3278 { 0x0c, 0x01111012 },
3279 { 0x0d, 0x01114010 },
3280 { 0x0e, 0x02a19020 },
3281 { 0x0f, 0x01117011 },
3282 { 0x10, 0x01451140 },
3283 { 0x11, 0x400001f0 },
3284 { 0x15, 0x01813122 },
3285 { 0x1b, 0x400001f1 },
3286 {}
dfe495d0
TI
3287};
3288
3289/*
3290 STAC 922X pin configs for
3291 102801BF
3292*/
0a427846
TI
3293static const struct hda_pintbl dell_922x_m81_pin_configs[] = {
3294 { 0x0a, 0x0321101f },
3295 { 0x0b, 0x01112024 },
3296 { 0x0c, 0x01111222 },
3297 { 0x0d, 0x91174220 },
3298 { 0x0e, 0x03a11050 },
3299 { 0x0f, 0x01116221 },
3300 { 0x10, 0x90a70330 },
3301 { 0x11, 0x01452340 },
3302 { 0x15, 0x40C003f1 },
3303 { 0x1b, 0x405003f0 },
3304 {}
dfe495d0
TI
3305};
3306
3307/*
3308 STAC 9221 A1 pin configs for
3309 102801D7 (Dell XPS M1210)
3310*/
0a427846
TI
3311static const struct hda_pintbl dell_922x_m82_pin_configs[] = {
3312 { 0x0a, 0x02211211 },
3313 { 0x0b, 0x408103ff },
3314 { 0x0c, 0x02a1123e },
3315 { 0x0d, 0x90100310 },
3316 { 0x0e, 0x408003f1 },
3317 { 0x0f, 0x0221121f },
3318 { 0x10, 0x03451340 },
3319 { 0x11, 0x40c003f2 },
3320 { 0x15, 0x508003f3 },
3321 { 0x1b, 0x405003f4 },
3322 {}
dfe495d0
TI
3323};
3324
0a427846
TI
3325static const struct hda_pintbl d945gtp3_pin_configs[] = {
3326 { 0x0a, 0x0221401f },
3327 { 0x0b, 0x01a19022 },
3328 { 0x0c, 0x01813021 },
3329 { 0x0d, 0x01014010 },
3330 { 0x0e, 0x40000100 },
3331 { 0x0f, 0x40000100 },
3332 { 0x10, 0x40000100 },
3333 { 0x11, 0x40000100 },
3334 { 0x15, 0x02a19120 },
3335 { 0x1b, 0x40000100 },
3336 {}
3337};
3338
3339static const struct hda_pintbl d945gtp5_pin_configs[] = {
3340 { 0x0a, 0x0221401f },
3341 { 0x0b, 0x01011012 },
3342 { 0x0c, 0x01813024 },
3343 { 0x0d, 0x01014010 },
3344 { 0x0e, 0x01a19021 },
3345 { 0x0f, 0x01016011 },
3346 { 0x10, 0x01452130 },
3347 { 0x11, 0x40000100 },
3348 { 0x15, 0x02a19320 },
3349 { 0x1b, 0x40000100 },
3350 {}
403d1944
MP
3351};
3352
0a427846
TI
3353static const struct hda_pintbl intel_mac_v1_pin_configs[] = {
3354 { 0x0a, 0x0121e21f },
3355 { 0x0b, 0x400000ff },
3356 { 0x0c, 0x9017e110 },
3357 { 0x0d, 0x400000fd },
3358 { 0x0e, 0x400000fe },
3359 { 0x0f, 0x0181e020 },
3360 { 0x10, 0x1145e030 },
3361 { 0x11, 0x11c5e240 },
3362 { 0x15, 0x400000fc },
3363 { 0x1b, 0x400000fb },
3364 {}
403d1944
MP
3365};
3366
0a427846
TI
3367static const struct hda_pintbl intel_mac_v2_pin_configs[] = {
3368 { 0x0a, 0x0121e21f },
3369 { 0x0b, 0x90a7012e },
3370 { 0x0c, 0x9017e110 },
3371 { 0x0d, 0x400000fd },
3372 { 0x0e, 0x400000fe },
3373 { 0x0f, 0x0181e020 },
3374 { 0x10, 0x1145e230 },
3375 { 0x11, 0x500000fa },
3376 { 0x15, 0x400000fc },
3377 { 0x1b, 0x400000fb },
3378 {}
5d5d3bc3
IZ
3379};
3380
0a427846
TI
3381static const struct hda_pintbl intel_mac_v3_pin_configs[] = {
3382 { 0x0a, 0x0121e21f },
3383 { 0x0b, 0x90a7012e },
3384 { 0x0c, 0x9017e110 },
3385 { 0x0d, 0x400000fd },
3386 { 0x0e, 0x400000fe },
3387 { 0x0f, 0x0181e020 },
3388 { 0x10, 0x1145e230 },
3389 { 0x11, 0x11c5e240 },
3390 { 0x15, 0x400000fc },
3391 { 0x1b, 0x400000fb },
3392 {}
6f0778d8
NB
3393};
3394
0a427846
TI
3395static const struct hda_pintbl intel_mac_v4_pin_configs[] = {
3396 { 0x0a, 0x0321e21f },
3397 { 0x0b, 0x03a1e02e },
3398 { 0x0c, 0x9017e110 },
3399 { 0x0d, 0x9017e11f },
3400 { 0x0e, 0x400000fe },
3401 { 0x0f, 0x0381e020 },
3402 { 0x10, 0x1345e230 },
3403 { 0x11, 0x13c5e240 },
3404 { 0x15, 0x400000fc },
3405 { 0x1b, 0x400000fb },
3406 {}
3fc24d85
TI
3407};
3408
0a427846
TI
3409static const struct hda_pintbl intel_mac_v5_pin_configs[] = {
3410 { 0x0a, 0x0321e21f },
3411 { 0x0b, 0x03a1e02e },
3412 { 0x0c, 0x9017e110 },
3413 { 0x0d, 0x9017e11f },
3414 { 0x0e, 0x400000fe },
3415 { 0x0f, 0x0381e020 },
3416 { 0x10, 0x1345e230 },
3417 { 0x11, 0x13c5e240 },
3418 { 0x15, 0x400000fc },
3419 { 0x1b, 0x400000fb },
3420 {}
f16928fb
SF
3421};
3422
0a427846
TI
3423static const struct hda_pintbl ecs202_pin_configs[] = {
3424 { 0x0a, 0x0221401f },
3425 { 0x0b, 0x02a19020 },
3426 { 0x0c, 0x01a19020 },
3427 { 0x0d, 0x01114010 },
3428 { 0x0e, 0x408000f0 },
3429 { 0x0f, 0x01813022 },
3430 { 0x10, 0x074510a0 },
3431 { 0x11, 0x40c400f1 },
3432 { 0x15, 0x9037012e },
3433 { 0x1b, 0x40e000f2 },
3434 {}
0dae0f83
TI
3435};
3436
0a427846
TI
3437/* codec SSIDs for Intel Mac sharing the same PCI SSID 8384:7680 */
3438static const struct snd_pci_quirk stac922x_intel_mac_fixup_tbl[] = {
697aebab 3439 SND_PCI_QUIRK(0x0000, 0x0100, "Mac Mini", STAC_INTEL_MAC_V3),
0a427846
TI
3440 SND_PCI_QUIRK(0x106b, 0x0800, "Mac", STAC_INTEL_MAC_V1),
3441 SND_PCI_QUIRK(0x106b, 0x0600, "Mac", STAC_INTEL_MAC_V2),
3442 SND_PCI_QUIRK(0x106b, 0x0700, "Mac", STAC_INTEL_MAC_V2),
3443 SND_PCI_QUIRK(0x106b, 0x0e00, "Mac", STAC_INTEL_MAC_V3),
3444 SND_PCI_QUIRK(0x106b, 0x0f00, "Mac", STAC_INTEL_MAC_V3),
3445 SND_PCI_QUIRK(0x106b, 0x1600, "Mac", STAC_INTEL_MAC_V3),
3446 SND_PCI_QUIRK(0x106b, 0x1700, "Mac", STAC_INTEL_MAC_V3),
3447 SND_PCI_QUIRK(0x106b, 0x0200, "Mac", STAC_INTEL_MAC_V3),
3448 SND_PCI_QUIRK(0x106b, 0x1e00, "Mac", STAC_INTEL_MAC_V3),
3449 SND_PCI_QUIRK(0x106b, 0x1a00, "Mac", STAC_INTEL_MAC_V4),
3450 SND_PCI_QUIRK(0x106b, 0x0a00, "Mac", STAC_INTEL_MAC_V5),
3451 SND_PCI_QUIRK(0x106b, 0x2200, "Mac", STAC_INTEL_MAC_V5),
3452 {}
8c650087 3453};
76c08828 3454
0a427846
TI
3455static const struct hda_fixup stac922x_fixups[];
3456
3457/* remap the fixup from codec SSID and apply it */
3458static void stac922x_fixup_intel_mac_auto(struct hda_codec *codec,
3459 const struct hda_fixup *fix,
3460 int action)
3461{
3462 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3463 return;
f5662e1c
DH
3464
3465 codec->fixup_id = HDA_FIXUP_ID_NOT_SET;
0a427846
TI
3466 snd_hda_pick_fixup(codec, NULL, stac922x_intel_mac_fixup_tbl,
3467 stac922x_fixups);
f5662e1c 3468 if (codec->fixup_id != HDA_FIXUP_ID_NOT_SET)
0a427846
TI
3469 snd_hda_apply_fixup(codec, action);
3470}
3471
3472static void stac922x_fixup_intel_mac_gpio(struct hda_codec *codec,
3473 const struct hda_fixup *fix,
3474 int action)
3475{
3476 struct sigmatel_spec *spec = codec->spec;
3477
3478 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
3479 spec->gpio_mask = spec->gpio_dir = 0x03;
3480 spec->gpio_data = 0x03;
3481 }
3482}
3483
3484static const struct hda_fixup stac922x_fixups[] = {
3485 [STAC_D945_REF] = {
3486 .type = HDA_FIXUP_PINS,
3487 .v.pins = ref922x_pin_configs,
3488 },
3489 [STAC_D945GTP3] = {
3490 .type = HDA_FIXUP_PINS,
3491 .v.pins = d945gtp3_pin_configs,
3492 },
3493 [STAC_D945GTP5] = {
3494 .type = HDA_FIXUP_PINS,
3495 .v.pins = d945gtp5_pin_configs,
3496 },
3497 [STAC_INTEL_MAC_AUTO] = {
3498 .type = HDA_FIXUP_FUNC,
3499 .v.func = stac922x_fixup_intel_mac_auto,
3500 },
3501 [STAC_INTEL_MAC_V1] = {
3502 .type = HDA_FIXUP_PINS,
3503 .v.pins = intel_mac_v1_pin_configs,
3504 .chained = true,
3505 .chain_id = STAC_922X_INTEL_MAC_GPIO,
3506 },
3507 [STAC_INTEL_MAC_V2] = {
3508 .type = HDA_FIXUP_PINS,
3509 .v.pins = intel_mac_v2_pin_configs,
3510 .chained = true,
3511 .chain_id = STAC_922X_INTEL_MAC_GPIO,
3512 },
3513 [STAC_INTEL_MAC_V3] = {
3514 .type = HDA_FIXUP_PINS,
3515 .v.pins = intel_mac_v3_pin_configs,
3516 .chained = true,
3517 .chain_id = STAC_922X_INTEL_MAC_GPIO,
3518 },
3519 [STAC_INTEL_MAC_V4] = {
3520 .type = HDA_FIXUP_PINS,
3521 .v.pins = intel_mac_v4_pin_configs,
3522 .chained = true,
3523 .chain_id = STAC_922X_INTEL_MAC_GPIO,
3524 },
3525 [STAC_INTEL_MAC_V5] = {
3526 .type = HDA_FIXUP_PINS,
3527 .v.pins = intel_mac_v5_pin_configs,
3528 .chained = true,
3529 .chain_id = STAC_922X_INTEL_MAC_GPIO,
3530 },
3531 [STAC_922X_INTEL_MAC_GPIO] = {
3532 .type = HDA_FIXUP_FUNC,
3533 .v.func = stac922x_fixup_intel_mac_gpio,
3534 },
3535 [STAC_ECS_202] = {
3536 .type = HDA_FIXUP_PINS,
3537 .v.pins = ecs202_pin_configs,
3538 },
3539 [STAC_922X_DELL_D81] = {
3540 .type = HDA_FIXUP_PINS,
3541 .v.pins = dell_922x_d81_pin_configs,
3542 },
3543 [STAC_922X_DELL_D82] = {
3544 .type = HDA_FIXUP_PINS,
3545 .v.pins = dell_922x_d82_pin_configs,
3546 },
3547 [STAC_922X_DELL_M81] = {
3548 .type = HDA_FIXUP_PINS,
3549 .v.pins = dell_922x_m81_pin_configs,
3550 },
3551 [STAC_922X_DELL_M82] = {
3552 .type = HDA_FIXUP_PINS,
3553 .v.pins = dell_922x_m82_pin_configs,
3554 },
3555};
3556
3557static const struct hda_model_fixup stac922x_models[] = {
3558 { .id = STAC_D945_REF, .name = "ref" },
3559 { .id = STAC_D945GTP5, .name = "5stack" },
3560 { .id = STAC_D945GTP3, .name = "3stack" },
3561 { .id = STAC_INTEL_MAC_V1, .name = "intel-mac-v1" },
3562 { .id = STAC_INTEL_MAC_V2, .name = "intel-mac-v2" },
3563 { .id = STAC_INTEL_MAC_V3, .name = "intel-mac-v3" },
3564 { .id = STAC_INTEL_MAC_V4, .name = "intel-mac-v4" },
3565 { .id = STAC_INTEL_MAC_V5, .name = "intel-mac-v5" },
3566 { .id = STAC_INTEL_MAC_AUTO, .name = "intel-mac-auto" },
3567 { .id = STAC_ECS_202, .name = "ecs202" },
3568 { .id = STAC_922X_DELL_D81, .name = "dell-d81" },
3569 { .id = STAC_922X_DELL_D82, .name = "dell-d82" },
3570 { .id = STAC_922X_DELL_M81, .name = "dell-m81" },
3571 { .id = STAC_922X_DELL_M82, .name = "dell-m82" },
dfe495d0 3572 /* for backward compatibility */
0a427846
TI
3573 { .id = STAC_INTEL_MAC_V3, .name = "macmini" },
3574 { .id = STAC_INTEL_MAC_V5, .name = "macbook" },
3575 { .id = STAC_INTEL_MAC_V3, .name = "macbook-pro-v1" },
3576 { .id = STAC_INTEL_MAC_V3, .name = "macbook-pro" },
3577 { .id = STAC_INTEL_MAC_V2, .name = "imac-intel" },
3578 { .id = STAC_INTEL_MAC_V3, .name = "imac-intel-20" },
3579 {}
3580};
3581
3582static const struct snd_pci_quirk stac922x_fixup_tbl[] = {
f5fcc13c
TI
3583 /* SigmaTel reference board */
3584 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
3585 "DFI LanParty", STAC_D945_REF),
577aa2c1
MR
3586 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
3587 "DFI LanParty", STAC_D945_REF),
f5fcc13c
TI
3588 /* Intel 945G based systems */
3589 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0101,
3590 "Intel D945G", STAC_D945GTP3),
3591 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0202,
3592 "Intel D945G", STAC_D945GTP3),
3593 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0606,
3594 "Intel D945G", STAC_D945GTP3),
3595 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0601,
3596 "Intel D945G", STAC_D945GTP3),
3597 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0111,
3598 "Intel D945G", STAC_D945GTP3),
3599 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1115,
3600 "Intel D945G", STAC_D945GTP3),
3601 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1116,
3602 "Intel D945G", STAC_D945GTP3),
3603 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1117,
3604 "Intel D945G", STAC_D945GTP3),
3605 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1118,
3606 "Intel D945G", STAC_D945GTP3),
3607 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x1119,
3608 "Intel D945G", STAC_D945GTP3),
3609 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x8826,
3610 "Intel D945G", STAC_D945GTP3),
3611 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5049,
3612 "Intel D945G", STAC_D945GTP3),
3613 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5055,
3614 "Intel D945G", STAC_D945GTP3),
3615 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x5048,
3616 "Intel D945G", STAC_D945GTP3),
3617 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0110,
3618 "Intel D945G", STAC_D945GTP3),
3619 /* Intel D945G 5-stack systems */
3620 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0404,
3621 "Intel D945G", STAC_D945GTP5),
3622 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0303,
3623 "Intel D945G", STAC_D945GTP5),
3624 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0013,
3625 "Intel D945G", STAC_D945GTP5),
3626 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0417,
3627 "Intel D945G", STAC_D945GTP5),
3628 /* Intel 945P based systems */
3629 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0b0b,
3630 "Intel D945P", STAC_D945GTP3),
3631 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0112,
3632 "Intel D945P", STAC_D945GTP3),
3633 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0d0d,
3634 "Intel D945P", STAC_D945GTP3),
3635 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0909,
3636 "Intel D945P", STAC_D945GTP3),
3637 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0505,
3638 "Intel D945P", STAC_D945GTP3),
3639 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0707,
3640 "Intel D945P", STAC_D945GTP5),
8056d47e
TI
3641 /* other intel */
3642 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x0204,
3643 "Intel D945", STAC_D945_REF),
f5fcc13c 3644 /* other systems */
0a427846 3645
536319af 3646 /* Apple Intel Mac (Mac Mini, MacBook, MacBook Pro...) */
0a427846
TI
3647 SND_PCI_QUIRK(0x8384, 0x7680, "Mac", STAC_INTEL_MAC_AUTO),
3648
dfe495d0
TI
3649 /* Dell systems */
3650 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a7,
3651 "unknown Dell", STAC_922X_DELL_D81),
3652 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01a9,
3653 "unknown Dell", STAC_922X_DELL_D81),
3654 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ab,
3655 "unknown Dell", STAC_922X_DELL_D81),
3656 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ac,
3657 "unknown Dell", STAC_922X_DELL_D82),
3658 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01bf,
3659 "unknown Dell", STAC_922X_DELL_M81),
3660 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d0,
3661 "unknown Dell", STAC_922X_DELL_D82),
3662 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d1,
3663 "unknown Dell", STAC_922X_DELL_D81),
3664 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d2,
3665 "unknown Dell", STAC_922X_DELL_D81),
3666 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01d7,
3667 "Dell XPS M1210", STAC_922X_DELL_M82),
8c650087 3668 /* ECS/PC Chips boards */
dea0a509 3669 SND_PCI_QUIRK_MASK(0x1019, 0xf000, 0x2000,
8663ae55 3670 "ECS/PC chips", STAC_ECS_202),
403d1944
MP
3671 {} /* terminator */
3672};
3673
29ac8363
TI
3674static const struct hda_pintbl ref927x_pin_configs[] = {
3675 { 0x0a, 0x02214020 },
3676 { 0x0b, 0x02a19080 },
3677 { 0x0c, 0x0181304e },
3678 { 0x0d, 0x01014010 },
3679 { 0x0e, 0x01a19040 },
3680 { 0x0f, 0x01011012 },
3681 { 0x10, 0x01016011 },
3682 { 0x11, 0x0101201f },
3683 { 0x12, 0x183301f0 },
3684 { 0x13, 0x18a001f0 },
3685 { 0x14, 0x18a001f0 },
3686 { 0x21, 0x01442070 },
3687 { 0x22, 0x01c42190 },
3688 { 0x23, 0x40000100 },
3689 {}
3cc08dc6
MP
3690};
3691
29ac8363
TI
3692static const struct hda_pintbl d965_3st_pin_configs[] = {
3693 { 0x0a, 0x0221401f },
3694 { 0x0b, 0x02a19120 },
3695 { 0x0c, 0x40000100 },
3696 { 0x0d, 0x01014011 },
3697 { 0x0e, 0x01a19021 },
3698 { 0x0f, 0x01813024 },
3699 { 0x10, 0x40000100 },
3700 { 0x11, 0x40000100 },
3701 { 0x12, 0x40000100 },
3702 { 0x13, 0x40000100 },
3703 { 0x14, 0x40000100 },
3704 { 0x21, 0x40000100 },
3705 { 0x22, 0x40000100 },
3706 { 0x23, 0x40000100 },
3707 {}
81d3dbde
TD
3708};
3709
29ac8363
TI
3710static const struct hda_pintbl d965_5st_pin_configs[] = {
3711 { 0x0a, 0x02214020 },
3712 { 0x0b, 0x02a19080 },
3713 { 0x0c, 0x0181304e },
3714 { 0x0d, 0x01014010 },
3715 { 0x0e, 0x01a19040 },
3716 { 0x0f, 0x01011012 },
3717 { 0x10, 0x01016011 },
3718 { 0x11, 0x40000100 },
3719 { 0x12, 0x40000100 },
3720 { 0x13, 0x40000100 },
3721 { 0x14, 0x40000100 },
3722 { 0x21, 0x01442070 },
3723 { 0x22, 0x40000100 },
3724 { 0x23, 0x40000100 },
3725 {}
93ed1503
TD
3726};
3727
29ac8363
TI
3728static const struct hda_pintbl d965_5st_no_fp_pin_configs[] = {
3729 { 0x0a, 0x40000100 },
3730 { 0x0b, 0x40000100 },
3731 { 0x0c, 0x0181304e },
3732 { 0x0d, 0x01014010 },
3733 { 0x0e, 0x01a19040 },
3734 { 0x0f, 0x01011012 },
3735 { 0x10, 0x01016011 },
3736 { 0x11, 0x40000100 },
3737 { 0x12, 0x40000100 },
3738 { 0x13, 0x40000100 },
3739 { 0x14, 0x40000100 },
3740 { 0x21, 0x01442070 },
3741 { 0x22, 0x40000100 },
3742 { 0x23, 0x40000100 },
3743 {}
679d92ed
TI
3744};
3745
29ac8363
TI
3746static const struct hda_pintbl dell_3st_pin_configs[] = {
3747 { 0x0a, 0x02211230 },
3748 { 0x0b, 0x02a11220 },
3749 { 0x0c, 0x01a19040 },
3750 { 0x0d, 0x01114210 },
3751 { 0x0e, 0x01111212 },
3752 { 0x0f, 0x01116211 },
3753 { 0x10, 0x01813050 },
3754 { 0x11, 0x01112214 },
3755 { 0x12, 0x403003fa },
3756 { 0x13, 0x90a60040 },
3757 { 0x14, 0x90a60040 },
3758 { 0x21, 0x404003fb },
3759 { 0x22, 0x40c003fc },
3760 { 0x23, 0x40000100 },
3761 {}
4ff076e5
TD
3762};
3763
29ac8363
TI
3764static void stac927x_fixup_ref_no_jd(struct hda_codec *codec,
3765 const struct hda_fixup *fix, int action)
3766{
29ac8363 3767 /* no jack detecion for ref-no-jd model */
36c9db7a
TI
3768 if (action == HDA_FIXUP_ACT_PRE_PROBE)
3769 codec->no_jack_detect = 1;
29ac8363
TI
3770}
3771
3772static void stac927x_fixup_ref(struct hda_codec *codec,
3773 const struct hda_fixup *fix, int action)
3774{
3775 struct sigmatel_spec *spec = codec->spec;
3776
3777 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
3778 snd_hda_apply_pincfgs(codec, ref927x_pin_configs);
3779 spec->eapd_mask = spec->gpio_mask = 0;
3780 spec->gpio_dir = spec->gpio_data = 0;
3781 }
3782}
3783
3784static void stac927x_fixup_dell_dmic(struct hda_codec *codec,
3785 const struct hda_fixup *fix, int action)
3786{
3787 struct sigmatel_spec *spec = codec->spec;
3788
3789 if (action != HDA_FIXUP_ACT_PRE_PROBE)
3790 return;
3791
3792 if (codec->subsystem_id != 0x1028022f) {
3793 /* GPIO2 High = Enable EAPD */
3794 spec->eapd_mask = spec->gpio_mask = 0x04;
3795 spec->gpio_dir = spec->gpio_data = 0x04;
3796 }
29ac8363
TI
3797
3798 snd_hda_add_verbs(codec, dell_3st_core_init);
3799 spec->volknob_init = 1;
29ac8363
TI
3800}
3801
3802static void stac927x_fixup_volknob(struct hda_codec *codec,
3803 const struct hda_fixup *fix, int action)
3804{
3805 struct sigmatel_spec *spec = codec->spec;
3806
3807 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
3808 snd_hda_add_verbs(codec, stac927x_volknob_core_init);
3809 spec->volknob_init = 1;
3810 }
3811}
3812
3813static const struct hda_fixup stac927x_fixups[] = {
3814 [STAC_D965_REF_NO_JD] = {
3815 .type = HDA_FIXUP_FUNC,
3816 .v.func = stac927x_fixup_ref_no_jd,
3817 .chained = true,
3818 .chain_id = STAC_D965_REF,
3819 },
3820 [STAC_D965_REF] = {
3821 .type = HDA_FIXUP_FUNC,
3822 .v.func = stac927x_fixup_ref,
3823 },
3824 [STAC_D965_3ST] = {
3825 .type = HDA_FIXUP_PINS,
3826 .v.pins = d965_3st_pin_configs,
3827 .chained = true,
3828 .chain_id = STAC_D965_VERBS,
3829 },
3830 [STAC_D965_5ST] = {
3831 .type = HDA_FIXUP_PINS,
3832 .v.pins = d965_5st_pin_configs,
3833 .chained = true,
3834 .chain_id = STAC_D965_VERBS,
3835 },
3836 [STAC_D965_VERBS] = {
3837 .type = HDA_FIXUP_VERBS,
3838 .v.verbs = d965_core_init,
3839 },
3840 [STAC_D965_5ST_NO_FP] = {
3841 .type = HDA_FIXUP_PINS,
3842 .v.pins = d965_5st_no_fp_pin_configs,
3843 },
3844 [STAC_DELL_3ST] = {
3845 .type = HDA_FIXUP_PINS,
3846 .v.pins = dell_3st_pin_configs,
3847 .chained = true,
3848 .chain_id = STAC_927X_DELL_DMIC,
3849 },
3850 [STAC_DELL_BIOS] = {
3851 .type = HDA_FIXUP_PINS,
3852 .v.pins = (const struct hda_pintbl[]) {
29ac8363 3853 /* correct the front output jack as a hp out */
f3e351ee 3854 { 0x0f, 0x0221101f },
29ac8363
TI
3855 /* correct the front input jack as a mic */
3856 { 0x0e, 0x02a79130 },
3857 {}
3858 },
3859 .chained = true,
3860 .chain_id = STAC_927X_DELL_DMIC,
3861 },
eefb8be4
TI
3862 [STAC_DELL_BIOS_AMIC] = {
3863 .type = HDA_FIXUP_PINS,
3864 .v.pins = (const struct hda_pintbl[]) {
3865 /* configure the analog microphone on some laptops */
3866 { 0x0c, 0x90a79130 },
3867 {}
3868 },
3869 .chained = true,
3870 .chain_id = STAC_DELL_BIOS,
3871 },
29ac8363
TI
3872 [STAC_DELL_BIOS_SPDIF] = {
3873 .type = HDA_FIXUP_PINS,
3874 .v.pins = (const struct hda_pintbl[]) {
3875 /* correct the device field to SPDIF out */
3876 { 0x21, 0x01442070 },
3877 {}
3878 },
3879 .chained = true,
3880 .chain_id = STAC_DELL_BIOS,
3881 },
3882 [STAC_927X_DELL_DMIC] = {
3883 .type = HDA_FIXUP_FUNC,
3884 .v.func = stac927x_fixup_dell_dmic,
3885 },
3886 [STAC_927X_VOLKNOB] = {
3887 .type = HDA_FIXUP_FUNC,
3888 .v.func = stac927x_fixup_volknob,
3889 },
3cc08dc6
MP
3890};
3891
29ac8363
TI
3892static const struct hda_model_fixup stac927x_models[] = {
3893 { .id = STAC_D965_REF_NO_JD, .name = "ref-no-jd" },
3894 { .id = STAC_D965_REF, .name = "ref" },
3895 { .id = STAC_D965_3ST, .name = "3stack" },
3896 { .id = STAC_D965_5ST, .name = "5stack" },
3897 { .id = STAC_D965_5ST_NO_FP, .name = "5stack-no-fp" },
3898 { .id = STAC_DELL_3ST, .name = "dell-3stack" },
3899 { .id = STAC_DELL_BIOS, .name = "dell-bios" },
eefb8be4 3900 { .id = STAC_DELL_BIOS_AMIC, .name = "dell-bios-amic" },
29ac8363
TI
3901 { .id = STAC_927X_VOLKNOB, .name = "volknob" },
3902 {}
f5fcc13c
TI
3903};
3904
29ac8363 3905static const struct snd_pci_quirk stac927x_fixup_tbl[] = {
f5fcc13c
TI
3906 /* SigmaTel reference board */
3907 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
3908 "DFI LanParty", STAC_D965_REF),
577aa2c1
MR
3909 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
3910 "DFI LanParty", STAC_D965_REF),
81d3dbde 3911 /* Intel 946 based systems */
f5fcc13c
TI
3912 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x3d01, "Intel D946", STAC_D965_3ST),
3913 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0xa301, "Intel D946", STAC_D965_3ST),
93ed1503 3914 /* 965 based 3 stack systems */
dea0a509
TI
3915 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_INTEL, 0xff00, 0x2100,
3916 "Intel D965", STAC_D965_3ST),
3917 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_INTEL, 0xff00, 0x2000,
3918 "Intel D965", STAC_D965_3ST),
4ff076e5 3919 /* Dell 3 stack systems */
dfe495d0 3920 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01dd, "Dell Dimension E520", STAC_DELL_3ST),
4ff076e5
TD
3921 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ed, "Dell ", STAC_DELL_3ST),
3922 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f4, "Dell ", STAC_DELL_3ST),
8e9068b1 3923 /* Dell 3 stack systems with verb table in BIOS */
2f32d909 3924 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f3, "Dell Inspiron 1420", STAC_DELL_BIOS),
66668b6f 3925 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f7, "Dell XPS M1730", STAC_DELL_BIOS),
2f32d909 3926 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0227, "Dell Vostro 1400 ", STAC_DELL_BIOS),
29ac8363 3927 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x022e, "Dell ", STAC_DELL_BIOS_SPDIF),
84d3dc20 3928 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x022f, "Dell Inspiron 1525", STAC_DELL_BIOS),
8e9068b1
MR
3929 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0242, "Dell ", STAC_DELL_BIOS),
3930 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0243, "Dell ", STAC_DELL_BIOS),
3931 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02ff, "Dell ", STAC_DELL_BIOS),
29ac8363 3932 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0209, "Dell XPS 1330", STAC_DELL_BIOS_SPDIF),
93ed1503 3933 /* 965 based 5 stack systems */
dea0a509
TI
3934 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_INTEL, 0xff00, 0x2300,
3935 "Intel D965", STAC_D965_5ST),
3936 SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_INTEL, 0xff00, 0x2500,
3937 "Intel D965", STAC_D965_5ST),
54930531
TI
3938 /* volume-knob fixes */
3939 SND_PCI_QUIRK_VENDOR(0x10cf, "FSC", STAC_927X_VOLKNOB),
3cc08dc6
MP
3940 {} /* terminator */
3941};
3942
fe6322ca
TI
3943static const struct hda_pintbl ref9205_pin_configs[] = {
3944 { 0x0a, 0x40000100 },
3945 { 0x0b, 0x40000100 },
3946 { 0x0c, 0x01016011 },
3947 { 0x0d, 0x01014010 },
3948 { 0x0e, 0x01813122 },
3949 { 0x0f, 0x01a19021 },
3950 { 0x14, 0x01019020 },
3951 { 0x16, 0x40000100 },
3952 { 0x17, 0x90a000f0 },
3953 { 0x18, 0x90a000f0 },
3954 { 0x21, 0x01441030 },
3955 { 0x22, 0x01c41030 },
3956 {}
f3302a59
MP
3957};
3958
dfe495d0
TI
3959/*
3960 STAC 9205 pin configs for
3961 102801F1
3962 102801F2
3963 102801FC
3964 102801FD
3965 10280204
3966 1028021F
3fa2ef74 3967 10280228 (Dell Vostro 1500)
95e70e87 3968 10280229 (Dell Vostro 1700)
dfe495d0 3969*/
fe6322ca
TI
3970static const struct hda_pintbl dell_9205_m42_pin_configs[] = {
3971 { 0x0a, 0x0321101F },
3972 { 0x0b, 0x03A11020 },
3973 { 0x0c, 0x400003FA },
3974 { 0x0d, 0x90170310 },
3975 { 0x0e, 0x400003FB },
3976 { 0x0f, 0x400003FC },
3977 { 0x14, 0x400003FD },
3978 { 0x16, 0x40F000F9 },
3979 { 0x17, 0x90A60330 },
3980 { 0x18, 0x400003FF },
3981 { 0x21, 0x0144131F },
3982 { 0x22, 0x40C003FE },
3983 {}
dfe495d0
TI
3984};
3985
3986/*
3987 STAC 9205 pin configs for
3988 102801F9
3989 102801FA
3990 102801FE
3991 102801FF (Dell Precision M4300)
3992 10280206
3993 10280200
3994 10280201
3995*/
fe6322ca
TI
3996static const struct hda_pintbl dell_9205_m43_pin_configs[] = {
3997 { 0x0a, 0x0321101f },
3998 { 0x0b, 0x03a11020 },
3999 { 0x0c, 0x90a70330 },
4000 { 0x0d, 0x90170310 },
4001 { 0x0e, 0x400000fe },
4002 { 0x0f, 0x400000ff },
4003 { 0x14, 0x400000fd },
4004 { 0x16, 0x40f000f9 },
4005 { 0x17, 0x400000fa },
4006 { 0x18, 0x400000fc },
4007 { 0x21, 0x0144131f },
4008 { 0x22, 0x40c003f8 },
4009 /* Enable SPDIF in/out */
4010 { 0x1f, 0x01441030 },
4011 { 0x20, 0x1c410030 },
4012 {}
ae0a8ed8
TD
4013};
4014
fe6322ca
TI
4015static const struct hda_pintbl dell_9205_m44_pin_configs[] = {
4016 { 0x0a, 0x0421101f },
4017 { 0x0b, 0x04a11020 },
4018 { 0x0c, 0x400003fa },
4019 { 0x0d, 0x90170310 },
4020 { 0x0e, 0x400003fb },
4021 { 0x0f, 0x400003fc },
4022 { 0x14, 0x400003fd },
4023 { 0x16, 0x400003f9 },
4024 { 0x17, 0x90a60330 },
4025 { 0x18, 0x400003ff },
4026 { 0x21, 0x01441340 },
4027 { 0x22, 0x40c003fe },
4028 {}
ae0a8ed8
TD
4029};
4030
fe6322ca
TI
4031static void stac9205_fixup_ref(struct hda_codec *codec,
4032 const struct hda_fixup *fix, int action)
4033{
4034 struct sigmatel_spec *spec = codec->spec;
4035
4036 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
4037 snd_hda_apply_pincfgs(codec, ref9205_pin_configs);
4038 /* SPDIF-In enabled */
4039 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0;
4040 }
4041}
4042
fe6322ca
TI
4043static void stac9205_fixup_dell_m43(struct hda_codec *codec,
4044 const struct hda_fixup *fix, int action)
4045{
4046 struct sigmatel_spec *spec = codec->spec;
36c9db7a 4047 struct hda_jack_tbl *jack;
fe6322ca
TI
4048
4049 if (action == HDA_FIXUP_ACT_PRE_PROBE) {
4050 snd_hda_apply_pincfgs(codec, dell_9205_m43_pin_configs);
4051
4052 /* Enable unsol response for GPIO4/Dock HP connection */
fe6322ca
TI
4053 snd_hda_codec_write_cache(codec, codec->afg, 0,
4054 AC_VERB_SET_GPIO_UNSOLICITED_RSP_MASK, 0x10);
36c9db7a
TI
4055 snd_hda_jack_detect_enable_callback(codec, codec->afg,
4056 STAC_VREF_EVENT,
4057 stac_vref_event);
4058 jack = snd_hda_jack_tbl_get(codec, codec->afg);
4059 if (jack)
4060 jack->private_data = 0x01;
fe6322ca
TI
4061
4062 spec->gpio_dir = 0x0b;
4063 spec->eapd_mask = 0x01;
4064 spec->gpio_mask = 0x1b;
4065 spec->gpio_mute = 0x10;
4066 /* GPIO0 High = EAPD, GPIO1 Low = Headphone Mute,
4067 * GPIO3 Low = DRM
4068 */
4069 spec->gpio_data = 0x01;
4070 }
4071}
4072
4073static void stac9205_fixup_eapd(struct hda_codec *codec,
4074 const struct hda_fixup *fix, int action)
4075{
4076 struct sigmatel_spec *spec = codec->spec;
4077
4078 if (action == HDA_FIXUP_ACT_PRE_PROBE)
4079 spec->eapd_switch = 0;
4080}
4081
4082static const struct hda_fixup stac9205_fixups[] = {
4083 [STAC_9205_REF] = {
4084 .type = HDA_FIXUP_FUNC,
4085 .v.func = stac9205_fixup_ref,
4086 },
4087 [STAC_9205_DELL_M42] = {
4088 .type = HDA_FIXUP_PINS,
4089 .v.pins = dell_9205_m42_pin_configs,
4090 },
4091 [STAC_9205_DELL_M43] = {
4092 .type = HDA_FIXUP_FUNC,
4093 .v.func = stac9205_fixup_dell_m43,
4094 },
4095 [STAC_9205_DELL_M44] = {
4096 .type = HDA_FIXUP_PINS,
4097 .v.pins = dell_9205_m44_pin_configs,
4098 },
4099 [STAC_9205_EAPD] = {
4100 .type = HDA_FIXUP_FUNC,
4101 .v.func = stac9205_fixup_eapd,
4102 },
4103 {}
f3302a59
MP
4104};
4105
fe6322ca
TI
4106static const struct hda_model_fixup stac9205_models[] = {
4107 { .id = STAC_9205_REF, .name = "ref" },
4108 { .id = STAC_9205_DELL_M42, .name = "dell-m42" },
4109 { .id = STAC_9205_DELL_M43, .name = "dell-m43" },
4110 { .id = STAC_9205_DELL_M44, .name = "dell-m44" },
4111 { .id = STAC_9205_EAPD, .name = "eapd" },
4112 {}
f5fcc13c
TI
4113};
4114
fe6322ca 4115static const struct snd_pci_quirk stac9205_fixup_tbl[] = {
f5fcc13c
TI
4116 /* SigmaTel reference board */
4117 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0x2668,
4118 "DFI LanParty", STAC_9205_REF),
02358fcf
HRK
4119 SND_PCI_QUIRK(PCI_VENDOR_ID_INTEL, 0xfb30,
4120 "SigmaTel", STAC_9205_REF),
577aa2c1
MR
4121 SND_PCI_QUIRK(PCI_VENDOR_ID_DFI, 0x3101,
4122 "DFI LanParty", STAC_9205_REF),
d9a4268e 4123 /* Dell */
dfe495d0
TI
4124 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f1,
4125 "unknown Dell", STAC_9205_DELL_M42),
4126 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f2,
4127 "unknown Dell", STAC_9205_DELL_M42),
ae0a8ed8 4128 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f8,
b44ef2f1 4129 "Dell Precision", STAC_9205_DELL_M43),
ae0a8ed8
TD
4130 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01f9,
4131 "Dell Precision", STAC_9205_DELL_M43),
4132 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fa,
4133 "Dell Precision", STAC_9205_DELL_M43),
dfe495d0
TI
4134 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fc,
4135 "unknown Dell", STAC_9205_DELL_M42),
4136 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fd,
4137 "unknown Dell", STAC_9205_DELL_M42),
ae0a8ed8
TD
4138 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01fe,
4139 "Dell Precision", STAC_9205_DELL_M43),
4140 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x01ff,
dfe495d0 4141 "Dell Precision M4300", STAC_9205_DELL_M43),
dfe495d0
TI
4142 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0204,
4143 "unknown Dell", STAC_9205_DELL_M42),
4549915c
TI
4144 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0206,
4145 "Dell Precision", STAC_9205_DELL_M43),
4146 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021b,
4147 "Dell Precision", STAC_9205_DELL_M43),
36c9db7a
TI
4148 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021c,
4149 "Dell Precision", STAC_9205_DELL_M43),
4150 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x021f,
4151 "Dell Inspiron", STAC_9205_DELL_M44),
4152 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0228,
4153 "Dell Vostro 1500", STAC_9205_DELL_M42),
4154 SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x0229,
4155 "Dell Vostro 1700", STAC_9205_DELL_M42),
4156 /* Gateway */
4157 SND_PCI_QUIRK(0x107b, 0x0560, "Gateway T6834c", STAC_9205_EAPD),
4158 SND_PCI_QUIRK(0x107b, 0x0565, "Gateway T1616", STAC_9205_EAPD),
4159 {} /* terminator */
4160};
a64135a2 4161
8b3dfdaf
TI
4162static void stac92hd95_fixup_hp_led(struct hda_codec *codec,
4163 const struct hda_fixup *fix, int action)
4164{
4165 struct sigmatel_spec *spec = codec->spec;
4166
4167 if (action != HDA_FIXUP_ACT_PRE_PROBE)
4168 return;
4169
4170 if (find_mute_led_cfg(codec, spec->default_polarity))
4171 codec_dbg(codec, "mute LED gpio %d polarity %d\n",
4172 spec->gpio_led,
4173 spec->gpio_led_polarity);
4174}
4175
4176static const struct hda_fixup stac92hd95_fixups[] = {
4177 [STAC_92HD95_HP_LED] = {
4178 .type = HDA_FIXUP_FUNC,
4179 .v.func = stac92hd95_fixup_hp_led,
4180 },
4181 [STAC_92HD95_HP_BASS] = {
4182 .type = HDA_FIXUP_VERBS,
4183 .v.verbs = (const struct hda_verb[]) {
4184 {0x1a, 0x795, 0x00}, /* HPF to 100Hz */
4185 {}
4186 },
4187 .chained = true,
4188 .chain_id = STAC_92HD95_HP_LED,
4189 },
4190};
4191
4192static const struct snd_pci_quirk stac92hd95_fixup_tbl[] = {
4193 SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x1911, "HP Spectre 13", STAC_92HD95_HP_BASS),
4194 {} /* terminator */
4195};
4196
4197static const struct hda_model_fixup stac92hd95_models[] = {
4198 { .id = STAC_92HD95_HP_LED, .name = "hp-led" },
4199 { .id = STAC_92HD95_HP_BASS, .name = "hp-bass" },
4200 {}
4201};
4202
4203
36c9db7a 4204static int stac_parse_auto_config(struct hda_codec *codec)
ab5a6ebe
VK
4205{
4206 struct sigmatel_spec *spec = codec->spec;
36c9db7a 4207 int err;
f390dad4 4208 int flags = 0;
ab5a6ebe 4209
f390dad4
DH
4210 if (spec->headset_jack)
4211 flags |= HDA_PINCFG_HEADSET_MIC;
4212
4213 err = snd_hda_parse_pin_defcfg(codec, &spec->gen.autocfg, NULL, flags);
36c9db7a
TI
4214 if (err < 0)
4215 return err;
ab5a6ebe 4216
36c9db7a
TI
4217 /* add hooks */
4218 spec->gen.pcm_playback_hook = stac_playback_pcm_hook;
4219 spec->gen.pcm_capture_hook = stac_capture_pcm_hook;
ab5a6ebe 4220
36c9db7a
TI
4221 spec->gen.automute_hook = stac_update_outputs;
4222 spec->gen.hp_automute_hook = stac_hp_automute;
4223 spec->gen.line_automute_hook = stac_line_automute;
664389db 4224 spec->gen.mic_autoswitch_hook = stac_mic_autoswitch;
3d21d3f7 4225
36c9db7a
TI
4226 err = snd_hda_gen_parse_auto_config(codec, &spec->gen.autocfg);
4227 if (err < 0)
4228 return err;
3d21d3f7 4229
36c9db7a
TI
4230 /* minimum value is actually mute */
4231 spec->gen.vmaster_tlv[3] |= TLV_DB_SCALE_MUTE;
c6e4c666 4232
36c9db7a
TI
4233 /* setup analog beep controls */
4234 if (spec->anabeep_nid > 0) {
4235 err = stac_auto_create_beep_ctls(codec,
4236 spec->anabeep_nid);
4237 if (err < 0)
4238 return err;
3d21d3f7
TI
4239 }
4240
36c9db7a
TI
4241 /* setup digital beep controls and input device */
4242#ifdef CONFIG_SND_HDA_INPUT_BEEP
7504b6cd
TI
4243 if (spec->gen.beep_nid) {
4244 hda_nid_t nid = spec->gen.beep_nid;
36c9db7a
TI
4245 unsigned int caps;
4246
4247 err = stac_auto_create_beep_ctls(codec, nid);
36c9db7a
TI
4248 if (err < 0)
4249 return err;
4250 if (codec->beep) {
4251 /* IDT/STAC codecs have linear beep tone parameter */
4252 codec->beep->linear_tone = spec->linear_tone_beep;
4253 /* if no beep switch is available, make its own one */
4254 caps = query_amp_caps(codec, nid, HDA_OUTPUT);
4255 if (!(caps & AC_AMPCAP_MUTE)) {
4256 err = stac_beep_switch_ctl(codec);
4257 if (err < 0)
4258 return err;
fd60cc89
MR
4259 }
4260 }
314634bc 4261 }
36c9db7a 4262#endif
314634bc 4263
36c9db7a
TI
4264 if (spec->gpio_led)
4265 spec->gen.vmaster_mute.hook = stac_vmaster_hook;
4266
4267 if (spec->aloopback_ctl &&
4268 snd_hda_get_bool_hint(codec, "loopback") == 1) {
4269 if (!snd_hda_gen_add_kctl(&spec->gen, NULL, spec->aloopback_ctl))
4270 return -ENOMEM;
4271 }
4272
42875479
TI
4273 if (spec->have_spdif_mux) {
4274 err = stac_create_spdif_mux_ctls(codec);
4275 if (err < 0)
4276 return err;
4277 }
4278
36c9db7a
TI
4279 stac_init_power_map(codec);
4280
4281 return 0;
1835a0f9
TI
4282}
4283
36c9db7a
TI
4284
4285static int stac_init(struct hda_codec *codec)
d38cce70
KG
4286{
4287 struct sigmatel_spec *spec = codec->spec;
36c9db7a 4288 int i;
07f80449 4289
36c9db7a
TI
4290 /* override some hints */
4291 stac_store_hints(codec);
26ebe0a2 4292
36c9db7a 4293 /* set up GPIO */
36c9db7a
TI
4294 /* turn on EAPD statically when spec->eapd_switch isn't set.
4295 * otherwise, unsol event will turn it on/off dynamically
4296 */
4297 if (!spec->eapd_switch)
1ea9a69d
TI
4298 spec->gpio_data |= spec->eapd_mask;
4299 stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir, spec->gpio_data);
d38cce70 4300
36c9db7a 4301 snd_hda_gen_init(codec);
c357aab0 4302
36c9db7a
TI
4303 /* sync the power-map */
4304 if (spec->num_pwrs)
4305 snd_hda_codec_write(codec, codec->afg, 0,
4306 AC_VERB_IDT_SET_POWER_MAP,
4307 spec->power_map_bits);
0f6fcb73 4308
36c9db7a
TI
4309 /* power down inactive ADCs */
4310 if (spec->powerdown_adcs) {
4311 for (i = 0; i < spec->gen.num_all_adcs; i++) {
4312 if (spec->active_adcs & (1 << i))
4313 continue;
4314 snd_hda_codec_write(codec, spec->gen.all_adcs[i], 0,
4315 AC_VERB_SET_POWER_STATE,
4316 AC_PWRST_D3);
89bb3e74
TI
4317 }
4318 }
4319
c357aab0
VK
4320 return 0;
4321}
4322
36c9db7a 4323static void stac_shutup(struct hda_codec *codec)
78987bdc 4324{
36c9db7a
TI
4325 struct sigmatel_spec *spec = codec->spec;
4326
4327 snd_hda_shutup_pins(codec);
4328
4329 if (spec->eapd_mask)
4330 stac_gpio_set(codec, spec->gpio_mask,
4331 spec->gpio_dir, spec->gpio_data &
4332 ~spec->eapd_mask);
4333}
4334
7504b6cd 4335#define stac_free snd_hda_gen_free
78987bdc 4336
2d34e1b3
TI
4337#ifdef CONFIG_PROC_FS
4338static void stac92hd_proc_hook(struct snd_info_buffer *buffer,
4339 struct hda_codec *codec, hda_nid_t nid)
4340{
4341 if (nid == codec->afg)
4342 snd_iprintf(buffer, "Power-Map: 0x%02x\n",
c882246d
TI
4343 snd_hda_codec_read(codec, nid, 0,
4344 AC_VERB_IDT_GET_POWER_MAP, 0));
2d34e1b3
TI
4345}
4346
4347static void analog_loop_proc_hook(struct snd_info_buffer *buffer,
4348 struct hda_codec *codec,
4349 unsigned int verb)
4350{
4351 snd_iprintf(buffer, "Analog Loopback: 0x%02x\n",
4352 snd_hda_codec_read(codec, codec->afg, 0, verb, 0));
4353}
4354
4355/* stac92hd71bxx, stac92hd73xx */
4356static void stac92hd7x_proc_hook(struct snd_info_buffer *buffer,
4357 struct hda_codec *codec, hda_nid_t nid)
4358{
4359 stac92hd_proc_hook(buffer, codec, nid);
4360 if (nid == codec->afg)
4361 analog_loop_proc_hook(buffer, codec, 0xfa0);
4362}
4363
4364static void stac9205_proc_hook(struct snd_info_buffer *buffer,
4365 struct hda_codec *codec, hda_nid_t nid)
4366{
4367 if (nid == codec->afg)
4368 analog_loop_proc_hook(buffer, codec, 0xfe0);
4369}
4370
4371static void stac927x_proc_hook(struct snd_info_buffer *buffer,
4372 struct hda_codec *codec, hda_nid_t nid)
4373{
4374 if (nid == codec->afg)
4375 analog_loop_proc_hook(buffer, codec, 0xfeb);
4376}
4377#else
4378#define stac92hd_proc_hook NULL
4379#define stac92hd7x_proc_hook NULL
4380#define stac9205_proc_hook NULL
4381#define stac927x_proc_hook NULL
4382#endif
4383
2a43952a 4384#ifdef CONFIG_PM
36c9db7a
TI
4385static int stac_suspend(struct hda_codec *codec)
4386{
4387 stac_shutup(codec);
4388 return 0;
4389}
36c9db7a
TI
4390#else
4391#define stac_suspend NULL
36c9db7a 4392#endif /* CONFIG_PM */
7df1ce1a 4393
36c9db7a
TI
4394static const struct hda_codec_ops stac_patch_ops = {
4395 .build_controls = snd_hda_gen_build_controls,
4396 .build_pcms = snd_hda_gen_build_pcms,
4397 .init = stac_init,
4398 .free = stac_free,
29adc4b9 4399 .unsol_event = snd_hda_jack_unsol_event,
2a43952a 4400#ifdef CONFIG_PM
36c9db7a 4401 .suspend = stac_suspend,
ff6fdc37 4402#endif
36c9db7a 4403 .reboot_notify = stac_shutup,
2f2f4251
M
4404};
4405
36c9db7a 4406static int alloc_stac_spec(struct hda_codec *codec)
361dab3e
TI
4407{
4408 struct sigmatel_spec *spec;
4409
4410 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
4411 if (!spec)
4412 return -ENOMEM;
36c9db7a 4413 snd_hda_gen_spec_init(&spec->gen);
361dab3e
TI
4414 codec->spec = spec;
4415 codec->no_trigger_sense = 1; /* seems common with STAC/IDT codecs */
361dab3e
TI
4416 return 0;
4417}
4418
2f2f4251
M
4419static int patch_stac9200(struct hda_codec *codec)
4420{
4421 struct sigmatel_spec *spec;
c7d4b2fa 4422 int err;
2f2f4251 4423
36c9db7a 4424 err = alloc_stac_spec(codec);
361dab3e
TI
4425 if (err < 0)
4426 return err;
2f2f4251 4427
361dab3e 4428 spec = codec->spec;
1b0e372d 4429 spec->linear_tone_beep = 1;
36c9db7a 4430 spec->gen.own_eapd_ctl = 1;
d39a3ae8 4431
36c9db7a 4432 codec->patch_ops = stac_patch_ops;
ba615b86 4433 codec->power_filter = snd_hda_codec_eapd_power_filter;
2f2f4251 4434
d39a3ae8 4435 snd_hda_add_verbs(codec, stac9200_eapd_init);
c7d4b2fa 4436
36c9db7a
TI
4437 snd_hda_pick_fixup(codec, stac9200_models, stac9200_fixup_tbl,
4438 stac9200_fixups);
d39a3ae8 4439 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
117f257d 4440
36c9db7a 4441 err = stac_parse_auto_config(codec);
c7d4b2fa 4442 if (err < 0) {
36c9db7a 4443 stac_free(codec);
c7d4b2fa
M
4444 return err;
4445 }
2f2f4251 4446
d39a3ae8
TI
4447 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4448
2f2f4251
M
4449 return 0;
4450}
4451
8e21c34c
TD
4452static int patch_stac925x(struct hda_codec *codec)
4453{
4454 struct sigmatel_spec *spec;
4455 int err;
4456
36c9db7a 4457 err = alloc_stac_spec(codec);
361dab3e
TI
4458 if (err < 0)
4459 return err;
8e21c34c 4460
361dab3e 4461 spec = codec->spec;
1b0e372d 4462 spec->linear_tone_beep = 1;
36c9db7a 4463 spec->gen.own_eapd_ctl = 1;
9cb36c2a 4464
36c9db7a 4465 codec->patch_ops = stac_patch_ops;
8e21c34c 4466
d2077d40 4467 snd_hda_add_verbs(codec, stac925x_core_init);
8e21c34c 4468
36c9db7a
TI
4469 snd_hda_pick_fixup(codec, stac925x_models, stac925x_fixup_tbl,
4470 stac925x_fixups);
d2077d40
TI
4471 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
4472
36c9db7a 4473 err = stac_parse_auto_config(codec);
8e21c34c 4474 if (err < 0) {
36c9db7a 4475 stac_free(codec);
8e21c34c
TD
4476 return err;
4477 }
4478
d2077d40
TI
4479 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4480
8e21c34c
TD
4481 return 0;
4482}
4483
e1f0d669
MR
4484static int patch_stac92hd73xx(struct hda_codec *codec)
4485{
4486 struct sigmatel_spec *spec;
361dab3e 4487 int err;
c21ca4a8 4488 int num_dacs;
e1f0d669 4489
36c9db7a 4490 err = alloc_stac_spec(codec);
361dab3e
TI
4491 if (err < 0)
4492 return err;
e1f0d669 4493
361dab3e 4494 spec = codec->spec;
1b0e372d 4495 spec->linear_tone_beep = 0;
2748746f 4496 spec->gen.mixer_nid = 0x1d;
42875479 4497 spec->have_spdif_mux = 1;
e1f0d669 4498
36c9db7a 4499 num_dacs = snd_hda_get_num_conns(codec, 0x0a) - 1;
c21ca4a8 4500 if (num_dacs < 3 || num_dacs > 5) {
4e76a883
TI
4501 codec_warn(codec,
4502 "Could not determine number of channels defaulting to DAC count\n");
36c9db7a 4503 num_dacs = 5;
e1f0d669 4504 }
55e30141 4505
c21ca4a8 4506 switch (num_dacs) {
e1f0d669 4507 case 0x3: /* 6 Channel */
36c9db7a 4508 spec->aloopback_ctl = &stac92hd73xx_6ch_loopback;
e1f0d669
MR
4509 break;
4510 case 0x4: /* 8 Channel */
36c9db7a 4511 spec->aloopback_ctl = &stac92hd73xx_8ch_loopback;
e1f0d669
MR
4512 break;
4513 case 0x5: /* 10 Channel */
36c9db7a 4514 spec->aloopback_ctl = &stac92hd73xx_10ch_loopback;
d78d7a90 4515 break;
c21ca4a8 4516 }
e1f0d669 4517
e1f0d669
MR
4518 spec->aloopback_mask = 0x01;
4519 spec->aloopback_shift = 8;
4520
7504b6cd 4521 spec->gen.beep_nid = 0x1c; /* digital beep */
6479c631 4522
55e30141
TI
4523 /* GPIO0 High = Enable EAPD */
4524 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x1;
4525 spec->gpio_data = 0x01;
6b3ab21e 4526
55e30141 4527 spec->eapd_switch = 1;
a7662640 4528
a64135a2
MR
4529 spec->num_pwrs = ARRAY_SIZE(stac92hd73xx_pwr_nids);
4530 spec->pwr_nids = stac92hd73xx_pwr_nids;
4531
36c9db7a 4532 spec->gen.own_eapd_ctl = 1;
f4f678d2 4533 spec->gen.power_down_unused = 1;
36c9db7a
TI
4534
4535 codec->patch_ops = stac_patch_ops;
4536
4537 snd_hda_pick_fixup(codec, stac92hd73xx_models, stac92hd73xx_fixup_tbl,
4538 stac92hd73xx_fixups);
55e30141
TI
4539 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
4540
4541 if (!spec->volknob_init)
4542 snd_hda_add_verbs(codec, stac92hd73xx_core_init);
4543
36c9db7a 4544 err = stac_parse_auto_config(codec);
e1f0d669 4545 if (err < 0) {
36c9db7a 4546 stac_free(codec);
e1f0d669
MR
4547 return err;
4548 }
4549
303985f8
DH
4550 /* Don't GPIO-mute speakers if there are no internal speakers, because
4551 * the GPIO might be necessary for Headphone
4552 */
4553 if (spec->eapd_switch && !has_builtin_speaker(codec))
4554 spec->eapd_switch = 0;
4555
2d34e1b3
TI
4556 codec->proc_widget_hook = stac92hd7x_proc_hook;
4557
55e30141
TI
4558 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4559
e1f0d669
MR
4560 return 0;
4561}
4562
372f8c75
TI
4563static void stac_setup_gpio(struct hda_codec *codec)
4564{
4565 struct sigmatel_spec *spec = codec->spec;
4566
1ea9a69d 4567 spec->gpio_mask |= spec->eapd_mask;
372f8c75
TI
4568 if (spec->gpio_led) {
4569 if (!spec->vref_mute_led_nid) {
4570 spec->gpio_mask |= spec->gpio_led;
4571 spec->gpio_dir |= spec->gpio_led;
4572 spec->gpio_data |= spec->gpio_led;
4573 } else {
dfc6e469 4574 codec->power_filter = stac_vref_led_power_filter;
372f8c75
TI
4575 }
4576 }
4577
4578 if (spec->mic_mute_led_gpio) {
4579 spec->gpio_mask |= spec->mic_mute_led_gpio;
4580 spec->gpio_dir |= spec->mic_mute_led_gpio;
7fe30711 4581 spec->mic_enabled = 0;
372f8c75 4582 spec->gpio_data |= spec->mic_mute_led_gpio;
36c9db7a 4583
a90229e0 4584 spec->gen.cap_sync_hook = stac_capture_led_hook;
372f8c75
TI
4585 }
4586}
4587
d0513fc6
MR
4588static int patch_stac92hd83xxx(struct hda_codec *codec)
4589{
4590 struct sigmatel_spec *spec;
4591 int err;
4592
36c9db7a 4593 err = alloc_stac_spec(codec);
361dab3e
TI
4594 if (err < 0)
4595 return err;
d0513fc6 4596
c36b5b05 4597 codec->epss = 0; /* longer delay needed for D3 */
699d8995 4598
361dab3e 4599 spec = codec->spec;
1db7ccdb 4600 spec->linear_tone_beep = 0;
36c9db7a 4601 spec->gen.own_eapd_ctl = 1;
f4f678d2 4602 spec->gen.power_down_unused = 1;
2748746f 4603 spec->gen.mixer_nid = 0x1b;
36c9db7a 4604
7504b6cd 4605 spec->gen.beep_nid = 0x21; /* digital beep */
d0513fc6 4606 spec->pwr_nids = stac92hd83xxx_pwr_nids;
d0513fc6 4607 spec->num_pwrs = ARRAY_SIZE(stac92hd83xxx_pwr_nids);
36c9db7a 4608 spec->default_polarity = -1; /* no default cfg */
d0513fc6 4609
36c9db7a 4610 codec->patch_ops = stac_patch_ops;
b4e81876 4611
372f8c75 4612 snd_hda_add_verbs(codec, stac92hd83xxx_core_init);
e108c7b7 4613
36c9db7a
TI
4614 snd_hda_pick_fixup(codec, stac92hd83xxx_models, stac92hd83xxx_fixup_tbl,
4615 stac92hd83xxx_fixups);
372f8c75 4616 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
b4e81876 4617
372f8c75 4618 stac_setup_gpio(codec);
62cbde18 4619
36c9db7a 4620 err = stac_parse_auto_config(codec);
d0513fc6 4621 if (err < 0) {
36c9db7a 4622 stac_free(codec);
d0513fc6
MR
4623 return err;
4624 }
4625
2d34e1b3
TI
4626 codec->proc_widget_hook = stac92hd_proc_hook;
4627
372f8c75
TI
4628 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4629
d0513fc6
MR
4630 return 0;
4631}
4632
4e637c6e
VK
4633static const hda_nid_t stac92hd95_pwr_nids[] = {
4634 0x0a, 0x0b, 0x0c, 0x0d
4635};
4636
4637static int patch_stac92hd95(struct hda_codec *codec)
4638{
4639 struct sigmatel_spec *spec;
4640 int err;
4641
4642 err = alloc_stac_spec(codec);
4643 if (err < 0)
4644 return err;
4645
4646 codec->epss = 0; /* longer delay needed for D3 */
4647
4648 spec = codec->spec;
4649 spec->linear_tone_beep = 0;
4650 spec->gen.own_eapd_ctl = 1;
4651 spec->gen.power_down_unused = 1;
4652
7504b6cd 4653 spec->gen.beep_nid = 0x19; /* digital beep */
4e637c6e
VK
4654 spec->pwr_nids = stac92hd95_pwr_nids;
4655 spec->num_pwrs = ARRAY_SIZE(stac92hd95_pwr_nids);
8b3dfdaf 4656 spec->default_polarity = 0;
4e637c6e
VK
4657
4658 codec->patch_ops = stac_patch_ops;
4659
8b3dfdaf
TI
4660 snd_hda_pick_fixup(codec, stac92hd95_models, stac92hd95_fixup_tbl,
4661 stac92hd95_fixups);
4662 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
4663
4664 stac_setup_gpio(codec);
4665
4e637c6e
VK
4666 err = stac_parse_auto_config(codec);
4667 if (err < 0) {
4668 stac_free(codec);
4669 return err;
4670 }
4671
4672 codec->proc_widget_hook = stac92hd_proc_hook;
4673
8b3dfdaf
TI
4674 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4675
4e637c6e
VK
4676 return 0;
4677}
4678
e035b841
MR
4679static int patch_stac92hd71bxx(struct hda_codec *codec)
4680{
4681 struct sigmatel_spec *spec;
2b63536f 4682 const struct hda_verb *unmute_init = stac92hd71bxx_unmute_core_init;
361dab3e 4683 int err;
e035b841 4684
36c9db7a 4685 err = alloc_stac_spec(codec);
361dab3e
TI
4686 if (err < 0)
4687 return err;
e035b841 4688
361dab3e 4689 spec = codec->spec;
1b0e372d 4690 spec->linear_tone_beep = 0;
36c9db7a 4691 spec->gen.own_eapd_ctl = 1;
f4f678d2 4692 spec->gen.power_down_unused = 1;
2748746f 4693 spec->gen.mixer_nid = 0x17;
42875479 4694 spec->have_spdif_mux = 1;
e035b841 4695
36c9db7a 4696 codec->patch_ops = stac_patch_ops;
0f6fcb73
TI
4697
4698 /* GPIO0 = EAPD */
4699 spec->gpio_mask = 0x01;
4700 spec->gpio_dir = 0x01;
4701 spec->gpio_data = 0x01;
41c3b648 4702
541eee87
MR
4703 switch (codec->vendor_id) {
4704 case 0x111d76b6: /* 4 Port without Analog Mixer */
4705 case 0x111d76b7:
23c7b521 4706 unmute_init++;
541eee87 4707 break;
aafc4412 4708 case 0x111d7608: /* 5 Port with Analog Mixer */
8daaaa97 4709 if ((codec->revision_id & 0xf) == 0 ||
8c2f767b 4710 (codec->revision_id & 0xf) == 1)
8daaaa97 4711 spec->stream_delay = 40; /* 40 milliseconds */
8daaaa97 4712
aafc4412 4713 /* disable VSW */
ca8d33fc 4714 unmute_init++;
330ee995
TI
4715 snd_hda_codec_set_pincfg(codec, 0x0f, 0x40f000f0);
4716 snd_hda_codec_set_pincfg(codec, 0x19, 0x40f000f3);
aafc4412
MR
4717 break;
4718 case 0x111d7603: /* 6 Port with Analog Mixer */
8c2f767b 4719 if ((codec->revision_id & 0xf) == 1)
8daaaa97 4720 spec->stream_delay = 40; /* 40 milliseconds */
8daaaa97 4721
5207e10e 4722 break;
541eee87
MR
4723 }
4724
5e68fb3c 4725 if (get_wcaps_type(get_wcaps(codec, 0x28)) == AC_WID_VOL_KNB)
0f6fcb73 4726 snd_hda_add_verbs(codec, stac92hd71bxx_core_init);
5e68fb3c 4727
ca8d33fc
MR
4728 if (get_wcaps(codec, 0xa) & AC_WCAP_IN_AMP)
4729 snd_hda_sequence_write_cache(codec, unmute_init);
4730
36c9db7a 4731 spec->aloopback_ctl = &stac92hd71bxx_loopback;
4b33c767 4732 spec->aloopback_mask = 0x50;
541eee87
MR
4733 spec->aloopback_shift = 0;
4734
8daaaa97 4735 spec->powerdown_adcs = 1;
7504b6cd 4736 spec->gen.beep_nid = 0x26; /* digital beep */
36c9db7a 4737 spec->num_pwrs = ARRAY_SIZE(stac92hd71bxx_pwr_nids);
aafc4412 4738 spec->pwr_nids = stac92hd71bxx_pwr_nids;
e035b841 4739
36c9db7a
TI
4740 snd_hda_pick_fixup(codec, stac92hd71bxx_models, stac92hd71bxx_fixup_tbl,
4741 stac92hd71bxx_fixups);
0f6fcb73 4742 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
5bdaaada 4743
372f8c75 4744 stac_setup_gpio(codec);
6a14f585 4745
36c9db7a 4746 err = stac_parse_auto_config(codec);
e035b841 4747 if (err < 0) {
36c9db7a 4748 stac_free(codec);
e035b841
MR
4749 return err;
4750 }
4751
2d34e1b3
TI
4752 codec->proc_widget_hook = stac92hd7x_proc_hook;
4753
0f6fcb73
TI
4754 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4755
e035b841 4756 return 0;
86d190e7 4757}
e035b841 4758
2f2f4251
M
4759static int patch_stac922x(struct hda_codec *codec)
4760{
4761 struct sigmatel_spec *spec;
c7d4b2fa 4762 int err;
2f2f4251 4763
36c9db7a 4764 err = alloc_stac_spec(codec);
361dab3e
TI
4765 if (err < 0)
4766 return err;
2f2f4251 4767
361dab3e 4768 spec = codec->spec;
1b0e372d 4769 spec->linear_tone_beep = 1;
36c9db7a 4770 spec->gen.own_eapd_ctl = 1;
5d5d3bc3 4771
36c9db7a 4772 codec->patch_ops = stac_patch_ops;
c7d4b2fa 4773
0a427846
TI
4774 snd_hda_add_verbs(codec, stac922x_core_init);
4775
807a4636
TI
4776 /* Fix Mux capture level; max to 2 */
4777 snd_hda_override_amp_caps(codec, 0x12, HDA_OUTPUT,
4778 (0 << AC_AMPCAP_OFFSET_SHIFT) |
4779 (2 << AC_AMPCAP_NUM_STEPS_SHIFT) |
4780 (0x27 << AC_AMPCAP_STEP_SIZE_SHIFT) |
4781 (0 << AC_AMPCAP_MUTE_SHIFT));
4782
36c9db7a
TI
4783 snd_hda_pick_fixup(codec, stac922x_models, stac922x_fixup_tbl,
4784 stac922x_fixups);
4785 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
4786
4787 err = stac_parse_auto_config(codec);
4788 if (err < 0) {
4789 stac_free(codec);
4790 return err;
4791 }
4792
0a427846
TI
4793 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4794
3cc08dc6
MP
4795 return 0;
4796}
4797
42875479
TI
4798static const char * const stac927x_spdif_labels[] = {
4799 "Digital Playback", "ADAT", "Analog Mux 1",
4800 "Analog Mux 2", "Analog Mux 3", NULL
4801};
4802
3cc08dc6
MP
4803static int patch_stac927x(struct hda_codec *codec)
4804{
4805 struct sigmatel_spec *spec;
4806 int err;
4807
36c9db7a 4808 err = alloc_stac_spec(codec);
361dab3e
TI
4809 if (err < 0)
4810 return err;
3cc08dc6 4811
361dab3e 4812 spec = codec->spec;
1b0e372d 4813 spec->linear_tone_beep = 1;
36c9db7a 4814 spec->gen.own_eapd_ctl = 1;
42875479
TI
4815 spec->have_spdif_mux = 1;
4816 spec->spdif_labels = stac927x_spdif_labels;
3cc08dc6 4817
7504b6cd 4818 spec->gen.beep_nid = 0x23; /* digital beep */
8e9068b1 4819
29ac8363
TI
4820 /* GPIO0 High = Enable EAPD */
4821 spec->eapd_mask = spec->gpio_mask = 0x01;
4822 spec->gpio_dir = spec->gpio_data = 0x01;
af6ee302 4823
36c9db7a 4824 spec->aloopback_ctl = &stac927x_loopback;
e1f0d669
MR
4825 spec->aloopback_mask = 0x40;
4826 spec->aloopback_shift = 0;
c0cea0d0 4827 spec->eapd_switch = 1;
8e9068b1 4828
36c9db7a
TI
4829 codec->patch_ops = stac_patch_ops;
4830
4831 snd_hda_pick_fixup(codec, stac927x_models, stac927x_fixup_tbl,
4832 stac927x_fixups);
f6655d52
TI
4833 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
4834
29ac8363
TI
4835 if (!spec->volknob_init)
4836 snd_hda_add_verbs(codec, stac927x_core_init);
4837
36c9db7a 4838 err = stac_parse_auto_config(codec);
c7d4b2fa 4839 if (err < 0) {
36c9db7a 4840 stac_free(codec);
c7d4b2fa
M
4841 return err;
4842 }
2f2f4251 4843
2d34e1b3
TI
4844 codec->proc_widget_hook = stac927x_proc_hook;
4845
52987656
TI
4846 /*
4847 * !!FIXME!!
4848 * The STAC927x seem to require fairly long delays for certain
4849 * command sequences. With too short delays (even if the answer
4850 * is set to RIRB properly), it results in the silence output
4851 * on some hardwares like Dell.
4852 *
4853 * The below flag enables the longer delay (see get_response
4854 * in hda_intel.c).
4855 */
4856 codec->bus->needs_damn_long_delay = 1;
4857
29ac8363 4858 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
e28d8322 4859
2f2f4251
M
4860 return 0;
4861}
4862
f3302a59
MP
4863static int patch_stac9205(struct hda_codec *codec)
4864{
4865 struct sigmatel_spec *spec;
8259980e 4866 int err;
f3302a59 4867
36c9db7a 4868 err = alloc_stac_spec(codec);
361dab3e
TI
4869 if (err < 0)
4870 return err;
f3302a59 4871
361dab3e 4872 spec = codec->spec;
1b0e372d 4873 spec->linear_tone_beep = 1;
36c9db7a 4874 spec->gen.own_eapd_ctl = 1;
42875479 4875 spec->have_spdif_mux = 1;
f3302a59 4876
7504b6cd 4877 spec->gen.beep_nid = 0x23; /* digital beep */
f3302a59 4878
fe6322ca 4879 snd_hda_add_verbs(codec, stac9205_core_init);
36c9db7a 4880 spec->aloopback_ctl = &stac9205_loopback;
6479c631 4881
e1f0d669
MR
4882 spec->aloopback_mask = 0x40;
4883 spec->aloopback_shift = 0;
87d48363 4884
fe6322ca
TI
4885 /* GPIO0 High = EAPD */
4886 spec->eapd_mask = spec->gpio_mask = spec->gpio_dir = 0x1;
4887 spec->gpio_data = 0x01;
87d48363 4888
fe6322ca
TI
4889 /* Turn on/off EAPD per HP plugging */
4890 spec->eapd_switch = 1;
4fe5195c 4891
36c9db7a
TI
4892 codec->patch_ops = stac_patch_ops;
4893
4894 snd_hda_pick_fixup(codec, stac9205_models, stac9205_fixup_tbl,
4895 stac9205_fixups);
fe6322ca 4896 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
33382403 4897
36c9db7a 4898 err = stac_parse_auto_config(codec);
f3302a59 4899 if (err < 0) {
36c9db7a 4900 stac_free(codec);
f3302a59
MP
4901 return err;
4902 }
4903
2d34e1b3
TI
4904 codec->proc_widget_hook = stac9205_proc_hook;
4905
fe6322ca
TI
4906 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4907
f3302a59
MP
4908 return 0;
4909}
4910
db064e50 4911/*
6d859065 4912 * STAC9872 hack
db064e50
TI
4913 */
4914
2b63536f 4915static const struct hda_verb stac9872_core_init[] = {
1624cb9a 4916 {0x15, AC_VERB_SET_CONNECT_SEL, 0x1}, /* mic-sel: 0a,0d,14,02 */
6d859065
GM
4917 {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_UNMUTE}, /* Mic-in -> 0x9 */
4918 {}
4919};
4920
fc268c10
TI
4921static const struct hda_pintbl stac9872_vaio_pin_configs[] = {
4922 { 0x0a, 0x03211020 },
4923 { 0x0b, 0x411111f0 },
4924 { 0x0c, 0x411111f0 },
4925 { 0x0d, 0x03a15030 },
4926 { 0x0e, 0x411111f0 },
4927 { 0x0f, 0x90170110 },
4928 { 0x11, 0x411111f0 },
4929 { 0x13, 0x411111f0 },
4930 { 0x14, 0x90a7013e },
4931 {}
307282c8
TI
4932};
4933
fc268c10
TI
4934static const struct hda_model_fixup stac9872_models[] = {
4935 { .id = STAC_9872_VAIO, .name = "vaio" },
4936 {}
307282c8
TI
4937};
4938
fc268c10
TI
4939static const struct hda_fixup stac9872_fixups[] = {
4940 [STAC_9872_VAIO] = {
4941 .type = HDA_FIXUP_PINS,
4942 .v.pins = stac9872_vaio_pin_configs,
4943 },
307282c8
TI
4944};
4945
fc268c10 4946static const struct snd_pci_quirk stac9872_fixup_tbl[] = {
b04add95
TI
4947 SND_PCI_QUIRK_MASK(0x104d, 0xfff0, 0x81e0,
4948 "Sony VAIO F/S", STAC_9872_VAIO),
307282c8
TI
4949 {} /* terminator */
4950};
4951
6d859065 4952static int patch_stac9872(struct hda_codec *codec)
db064e50
TI
4953{
4954 struct sigmatel_spec *spec;
1e137f92 4955 int err;
db064e50 4956
36c9db7a 4957 err = alloc_stac_spec(codec);
361dab3e
TI
4958 if (err < 0)
4959 return err;
4960
4961 spec = codec->spec;
1b0e372d 4962 spec->linear_tone_beep = 1;
36c9db7a 4963 spec->gen.own_eapd_ctl = 1;
caa10b6e 4964
36c9db7a 4965 codec->patch_ops = stac_patch_ops;
db064e50 4966
fc268c10
TI
4967 snd_hda_add_verbs(codec, stac9872_core_init);
4968
36c9db7a
TI
4969 snd_hda_pick_fixup(codec, stac9872_models, stac9872_fixup_tbl,
4970 stac9872_fixups);
fc268c10 4971 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
1e137f92 4972
36c9db7a 4973 err = stac_parse_auto_config(codec);
1e137f92 4974 if (err < 0) {
36c9db7a 4975 stac_free(codec);
1e137f92
TI
4976 return -EINVAL;
4977 }
fc268c10
TI
4978
4979 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
4980
db064e50
TI
4981 return 0;
4982}
4983
4984
2f2f4251
M
4985/*
4986 * patch entries
4987 */
2b63536f 4988static const struct hda_codec_preset snd_hda_preset_sigmatel[] = {
2f2f4251
M
4989 { .id = 0x83847690, .name = "STAC9200", .patch = patch_stac9200 },
4990 { .id = 0x83847882, .name = "STAC9220 A1", .patch = patch_stac922x },
4991 { .id = 0x83847680, .name = "STAC9221 A1", .patch = patch_stac922x },
4992 { .id = 0x83847880, .name = "STAC9220 A2", .patch = patch_stac922x },
4993 { .id = 0x83847681, .name = "STAC9220D/9223D A2", .patch = patch_stac922x },
4994 { .id = 0x83847682, .name = "STAC9221 A2", .patch = patch_stac922x },
4995 { .id = 0x83847683, .name = "STAC9221D A2", .patch = patch_stac922x },
22a27c7f
MP
4996 { .id = 0x83847618, .name = "STAC9227", .patch = patch_stac927x },
4997 { .id = 0x83847619, .name = "STAC9227", .patch = patch_stac927x },
4998 { .id = 0x83847616, .name = "STAC9228", .patch = patch_stac927x },
4999 { .id = 0x83847617, .name = "STAC9228", .patch = patch_stac927x },
5000 { .id = 0x83847614, .name = "STAC9229", .patch = patch_stac927x },
5001 { .id = 0x83847615, .name = "STAC9229", .patch = patch_stac927x },
3cc08dc6
MP
5002 { .id = 0x83847620, .name = "STAC9274", .patch = patch_stac927x },
5003 { .id = 0x83847621, .name = "STAC9274D", .patch = patch_stac927x },
5004 { .id = 0x83847622, .name = "STAC9273X", .patch = patch_stac927x },
5005 { .id = 0x83847623, .name = "STAC9273D", .patch = patch_stac927x },
5006 { .id = 0x83847624, .name = "STAC9272X", .patch = patch_stac927x },
5007 { .id = 0x83847625, .name = "STAC9272D", .patch = patch_stac927x },
5008 { .id = 0x83847626, .name = "STAC9271X", .patch = patch_stac927x },
5009 { .id = 0x83847627, .name = "STAC9271D", .patch = patch_stac927x },
5010 { .id = 0x83847628, .name = "STAC9274X5NH", .patch = patch_stac927x },
5011 { .id = 0x83847629, .name = "STAC9274D5NH", .patch = patch_stac927x },
8e21c34c
TD
5012 { .id = 0x83847632, .name = "STAC9202", .patch = patch_stac925x },
5013 { .id = 0x83847633, .name = "STAC9202D", .patch = patch_stac925x },
5014 { .id = 0x83847634, .name = "STAC9250", .patch = patch_stac925x },
5015 { .id = 0x83847635, .name = "STAC9250D", .patch = patch_stac925x },
5016 { .id = 0x83847636, .name = "STAC9251", .patch = patch_stac925x },
5017 { .id = 0x83847637, .name = "STAC9250D", .patch = patch_stac925x },
7bd3c0f7
TI
5018 { .id = 0x83847645, .name = "92HD206X", .patch = patch_stac927x },
5019 { .id = 0x83847646, .name = "92HD206D", .patch = patch_stac927x },
6d859065
GM
5020 /* The following does not take into account .id=0x83847661 when subsys =
5021 * 104D0C00 which is STAC9225s. Because of this, some SZ Notebooks are
5022 * currently not fully supported.
5023 */
5024 { .id = 0x83847661, .name = "CXD9872RD/K", .patch = patch_stac9872 },
5025 { .id = 0x83847662, .name = "STAC9872AK", .patch = patch_stac9872 },
5026 { .id = 0x83847664, .name = "CXD9872AKD", .patch = patch_stac9872 },
a5c0f886 5027 { .id = 0x83847698, .name = "STAC9205", .patch = patch_stac9205 },
f3302a59
MP
5028 { .id = 0x838476a0, .name = "STAC9205", .patch = patch_stac9205 },
5029 { .id = 0x838476a1, .name = "STAC9205D", .patch = patch_stac9205 },
5030 { .id = 0x838476a2, .name = "STAC9204", .patch = patch_stac9205 },
5031 { .id = 0x838476a3, .name = "STAC9204D", .patch = patch_stac9205 },
5032 { .id = 0x838476a4, .name = "STAC9255", .patch = patch_stac9205 },
5033 { .id = 0x838476a5, .name = "STAC9255D", .patch = patch_stac9205 },
5034 { .id = 0x838476a6, .name = "STAC9254", .patch = patch_stac9205 },
5035 { .id = 0x838476a7, .name = "STAC9254D", .patch = patch_stac9205 },
aafc4412 5036 { .id = 0x111d7603, .name = "92HD75B3X5", .patch = patch_stac92hd71bxx},
d0513fc6 5037 { .id = 0x111d7604, .name = "92HD83C1X5", .patch = patch_stac92hd83xxx},
a9694faa 5038 { .id = 0x111d76d4, .name = "92HD83C1C5", .patch = patch_stac92hd83xxx},
d0513fc6 5039 { .id = 0x111d7605, .name = "92HD81B1X5", .patch = patch_stac92hd83xxx},
ff2e7337 5040 { .id = 0x111d76d5, .name = "92HD81B1C5", .patch = patch_stac92hd83xxx},
8a345a04
CC
5041 { .id = 0x111d76d1, .name = "92HD87B1/3", .patch = patch_stac92hd83xxx},
5042 { .id = 0x111d76d9, .name = "92HD87B2/4", .patch = patch_stac92hd83xxx},
36706005
CC
5043 { .id = 0x111d7666, .name = "92HD88B3", .patch = patch_stac92hd83xxx},
5044 { .id = 0x111d7667, .name = "92HD88B1", .patch = patch_stac92hd83xxx},
5045 { .id = 0x111d7668, .name = "92HD88B2", .patch = patch_stac92hd83xxx},
5046 { .id = 0x111d7669, .name = "92HD88B4", .patch = patch_stac92hd83xxx},
aafc4412 5047 { .id = 0x111d7608, .name = "92HD75B2X5", .patch = patch_stac92hd71bxx},
541eee87
MR
5048 { .id = 0x111d7674, .name = "92HD73D1X5", .patch = patch_stac92hd73xx },
5049 { .id = 0x111d7675, .name = "92HD73C1X5", .patch = patch_stac92hd73xx },
e1f0d669 5050 { .id = 0x111d7676, .name = "92HD73E1X5", .patch = patch_stac92hd73xx },
4e637c6e 5051 { .id = 0x111d7695, .name = "92HD95", .patch = patch_stac92hd95 },
541eee87
MR
5052 { .id = 0x111d76b0, .name = "92HD71B8X", .patch = patch_stac92hd71bxx },
5053 { .id = 0x111d76b1, .name = "92HD71B8X", .patch = patch_stac92hd71bxx },
5054 { .id = 0x111d76b2, .name = "92HD71B7X", .patch = patch_stac92hd71bxx },
5055 { .id = 0x111d76b3, .name = "92HD71B7X", .patch = patch_stac92hd71bxx },
5056 { .id = 0x111d76b4, .name = "92HD71B6X", .patch = patch_stac92hd71bxx },
5057 { .id = 0x111d76b5, .name = "92HD71B6X", .patch = patch_stac92hd71bxx },
5058 { .id = 0x111d76b6, .name = "92HD71B5X", .patch = patch_stac92hd71bxx },
5059 { .id = 0x111d76b7, .name = "92HD71B5X", .patch = patch_stac92hd71bxx },
4d8ec5f3
CC
5060 { .id = 0x111d76c0, .name = "92HD89C3", .patch = patch_stac92hd73xx },
5061 { .id = 0x111d76c1, .name = "92HD89C2", .patch = patch_stac92hd73xx },
5062 { .id = 0x111d76c2, .name = "92HD89C1", .patch = patch_stac92hd73xx },
5063 { .id = 0x111d76c3, .name = "92HD89B3", .patch = patch_stac92hd73xx },
5064 { .id = 0x111d76c4, .name = "92HD89B2", .patch = patch_stac92hd73xx },
5065 { .id = 0x111d76c5, .name = "92HD89B1", .patch = patch_stac92hd73xx },
5066 { .id = 0x111d76c6, .name = "92HD89E3", .patch = patch_stac92hd73xx },
5067 { .id = 0x111d76c7, .name = "92HD89E2", .patch = patch_stac92hd73xx },
5068 { .id = 0x111d76c8, .name = "92HD89E1", .patch = patch_stac92hd73xx },
5069 { .id = 0x111d76c9, .name = "92HD89D3", .patch = patch_stac92hd73xx },
5070 { .id = 0x111d76ca, .name = "92HD89D2", .patch = patch_stac92hd73xx },
5071 { .id = 0x111d76cb, .name = "92HD89D1", .patch = patch_stac92hd73xx },
5072 { .id = 0x111d76cc, .name = "92HD89F3", .patch = patch_stac92hd73xx },
5073 { .id = 0x111d76cd, .name = "92HD89F2", .patch = patch_stac92hd73xx },
5074 { .id = 0x111d76ce, .name = "92HD89F1", .patch = patch_stac92hd73xx },
46724c2e 5075 { .id = 0x111d76df, .name = "92HD93BXX", .patch = patch_stac92hd83xxx},
ab5a6ebe 5076 { .id = 0x111d76e0, .name = "92HD91BXX", .patch = patch_stac92hd83xxx},
4dfb8a45
VK
5077 { .id = 0x111d76e3, .name = "92HD98BXX", .patch = patch_stac92hd83xxx},
5078 { .id = 0x111d76e5, .name = "92HD99BXX", .patch = patch_stac92hd83xxx},
ab5a6ebe 5079 { .id = 0x111d76e7, .name = "92HD90BXX", .patch = patch_stac92hd83xxx},
ad5d8755
CC
5080 { .id = 0x111d76e8, .name = "92HD66B1X5", .patch = patch_stac92hd83xxx},
5081 { .id = 0x111d76e9, .name = "92HD66B2X5", .patch = patch_stac92hd83xxx},
5082 { .id = 0x111d76ea, .name = "92HD66B3X5", .patch = patch_stac92hd83xxx},
5083 { .id = 0x111d76eb, .name = "92HD66C1X5", .patch = patch_stac92hd83xxx},
5084 { .id = 0x111d76ec, .name = "92HD66C2X5", .patch = patch_stac92hd83xxx},
5085 { .id = 0x111d76ed, .name = "92HD66C3X5", .patch = patch_stac92hd83xxx},
5086 { .id = 0x111d76ee, .name = "92HD66B1X3", .patch = patch_stac92hd83xxx},
5087 { .id = 0x111d76ef, .name = "92HD66B2X3", .patch = patch_stac92hd83xxx},
5088 { .id = 0x111d76f0, .name = "92HD66B3X3", .patch = patch_stac92hd83xxx},
5089 { .id = 0x111d76f1, .name = "92HD66C1X3", .patch = patch_stac92hd83xxx},
5090 { .id = 0x111d76f2, .name = "92HD66C2X3", .patch = patch_stac92hd83xxx},
5091 { .id = 0x111d76f3, .name = "92HD66C3/65", .patch = patch_stac92hd83xxx},
2f2f4251
M
5092 {} /* terminator */
5093};
1289e9e8
TI
5094
5095MODULE_ALIAS("snd-hda-codec-id:8384*");
5096MODULE_ALIAS("snd-hda-codec-id:111d*");
5097
5098MODULE_LICENSE("GPL");
5099MODULE_DESCRIPTION("IDT/Sigmatel HD-audio codec");
5100
5101static struct hda_codec_preset_list sigmatel_list = {
5102 .preset = snd_hda_preset_sigmatel,
5103 .owner = THIS_MODULE,
5104};
5105
5106static int __init patch_sigmatel_init(void)
5107{
5108 return snd_hda_add_codec_preset(&sigmatel_list);
5109}
5110
5111static void __exit patch_sigmatel_exit(void)
5112{
5113 snd_hda_delete_codec_preset(&sigmatel_list);
5114}
5115
5116module_init(patch_sigmatel_init)
5117module_exit(patch_sigmatel_exit)