1
2
3
4
5
6
7
8
9#include <linux/init.h>
10#include <linux/slab.h>
11#include <linux/module.h>
12#include <sound/core.h>
13#include <linux/mutex.h>
14#include <linux/iopoll.h>
15
16#include "patch_cs8409.h"
17
18
19
20
21
22static int cs8409_parse_auto_config(struct hda_codec *codec)
23{
24 struct cs8409_spec *spec = codec->spec;
25 int err;
26 int i;
27
28 err = snd_hda_parse_pin_defcfg(codec, &spec->gen.autocfg, NULL, 0);
29 if (err < 0)
30 return err;
31
32 err = snd_hda_gen_parse_auto_config(codec, &spec->gen.autocfg);
33 if (err < 0)
34 return err;
35
36
37 if (spec->gen.dyn_adc_switch) {
38 unsigned int done = 0;
39
40 for (i = 0; i < spec->gen.input_mux.num_items; i++) {
41 int idx = spec->gen.dyn_adc_idx[i];
42
43 if (done & (1 << idx))
44 continue;
45 snd_hda_gen_fix_pin_power(codec, spec->gen.adc_nids[idx]);
46 done |= 1 << idx;
47 }
48 }
49
50 return 0;
51}
52
53static void cs8409_disable_i2c_clock_worker(struct work_struct *work);
54
55static struct cs8409_spec *cs8409_alloc_spec(struct hda_codec *codec)
56{
57 struct cs8409_spec *spec;
58
59 spec = kzalloc(sizeof(*spec), GFP_KERNEL);
60 if (!spec)
61 return NULL;
62 codec->spec = spec;
63 spec->codec = codec;
64 codec->power_save_node = 1;
65 mutex_init(&spec->i2c_mux);
66 INIT_DELAYED_WORK(&spec->i2c_clk_work, cs8409_disable_i2c_clock_worker);
67 snd_hda_gen_spec_init(&spec->gen);
68
69 return spec;
70}
71
72static inline int cs8409_vendor_coef_get(struct hda_codec *codec, unsigned int idx)
73{
74 snd_hda_codec_write(codec, CS8409_PIN_VENDOR_WIDGET, 0, AC_VERB_SET_COEF_INDEX, idx);
75 return snd_hda_codec_read(codec, CS8409_PIN_VENDOR_WIDGET, 0, AC_VERB_GET_PROC_COEF, 0);
76}
77
78static inline void cs8409_vendor_coef_set(struct hda_codec *codec, unsigned int idx,
79 unsigned int coef)
80{
81 snd_hda_codec_write(codec, CS8409_PIN_VENDOR_WIDGET, 0, AC_VERB_SET_COEF_INDEX, idx);
82 snd_hda_codec_write(codec, CS8409_PIN_VENDOR_WIDGET, 0, AC_VERB_SET_PROC_COEF, coef);
83}
84
85
86
87
88
89
90
91static void cs8409_disable_i2c_clock(struct hda_codec *codec)
92{
93 struct cs8409_spec *spec = codec->spec;
94
95 mutex_lock(&spec->i2c_mux);
96 if (spec->i2c_clck_enabled) {
97 cs8409_vendor_coef_set(spec->codec, 0x0,
98 cs8409_vendor_coef_get(spec->codec, 0x0) & 0xfffffff7);
99 spec->i2c_clck_enabled = 0;
100 }
101 mutex_unlock(&spec->i2c_mux);
102}
103
104
105
106
107static void cs8409_disable_i2c_clock_worker(struct work_struct *work)
108{
109 struct cs8409_spec *spec = container_of(work, struct cs8409_spec, i2c_clk_work.work);
110
111 cs8409_disable_i2c_clock(spec->codec);
112}
113
114
115
116
117
118
119
120static void cs8409_enable_i2c_clock(struct hda_codec *codec)
121{
122 struct cs8409_spec *spec = codec->spec;
123
124
125
126
127
128
129
130 cancel_delayed_work(&spec->i2c_clk_work);
131
132 if (!spec->i2c_clck_enabled) {
133 cs8409_vendor_coef_set(codec, 0x0, cs8409_vendor_coef_get(codec, 0x0) | 0x8);
134 spec->i2c_clck_enabled = 1;
135 }
136 queue_delayed_work(system_power_efficient_wq, &spec->i2c_clk_work, msecs_to_jiffies(25));
137}
138
139
140
141
142
143
144
145
146static int cs8409_i2c_wait_complete(struct hda_codec *codec)
147{
148 unsigned int retval;
149
150 return read_poll_timeout(cs8409_vendor_coef_get, retval, retval & 0x18,
151 CS42L42_I2C_SLEEP_US, CS42L42_I2C_TIMEOUT_US, false, codec, CS8409_I2C_STS);
152}
153
154
155
156
157
158
159static void cs8409_set_i2c_dev_addr(struct hda_codec *codec, unsigned int addr)
160{
161 struct cs8409_spec *spec = codec->spec;
162
163 if (spec->dev_addr != addr) {
164 cs8409_vendor_coef_set(codec, CS8409_I2C_ADDR, addr);
165 spec->dev_addr = addr;
166 }
167}
168
169
170
171
172
173
174
175
176static int cs8409_i2c_set_page(struct sub_codec *scodec, unsigned int i2c_reg)
177{
178 struct hda_codec *codec = scodec->codec;
179
180 if (scodec->paged && (scodec->last_page != (i2c_reg >> 8))) {
181 cs8409_vendor_coef_set(codec, CS8409_I2C_QWRITE, i2c_reg >> 8);
182 if (cs8409_i2c_wait_complete(codec) < 0)
183 return -EIO;
184 scodec->last_page = i2c_reg >> 8;
185 }
186
187 return 0;
188}
189
190
191
192
193
194
195
196
197static int cs8409_i2c_read(struct sub_codec *scodec, unsigned int addr)
198{
199 struct hda_codec *codec = scodec->codec;
200 struct cs8409_spec *spec = codec->spec;
201 unsigned int i2c_reg_data;
202 unsigned int read_data;
203
204 if (scodec->suspended)
205 return -EPERM;
206
207 mutex_lock(&spec->i2c_mux);
208 cs8409_enable_i2c_clock(codec);
209 cs8409_set_i2c_dev_addr(codec, scodec->addr);
210
211 if (cs8409_i2c_set_page(scodec, addr))
212 goto error;
213
214 i2c_reg_data = (addr << 8) & 0x0ffff;
215 cs8409_vendor_coef_set(codec, CS8409_I2C_QREAD, i2c_reg_data);
216 if (cs8409_i2c_wait_complete(codec) < 0)
217 goto error;
218
219
220 read_data = cs8409_vendor_coef_get(codec, CS8409_I2C_QREAD);
221
222 mutex_unlock(&spec->i2c_mux);
223
224 return read_data & 0x0ff;
225
226error:
227 mutex_unlock(&spec->i2c_mux);
228 codec_err(codec, "%s() Failed 0x%02x : 0x%04x\n", __func__, scodec->addr, addr);
229 return -EIO;
230}
231
232
233
234
235
236
237
238
239
240static int cs8409_i2c_bulk_read(struct sub_codec *scodec, struct cs8409_i2c_param *seq, int count)
241{
242 struct hda_codec *codec = scodec->codec;
243 struct cs8409_spec *spec = codec->spec;
244 unsigned int i2c_reg_data;
245 int i;
246
247 if (scodec->suspended)
248 return -EPERM;
249
250 mutex_lock(&spec->i2c_mux);
251 cs8409_set_i2c_dev_addr(codec, scodec->addr);
252
253 for (i = 0; i < count; i++) {
254 cs8409_enable_i2c_clock(codec);
255 if (cs8409_i2c_set_page(scodec, seq[i].addr))
256 goto error;
257
258 i2c_reg_data = (seq[i].addr << 8) & 0x0ffff;
259 cs8409_vendor_coef_set(codec, CS8409_I2C_QREAD, i2c_reg_data);
260
261 if (cs8409_i2c_wait_complete(codec) < 0)
262 goto error;
263
264 seq[i].value = cs8409_vendor_coef_get(codec, CS8409_I2C_QREAD) & 0xff;
265 }
266
267 mutex_unlock(&spec->i2c_mux);
268
269 return 0;
270
271error:
272 mutex_unlock(&spec->i2c_mux);
273 codec_err(codec, "I2C Bulk Write Failed 0x%02x\n", scodec->addr);
274 return -EIO;
275}
276
277
278
279
280
281
282
283
284
285static int cs8409_i2c_write(struct sub_codec *scodec, unsigned int addr, unsigned int value)
286{
287 struct hda_codec *codec = scodec->codec;
288 struct cs8409_spec *spec = codec->spec;
289 unsigned int i2c_reg_data;
290
291 if (scodec->suspended)
292 return -EPERM;
293
294 mutex_lock(&spec->i2c_mux);
295
296 cs8409_enable_i2c_clock(codec);
297 cs8409_set_i2c_dev_addr(codec, scodec->addr);
298
299 if (cs8409_i2c_set_page(scodec, addr))
300 goto error;
301
302 i2c_reg_data = ((addr << 8) & 0x0ff00) | (value & 0x0ff);
303 cs8409_vendor_coef_set(codec, CS8409_I2C_QWRITE, i2c_reg_data);
304
305 if (cs8409_i2c_wait_complete(codec) < 0)
306 goto error;
307
308 mutex_unlock(&spec->i2c_mux);
309 return 0;
310
311error:
312 mutex_unlock(&spec->i2c_mux);
313 codec_err(codec, "%s() Failed 0x%02x : 0x%04x\n", __func__, scodec->addr, addr);
314 return -EIO;
315}
316
317
318
319
320
321
322
323
324
325static int cs8409_i2c_bulk_write(struct sub_codec *scodec, const struct cs8409_i2c_param *seq,
326 int count)
327{
328 struct hda_codec *codec = scodec->codec;
329 struct cs8409_spec *spec = codec->spec;
330 unsigned int i2c_reg_data;
331 int i;
332
333 if (scodec->suspended)
334 return -EPERM;
335
336 mutex_lock(&spec->i2c_mux);
337 cs8409_set_i2c_dev_addr(codec, scodec->addr);
338
339 for (i = 0; i < count; i++) {
340 cs8409_enable_i2c_clock(codec);
341 if (cs8409_i2c_set_page(scodec, seq[i].addr))
342 goto error;
343
344 i2c_reg_data = ((seq[i].addr << 8) & 0x0ff00) | (seq[i].value & 0x0ff);
345 cs8409_vendor_coef_set(codec, CS8409_I2C_QWRITE, i2c_reg_data);
346
347 if (cs8409_i2c_wait_complete(codec) < 0)
348 goto error;
349 }
350
351 mutex_unlock(&spec->i2c_mux);
352
353 return 0;
354
355error:
356 mutex_unlock(&spec->i2c_mux);
357 codec_err(codec, "I2C Bulk Write Failed 0x%02x\n", scodec->addr);
358 return -EIO;
359}
360
361static int cs8409_init(struct hda_codec *codec)
362{
363 int ret = snd_hda_gen_init(codec);
364
365 if (!ret)
366 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_INIT);
367
368 return ret;
369}
370
371static int cs8409_build_controls(struct hda_codec *codec)
372{
373 int err;
374
375 err = snd_hda_gen_build_controls(codec);
376 if (err < 0)
377 return err;
378 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_BUILD);
379
380 return 0;
381}
382
383
384static void cs8409_enable_ur(struct hda_codec *codec, int flag)
385{
386 struct cs8409_spec *spec = codec->spec;
387 unsigned int ur_gpios = 0;
388 int i;
389
390 for (i = 0; i < spec->num_scodecs; i++)
391 ur_gpios |= spec->scodecs[i]->irq_mask;
392
393 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_UNSOLICITED_RSP_MASK,
394 flag ? ur_gpios : 0);
395
396 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_UNSOLICITED_ENABLE,
397 flag ? AC_UNSOL_ENABLED : 0);
398}
399
400static void cs8409_fix_caps(struct hda_codec *codec, unsigned int nid)
401{
402 int caps;
403
404
405
406
407
408
409
410
411
412
413
414 caps = snd_hdac_read_parm(&codec->core, nid, AC_PAR_PIN_CAP);
415 if (caps >= 0)
416 snd_hdac_override_parm(&codec->core, nid, AC_PAR_PIN_CAP,
417 (caps | (AC_PINCAP_IMP_SENSE | AC_PINCAP_PRES_DETECT)));
418
419 snd_hda_override_wcaps(codec, nid, (get_wcaps(codec, nid) | AC_WCAP_UNSOL_CAP));
420}
421
422
423
424
425
426int cs42l42_volume_info(struct snd_kcontrol *kctrl, struct snd_ctl_elem_info *uinfo)
427{
428 unsigned int ofs = get_amp_offset(kctrl);
429 u8 chs = get_amp_channels(kctrl);
430
431 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
432 uinfo->value.integer.step = 1;
433 uinfo->count = chs == 3 ? 2 : 1;
434
435 switch (ofs) {
436 case CS42L42_VOL_DAC:
437 uinfo->value.integer.min = CS42L42_HP_VOL_REAL_MIN;
438 uinfo->value.integer.max = CS42L42_HP_VOL_REAL_MAX;
439 break;
440 case CS42L42_VOL_ADC:
441 uinfo->value.integer.min = CS42L42_AMIC_VOL_REAL_MIN;
442 uinfo->value.integer.max = CS42L42_AMIC_VOL_REAL_MAX;
443 break;
444 default:
445 break;
446 }
447
448 return 0;
449}
450
451int cs42l42_volume_get(struct snd_kcontrol *kctrl, struct snd_ctl_elem_value *uctrl)
452{
453 struct hda_codec *codec = snd_kcontrol_chip(kctrl);
454 struct cs8409_spec *spec = codec->spec;
455 struct sub_codec *cs42l42 = spec->scodecs[get_amp_index(kctrl)];
456 int chs = get_amp_channels(kctrl);
457 unsigned int ofs = get_amp_offset(kctrl);
458 long *valp = uctrl->value.integer.value;
459
460 switch (ofs) {
461 case CS42L42_VOL_DAC:
462 if (chs & BIT(0))
463 *valp++ = cs42l42->vol[ofs];
464 if (chs & BIT(1))
465 *valp = cs42l42->vol[ofs+1];
466 break;
467 case CS42L42_VOL_ADC:
468 if (chs & BIT(0))
469 *valp = cs42l42->vol[ofs];
470 break;
471 default:
472 break;
473 }
474
475 return 0;
476}
477
478static void cs42l42_mute(struct sub_codec *cs42l42, int vol_type,
479 unsigned int chs, bool mute)
480{
481 if (mute) {
482 if (vol_type == CS42L42_VOL_DAC) {
483 if (chs & BIT(0))
484 cs8409_i2c_write(cs42l42, CS42L42_REG_HS_VOL_CHA, 0x3f);
485 if (chs & BIT(1))
486 cs8409_i2c_write(cs42l42, CS42L42_REG_HS_VOL_CHB, 0x3f);
487 } else if (vol_type == CS42L42_VOL_ADC) {
488 if (chs & BIT(0))
489 cs8409_i2c_write(cs42l42, CS42L42_REG_AMIC_VOL, 0x9f);
490 }
491 } else {
492 if (vol_type == CS42L42_VOL_DAC) {
493 if (chs & BIT(0))
494 cs8409_i2c_write(cs42l42, CS42L42_REG_HS_VOL_CHA,
495 -(cs42l42->vol[CS42L42_DAC_CH0_VOL_OFFSET])
496 & CS42L42_REG_HS_VOL_MASK);
497 if (chs & BIT(1))
498 cs8409_i2c_write(cs42l42, CS42L42_REG_HS_VOL_CHB,
499 -(cs42l42->vol[CS42L42_DAC_CH1_VOL_OFFSET])
500 & CS42L42_REG_HS_VOL_MASK);
501 } else if (vol_type == CS42L42_VOL_ADC) {
502 if (chs & BIT(0))
503 cs8409_i2c_write(cs42l42, CS42L42_REG_AMIC_VOL,
504 cs42l42->vol[CS42L42_ADC_VOL_OFFSET]
505 & CS42L42_REG_AMIC_VOL_MASK);
506 }
507 }
508}
509
510int cs42l42_volume_put(struct snd_kcontrol *kctrl, struct snd_ctl_elem_value *uctrl)
511{
512 struct hda_codec *codec = snd_kcontrol_chip(kctrl);
513 struct cs8409_spec *spec = codec->spec;
514 struct sub_codec *cs42l42 = spec->scodecs[get_amp_index(kctrl)];
515 int chs = get_amp_channels(kctrl);
516 unsigned int ofs = get_amp_offset(kctrl);
517 long *valp = uctrl->value.integer.value;
518
519 switch (ofs) {
520 case CS42L42_VOL_DAC:
521 if (chs & BIT(0))
522 cs42l42->vol[ofs] = *valp;
523 if (chs & BIT(1)) {
524 valp++;
525 cs42l42->vol[ofs + 1] = *valp;
526 }
527 if (spec->playback_started)
528 cs42l42_mute(cs42l42, CS42L42_VOL_DAC, chs, false);
529 break;
530 case CS42L42_VOL_ADC:
531 if (chs & BIT(0))
532 cs42l42->vol[ofs] = *valp;
533 if (spec->capture_started)
534 cs42l42_mute(cs42l42, CS42L42_VOL_ADC, chs, false);
535 break;
536 default:
537 break;
538 }
539
540 return 0;
541}
542
543static void cs42l42_playback_pcm_hook(struct hda_pcm_stream *hinfo,
544 struct hda_codec *codec,
545 struct snd_pcm_substream *substream,
546 int action)
547{
548 struct cs8409_spec *spec = codec->spec;
549 struct sub_codec *cs42l42;
550 int i;
551 bool mute;
552
553 switch (action) {
554 case HDA_GEN_PCM_ACT_PREPARE:
555 mute = false;
556 spec->playback_started = 1;
557 break;
558 case HDA_GEN_PCM_ACT_CLEANUP:
559 mute = true;
560 spec->playback_started = 0;
561 break;
562 default:
563 return;
564 }
565
566 for (i = 0; i < spec->num_scodecs; i++) {
567 cs42l42 = spec->scodecs[i];
568 cs42l42_mute(cs42l42, CS42L42_VOL_DAC, 0x3, mute);
569 }
570}
571
572static void cs42l42_capture_pcm_hook(struct hda_pcm_stream *hinfo,
573 struct hda_codec *codec,
574 struct snd_pcm_substream *substream,
575 int action)
576{
577 struct cs8409_spec *spec = codec->spec;
578 struct sub_codec *cs42l42;
579 int i;
580 bool mute;
581
582 switch (action) {
583 case HDA_GEN_PCM_ACT_PREPARE:
584 mute = false;
585 spec->capture_started = 1;
586 break;
587 case HDA_GEN_PCM_ACT_CLEANUP:
588 mute = true;
589 spec->capture_started = 0;
590 break;
591 default:
592 return;
593 }
594
595 for (i = 0; i < spec->num_scodecs; i++) {
596 cs42l42 = spec->scodecs[i];
597 cs42l42_mute(cs42l42, CS42L42_VOL_ADC, 0x3, mute);
598 }
599}
600
601
602static void cs42l42_enable_jack_detect(struct sub_codec *cs42l42)
603{
604 cs8409_i2c_write(cs42l42, 0x1b70, cs42l42->hsbias_hiz);
605
606 cs8409_i2c_write(cs42l42, 0x1b71, 0x00C1);
607
608 usleep_range(2500, 3000);
609
610 cs8409_i2c_write(cs42l42, 0x1b71, 0x00C0);
611
612 cs8409_i2c_read(cs42l42, 0x130f);
613
614 cs8409_i2c_write(cs42l42, 0x1320, 0xF3);
615}
616
617
618static void cs42l42_run_jack_detect(struct sub_codec *cs42l42)
619{
620
621 cs8409_i2c_read(cs42l42, 0x1308);
622 cs8409_i2c_read(cs42l42, 0x1b77);
623 cs8409_i2c_write(cs42l42, 0x1320, 0xFF);
624 cs8409_i2c_read(cs42l42, 0x130f);
625
626 cs8409_i2c_write(cs42l42, 0x1102, 0x87);
627 cs8409_i2c_write(cs42l42, 0x1f06, 0x86);
628 cs8409_i2c_write(cs42l42, 0x1b74, 0x07);
629 cs8409_i2c_write(cs42l42, 0x131b, 0xFD);
630 cs8409_i2c_write(cs42l42, 0x1120, 0x80);
631
632 usleep_range(100, 200);
633 cs8409_i2c_write(cs42l42, 0x111f, 0x77);
634 cs8409_i2c_write(cs42l42, 0x1120, 0xc0);
635}
636
637static int cs42l42_handle_tip_sense(struct sub_codec *cs42l42, unsigned int reg_ts_status)
638{
639 int status_changed = 0;
640
641
642 switch (reg_ts_status) {
643 case CS42L42_JACK_INSERTED:
644 if (!cs42l42->hp_jack_in) {
645 if (cs42l42->no_type_dect) {
646 status_changed = 1;
647 cs42l42->hp_jack_in = 1;
648 cs42l42->mic_jack_in = 0;
649 } else {
650 cs42l42_run_jack_detect(cs42l42);
651 }
652 }
653 break;
654
655 case CS42L42_JACK_REMOVED:
656 if (cs42l42->hp_jack_in || cs42l42->mic_jack_in) {
657 status_changed = 1;
658 cs42l42->hp_jack_in = 0;
659 cs42l42->mic_jack_in = 0;
660 }
661 break;
662 default:
663
664 break;
665 }
666
667 return status_changed;
668}
669
670static int cs42l42_jack_unsol_event(struct sub_codec *cs42l42)
671{
672 int status_changed = 0;
673 int reg_cdc_status;
674 int reg_hs_status;
675 int reg_ts_status;
676 int type;
677
678
679 reg_cdc_status = cs8409_i2c_read(cs42l42, 0x1308);
680 reg_hs_status = cs8409_i2c_read(cs42l42, 0x1124);
681 reg_ts_status = cs8409_i2c_read(cs42l42, 0x130f);
682
683
684 if (reg_cdc_status < 0 || reg_hs_status < 0 || reg_ts_status < 0)
685 return -EIO;
686
687
688 if (reg_cdc_status & CS42L42_HSDET_AUTO_DONE) {
689
690
691 cs8409_i2c_write(cs42l42, 0x131b, 0xFF);
692
693 type = ((reg_hs_status & CS42L42_HSTYPE_MASK) + 1);
694
695 if (cs42l42->no_type_dect) {
696 status_changed = cs42l42_handle_tip_sense(cs42l42, reg_ts_status);
697 } else if (type == 4) {
698
699 status_changed = cs42l42_handle_tip_sense(cs42l42, CS42L42_JACK_REMOVED);
700 } else {
701 if (!cs42l42->hp_jack_in) {
702 status_changed = 1;
703 cs42l42->hp_jack_in = 1;
704 }
705
706 if ((!cs42l42->mic_jack_in) && (type != 3)) {
707 status_changed = 1;
708 cs42l42->mic_jack_in = 1;
709 }
710 }
711
712 cs8409_i2c_write(cs42l42, 0x1120, 0x80);
713
714 cs8409_i2c_write(cs42l42, 0x1F06, 0x02);
715
716 cs8409_i2c_write(cs42l42, 0x1320, 0xF3);
717 } else {
718 status_changed = cs42l42_handle_tip_sense(cs42l42, reg_ts_status);
719 }
720
721 return status_changed;
722}
723
724static void cs42l42_resume(struct sub_codec *cs42l42)
725{
726 struct hda_codec *codec = cs42l42->codec;
727 unsigned int gpio_data;
728 struct cs8409_i2c_param irq_regs[] = {
729 { 0x1308, 0x00 },
730 { 0x1309, 0x00 },
731 { 0x130A, 0x00 },
732 { 0x130F, 0x00 },
733 };
734
735
736 gpio_data = snd_hda_codec_read(codec, CS8409_PIN_AFG, 0, AC_VERB_GET_GPIO_DATA, 0);
737 gpio_data |= cs42l42->reset_gpio;
738 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DATA, gpio_data);
739 usleep_range(10000, 15000);
740
741 cs42l42->suspended = 0;
742
743
744 cs8409_i2c_bulk_write(cs42l42, cs42l42->init_seq, cs42l42->init_seq_num);
745 usleep_range(20000, 25000);
746
747
748 cs8409_i2c_bulk_read(cs42l42, irq_regs, ARRAY_SIZE(irq_regs));
749
750 if (cs42l42->full_scale_vol)
751 cs8409_i2c_write(cs42l42, 0x2001, 0x01);
752
753
754
755
756 snd_hda_codec_allow_unsol_events(cs42l42->codec);
757
758 cs42l42_enable_jack_detect(cs42l42);
759}
760
761#ifdef CONFIG_PM
762static void cs42l42_suspend(struct sub_codec *cs42l42)
763{
764 struct hda_codec *codec = cs42l42->codec;
765 unsigned int gpio_data;
766 int reg_cdc_status = 0;
767 const struct cs8409_i2c_param cs42l42_pwr_down_seq[] = {
768 { 0x1F06, 0x02 },
769 { 0x1129, 0x00 },
770 { 0x2301, 0x3F },
771 { 0x2302, 0x3F },
772 { 0x2303, 0x3F },
773 { 0x2001, 0x0F },
774 { 0x2A01, 0x00 },
775 { 0x1207, 0x00 },
776 { 0x1101, 0xFE },
777 { 0x1102, 0x8C },
778 { 0x1101, 0xFF },
779 };
780
781 cs8409_i2c_bulk_write(cs42l42, cs42l42_pwr_down_seq, ARRAY_SIZE(cs42l42_pwr_down_seq));
782
783 if (read_poll_timeout(cs8409_i2c_read, reg_cdc_status,
784 (reg_cdc_status & 0x1), CS42L42_PDN_SLEEP_US, CS42L42_PDN_TIMEOUT_US,
785 true, cs42l42, 0x1308) < 0)
786 codec_warn(codec, "Timeout waiting for PDN_DONE for CS42L42\n");
787
788
789 cs8409_i2c_write(cs42l42, 0x1102, 0x9C);
790 cs42l42->suspended = 1;
791 cs42l42->last_page = 0;
792 cs42l42->hp_jack_in = 0;
793 cs42l42->mic_jack_in = 0;
794
795
796 gpio_data = snd_hda_codec_read(codec, CS8409_PIN_AFG, 0, AC_VERB_GET_GPIO_DATA, 0);
797 gpio_data &= ~cs42l42->reset_gpio;
798 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DATA, gpio_data);
799}
800#endif
801
802static void cs8409_free(struct hda_codec *codec)
803{
804 struct cs8409_spec *spec = codec->spec;
805
806
807 cancel_delayed_work_sync(&spec->i2c_clk_work);
808 cs8409_disable_i2c_clock(codec);
809
810 snd_hda_gen_free(codec);
811}
812
813
814
815
816
817
818
819
820
821
822
823
824
825static void cs8409_cs42l42_jack_unsol_event(struct hda_codec *codec, unsigned int res)
826{
827 struct cs8409_spec *spec = codec->spec;
828 struct sub_codec *cs42l42 = spec->scodecs[CS8409_CODEC0];
829 struct hda_jack_tbl *jk;
830
831
832
833
834
835
836 if (res & cs42l42->irq_mask)
837 return;
838
839 if (cs42l42_jack_unsol_event(cs42l42)) {
840 snd_hda_set_pin_ctl(codec, CS8409_CS42L42_SPK_PIN_NID,
841 cs42l42->hp_jack_in ? 0 : PIN_OUT);
842
843 jk = snd_hda_jack_tbl_get_mst(codec, CS8409_CS42L42_HP_PIN_NID, 0);
844 if (jk)
845 snd_hda_jack_unsol_event(codec, (jk->tag << AC_UNSOL_RES_TAG_SHIFT) &
846 AC_UNSOL_RES_TAG);
847
848 jk = snd_hda_jack_tbl_get_mst(codec, CS8409_CS42L42_AMIC_PIN_NID, 0);
849 if (jk)
850 snd_hda_jack_unsol_event(codec, (jk->tag << AC_UNSOL_RES_TAG_SHIFT) &
851 AC_UNSOL_RES_TAG);
852 }
853}
854
855#ifdef CONFIG_PM
856
857static int cs8409_cs42l42_suspend(struct hda_codec *codec)
858{
859 struct cs8409_spec *spec = codec->spec;
860 int i;
861
862 spec->init_done = 0;
863
864 cs8409_enable_ur(codec, 0);
865
866 for (i = 0; i < spec->num_scodecs; i++)
867 cs42l42_suspend(spec->scodecs[i]);
868
869
870 cancel_delayed_work_sync(&spec->i2c_clk_work);
871 cs8409_disable_i2c_clock(codec);
872
873 snd_hda_shutup_pins(codec);
874
875 return 0;
876}
877#endif
878
879
880
881
882static void cs8409_cs42l42_hw_init(struct hda_codec *codec)
883{
884 const struct cs8409_cir_param *seq = cs8409_cs42l42_hw_cfg;
885 const struct cs8409_cir_param *seq_bullseye = cs8409_cs42l42_bullseye_atn;
886 struct cs8409_spec *spec = codec->spec;
887 struct sub_codec *cs42l42 = spec->scodecs[CS8409_CODEC0];
888
889 if (spec->gpio_mask) {
890 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_MASK,
891 spec->gpio_mask);
892 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DIRECTION,
893 spec->gpio_dir);
894 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DATA,
895 spec->gpio_data);
896 }
897
898 for (; seq->nid; seq++)
899 cs8409_vendor_coef_set(codec, seq->cir, seq->coeff);
900
901 if (codec->fixup_id == CS8409_BULLSEYE) {
902 for (; seq_bullseye->nid; seq_bullseye++)
903 cs8409_vendor_coef_set(codec, seq_bullseye->cir, seq_bullseye->coeff);
904 }
905
906
907 if (codec->fixup_id == CS8409_WARLOCK || codec->fixup_id == CS8409_CYBORG)
908 cs8409_vendor_coef_set(codec, 0x09, 0x0003);
909
910 cs42l42_resume(cs42l42);
911
912
913 cs8409_enable_ur(codec, 1);
914}
915
916static const struct hda_codec_ops cs8409_cs42l42_patch_ops = {
917 .build_controls = cs8409_build_controls,
918 .build_pcms = snd_hda_gen_build_pcms,
919 .init = cs8409_init,
920 .free = cs8409_free,
921 .unsol_event = cs8409_cs42l42_jack_unsol_event,
922#ifdef CONFIG_PM
923 .suspend = cs8409_cs42l42_suspend,
924#endif
925};
926
927static int cs8409_cs42l42_exec_verb(struct hdac_device *dev, unsigned int cmd, unsigned int flags,
928 unsigned int *res)
929{
930 struct hda_codec *codec = container_of(dev, struct hda_codec, core);
931 struct cs8409_spec *spec = codec->spec;
932 struct sub_codec *cs42l42 = spec->scodecs[CS8409_CODEC0];
933
934 unsigned int nid = ((cmd >> 20) & 0x07f);
935 unsigned int verb = ((cmd >> 8) & 0x0fff);
936
937
938
939
940
941
942 switch (nid) {
943 case CS8409_CS42L42_HP_PIN_NID:
944 if (verb == AC_VERB_GET_PIN_SENSE) {
945 *res = (cs42l42->hp_jack_in) ? AC_PINSENSE_PRESENCE : 0;
946 return 0;
947 }
948 break;
949 case CS8409_CS42L42_AMIC_PIN_NID:
950 if (verb == AC_VERB_GET_PIN_SENSE) {
951 *res = (cs42l42->mic_jack_in) ? AC_PINSENSE_PRESENCE : 0;
952 return 0;
953 }
954 break;
955 default:
956 break;
957 }
958
959 return spec->exec_verb(dev, cmd, flags, res);
960}
961
962void cs8409_cs42l42_fixups(struct hda_codec *codec, const struct hda_fixup *fix, int action)
963{
964 struct cs8409_spec *spec = codec->spec;
965
966 switch (action) {
967 case HDA_FIXUP_ACT_PRE_PROBE:
968 snd_hda_add_verbs(codec, cs8409_cs42l42_init_verbs);
969
970 spec->exec_verb = codec->core.exec_verb;
971 codec->core.exec_verb = cs8409_cs42l42_exec_verb;
972
973 spec->scodecs[CS8409_CODEC0] = &cs8409_cs42l42_codec;
974 spec->num_scodecs = 1;
975 spec->scodecs[CS8409_CODEC0]->codec = codec;
976 codec->patch_ops = cs8409_cs42l42_patch_ops;
977
978 spec->gen.suppress_auto_mute = 1;
979 spec->gen.no_primary_hp = 1;
980 spec->gen.suppress_vmaster = 1;
981
982
983 spec->gpio_dir = spec->scodecs[CS8409_CODEC0]->reset_gpio;
984 spec->gpio_data = 0;
985 spec->gpio_mask = 0x03f;
986
987
988 snd_hda_sequence_write(codec, cs8409_cs42l42_init_verbs);
989
990 cs8409_fix_caps(codec, CS8409_CS42L42_HP_PIN_NID);
991 cs8409_fix_caps(codec, CS8409_CS42L42_AMIC_PIN_NID);
992
993
994
995
996 switch (codec->fixup_id) {
997 case CS8409_WARLOCK:
998 spec->scodecs[CS8409_CODEC0]->hsbias_hiz = 0x0020;
999 spec->scodecs[CS8409_CODEC0]->full_scale_vol = 1;
1000 break;
1001 case CS8409_BULLSEYE:
1002 spec->scodecs[CS8409_CODEC0]->hsbias_hiz = 0x0020;
1003 spec->scodecs[CS8409_CODEC0]->full_scale_vol = 0;
1004 break;
1005 case CS8409_CYBORG:
1006 spec->scodecs[CS8409_CODEC0]->hsbias_hiz = 0x00a0;
1007 spec->scodecs[CS8409_CODEC0]->full_scale_vol = 1;
1008 break;
1009 default:
1010 spec->scodecs[CS8409_CODEC0]->hsbias_hiz = 0x0003;
1011 spec->scodecs[CS8409_CODEC0]->full_scale_vol = 1;
1012 break;
1013 }
1014
1015 break;
1016 case HDA_FIXUP_ACT_PROBE:
1017
1018 spec->gen.stream_analog_playback = &cs42l42_48k_pcm_analog_playback;
1019 spec->gen.stream_analog_capture = &cs42l42_48k_pcm_analog_capture;
1020
1021 spec->gen.pcm_playback_hook = cs42l42_playback_pcm_hook;
1022 spec->gen.pcm_capture_hook = cs42l42_capture_pcm_hook;
1023
1024 snd_hda_codec_amp_init_stereo(codec, CS8409_CS42L42_DMIC_ADC_PIN_NID,
1025 HDA_INPUT, 0, 0xff, 0x19);
1026 snd_hda_gen_add_kctl(&spec->gen, "Headphone Playback Volume",
1027 &cs42l42_dac_volume_mixer);
1028 snd_hda_gen_add_kctl(&spec->gen, "Mic Capture Volume",
1029 &cs42l42_adc_volume_mixer);
1030
1031 cs8409_enable_ur(codec, 0);
1032 snd_hda_codec_set_name(codec, "CS8409/CS42L42");
1033 break;
1034 case HDA_FIXUP_ACT_INIT:
1035 cs8409_cs42l42_hw_init(codec);
1036 spec->init_done = 1;
1037 if (spec->init_done && spec->build_ctrl_done
1038 && !spec->scodecs[CS8409_CODEC0]->hp_jack_in)
1039 cs42l42_run_jack_detect(spec->scodecs[CS8409_CODEC0]);
1040 break;
1041 case HDA_FIXUP_ACT_BUILD:
1042 spec->build_ctrl_done = 1;
1043
1044
1045
1046
1047
1048 if (spec->init_done && spec->build_ctrl_done
1049 && !spec->scodecs[CS8409_CODEC0]->hp_jack_in)
1050 cs42l42_run_jack_detect(spec->scodecs[CS8409_CODEC0]);
1051 break;
1052 default:
1053 break;
1054 }
1055}
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069static void dolphin_jack_unsol_event(struct hda_codec *codec, unsigned int res)
1070{
1071 struct cs8409_spec *spec = codec->spec;
1072 struct sub_codec *cs42l42;
1073 struct hda_jack_tbl *jk;
1074
1075 cs42l42 = spec->scodecs[CS8409_CODEC0];
1076 if (!cs42l42->suspended && (~res & cs42l42->irq_mask) &&
1077 cs42l42_jack_unsol_event(cs42l42)) {
1078 jk = snd_hda_jack_tbl_get_mst(codec, DOLPHIN_HP_PIN_NID, 0);
1079 if (jk)
1080 snd_hda_jack_unsol_event(codec,
1081 (jk->tag << AC_UNSOL_RES_TAG_SHIFT) &
1082 AC_UNSOL_RES_TAG);
1083
1084 jk = snd_hda_jack_tbl_get_mst(codec, DOLPHIN_AMIC_PIN_NID, 0);
1085 if (jk)
1086 snd_hda_jack_unsol_event(codec,
1087 (jk->tag << AC_UNSOL_RES_TAG_SHIFT) &
1088 AC_UNSOL_RES_TAG);
1089 }
1090
1091 cs42l42 = spec->scodecs[CS8409_CODEC1];
1092 if (!cs42l42->suspended && (~res & cs42l42->irq_mask) &&
1093 cs42l42_jack_unsol_event(cs42l42)) {
1094 jk = snd_hda_jack_tbl_get_mst(codec, DOLPHIN_LO_PIN_NID, 0);
1095 if (jk)
1096 snd_hda_jack_unsol_event(codec,
1097 (jk->tag << AC_UNSOL_RES_TAG_SHIFT) &
1098 AC_UNSOL_RES_TAG);
1099 }
1100}
1101
1102
1103
1104
1105static void dolphin_hw_init(struct hda_codec *codec)
1106{
1107 const struct cs8409_cir_param *seq = dolphin_hw_cfg;
1108 struct cs8409_spec *spec = codec->spec;
1109 struct sub_codec *cs42l42;
1110 int i;
1111
1112 if (spec->gpio_mask) {
1113 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_MASK,
1114 spec->gpio_mask);
1115 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DIRECTION,
1116 spec->gpio_dir);
1117 snd_hda_codec_write(codec, CS8409_PIN_AFG, 0, AC_VERB_SET_GPIO_DATA,
1118 spec->gpio_data);
1119 }
1120
1121 for (; seq->nid; seq++)
1122 cs8409_vendor_coef_set(codec, seq->cir, seq->coeff);
1123
1124 for (i = 0; i < spec->num_scodecs; i++) {
1125 cs42l42 = spec->scodecs[i];
1126 cs42l42_resume(cs42l42);
1127 }
1128
1129
1130 cs8409_enable_ur(codec, 1);
1131}
1132
1133static const struct hda_codec_ops cs8409_dolphin_patch_ops = {
1134 .build_controls = cs8409_build_controls,
1135 .build_pcms = snd_hda_gen_build_pcms,
1136 .init = cs8409_init,
1137 .free = cs8409_free,
1138 .unsol_event = dolphin_jack_unsol_event,
1139#ifdef CONFIG_PM
1140 .suspend = cs8409_cs42l42_suspend,
1141#endif
1142};
1143
1144static int dolphin_exec_verb(struct hdac_device *dev, unsigned int cmd, unsigned int flags,
1145 unsigned int *res)
1146{
1147 struct hda_codec *codec = container_of(dev, struct hda_codec, core);
1148 struct cs8409_spec *spec = codec->spec;
1149 struct sub_codec *cs42l42 = spec->scodecs[CS8409_CODEC0];
1150
1151 unsigned int nid = ((cmd >> 20) & 0x07f);
1152 unsigned int verb = ((cmd >> 8) & 0x0fff);
1153
1154
1155
1156
1157
1158
1159 switch (nid) {
1160 case DOLPHIN_HP_PIN_NID:
1161 case DOLPHIN_LO_PIN_NID:
1162 if (nid == DOLPHIN_LO_PIN_NID)
1163 cs42l42 = spec->scodecs[CS8409_CODEC1];
1164 if (verb == AC_VERB_GET_PIN_SENSE) {
1165 *res = (cs42l42->hp_jack_in) ? AC_PINSENSE_PRESENCE : 0;
1166 return 0;
1167 }
1168 break;
1169 case DOLPHIN_AMIC_PIN_NID:
1170 if (verb == AC_VERB_GET_PIN_SENSE) {
1171 *res = (cs42l42->mic_jack_in) ? AC_PINSENSE_PRESENCE : 0;
1172 return 0;
1173 }
1174 break;
1175 default:
1176 break;
1177 }
1178
1179 return spec->exec_verb(dev, cmd, flags, res);
1180}
1181
1182void dolphin_fixups(struct hda_codec *codec, const struct hda_fixup *fix, int action)
1183{
1184 struct cs8409_spec *spec = codec->spec;
1185 struct snd_kcontrol_new *kctrl;
1186 int i;
1187
1188 switch (action) {
1189 case HDA_FIXUP_ACT_PRE_PROBE:
1190 snd_hda_add_verbs(codec, dolphin_init_verbs);
1191
1192 spec->exec_verb = codec->core.exec_verb;
1193 codec->core.exec_verb = dolphin_exec_verb;
1194
1195 spec->scodecs[CS8409_CODEC0] = &dolphin_cs42l42_0;
1196 spec->scodecs[CS8409_CODEC0]->codec = codec;
1197 spec->scodecs[CS8409_CODEC1] = &dolphin_cs42l42_1;
1198 spec->scodecs[CS8409_CODEC1]->codec = codec;
1199 spec->num_scodecs = 2;
1200
1201 codec->patch_ops = cs8409_dolphin_patch_ops;
1202
1203
1204 spec->gpio_dir = spec->scodecs[CS8409_CODEC0]->reset_gpio |
1205 spec->scodecs[CS8409_CODEC1]->reset_gpio;
1206 spec->gpio_data = 0;
1207 spec->gpio_mask = 0x03f;
1208
1209
1210 snd_hda_sequence_write(codec, dolphin_init_verbs);
1211
1212 snd_hda_jack_add_kctl(codec, DOLPHIN_LO_PIN_NID, "Line Out", true,
1213 SND_JACK_HEADPHONE, NULL);
1214
1215 snd_hda_jack_add_kctl(codec, DOLPHIN_AMIC_PIN_NID, "Microphone", true,
1216 SND_JACK_MICROPHONE, NULL);
1217
1218 cs8409_fix_caps(codec, DOLPHIN_HP_PIN_NID);
1219 cs8409_fix_caps(codec, DOLPHIN_LO_PIN_NID);
1220 cs8409_fix_caps(codec, DOLPHIN_AMIC_PIN_NID);
1221
1222 break;
1223 case HDA_FIXUP_ACT_PROBE:
1224
1225 spec->gen.stream_analog_playback = &cs42l42_48k_pcm_analog_playback;
1226 spec->gen.stream_analog_capture = &cs42l42_48k_pcm_analog_capture;
1227
1228 spec->gen.pcm_playback_hook = cs42l42_playback_pcm_hook;
1229 spec->gen.pcm_capture_hook = cs42l42_capture_pcm_hook;
1230 snd_hda_gen_add_kctl(&spec->gen, "Headphone Playback Volume",
1231 &cs42l42_dac_volume_mixer);
1232 snd_hda_gen_add_kctl(&spec->gen, "Mic Capture Volume", &cs42l42_adc_volume_mixer);
1233 kctrl = snd_hda_gen_add_kctl(&spec->gen, "Line Out Playback Volume",
1234 &cs42l42_dac_volume_mixer);
1235
1236 kctrl->private_value = HDA_COMPOSE_AMP_VAL_OFS(DOLPHIN_HP_PIN_NID, 3, CS8409_CODEC1,
1237 HDA_OUTPUT, CS42L42_VOL_DAC) | HDA_AMP_VAL_MIN_MUTE;
1238 cs8409_enable_ur(codec, 0);
1239 snd_hda_codec_set_name(codec, "CS8409/CS42L42");
1240 break;
1241 case HDA_FIXUP_ACT_INIT:
1242 dolphin_hw_init(codec);
1243 spec->init_done = 1;
1244 if (spec->init_done && spec->build_ctrl_done) {
1245 for (i = 0; i < spec->num_scodecs; i++) {
1246 if (!spec->scodecs[i]->hp_jack_in)
1247 cs42l42_run_jack_detect(spec->scodecs[i]);
1248 }
1249 }
1250 break;
1251 case HDA_FIXUP_ACT_BUILD:
1252 spec->build_ctrl_done = 1;
1253
1254
1255
1256
1257
1258 if (spec->init_done && spec->build_ctrl_done) {
1259 for (i = 0; i < spec->num_scodecs; i++) {
1260 if (!spec->scodecs[i]->hp_jack_in)
1261 cs42l42_run_jack_detect(spec->scodecs[i]);
1262 }
1263 }
1264 break;
1265 default:
1266 break;
1267 }
1268}
1269
1270static int patch_cs8409(struct hda_codec *codec)
1271{
1272 int err;
1273
1274 if (!cs8409_alloc_spec(codec))
1275 return -ENOMEM;
1276
1277 snd_hda_pick_fixup(codec, cs8409_models, cs8409_fixup_tbl, cs8409_fixups);
1278
1279 codec_dbg(codec, "Picked ID=%d, VID=%08x, DEV=%08x\n", codec->fixup_id,
1280 codec->bus->pci->subsystem_vendor,
1281 codec->bus->pci->subsystem_device);
1282
1283 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PRE_PROBE);
1284
1285 err = cs8409_parse_auto_config(codec);
1286 if (err < 0) {
1287 cs8409_free(codec);
1288 return err;
1289 }
1290
1291 snd_hda_apply_fixup(codec, HDA_FIXUP_ACT_PROBE);
1292 return 0;
1293}
1294
1295static const struct hda_device_id snd_hda_id_cs8409[] = {
1296 HDA_CODEC_ENTRY(0x10138409, "CS8409", patch_cs8409),
1297 {}
1298};
1299MODULE_DEVICE_TABLE(hdaudio, snd_hda_id_cs8409);
1300
1301static struct hda_codec_driver cs8409_driver = {
1302 .id = snd_hda_id_cs8409,
1303};
1304module_hda_codec_driver(cs8409_driver);
1305
1306MODULE_LICENSE("GPL");
1307MODULE_DESCRIPTION("Cirrus Logic HDA bridge");
1308