xref: /linux/sound/soc/codecs/uda1380.c (revision 984b3f5746ed2cde3d184651dabf26980f2b66e5)
1b7482f52SPhilipp Zabel /*
2b7482f52SPhilipp Zabel  * uda1380.c - Philips UDA1380 ALSA SoC audio driver
3b7482f52SPhilipp Zabel  *
4b7482f52SPhilipp Zabel  * This program is free software; you can redistribute it and/or modify
5b7482f52SPhilipp Zabel  * it under the terms of the GNU General Public License version 2 as
6b7482f52SPhilipp Zabel  * published by the Free Software Foundation.
7b7482f52SPhilipp Zabel  *
81abd9184SPhilipp Zabel  * Copyright (c) 2007-2009 Philipp Zabel <philipp.zabel@gmail.com>
9b7482f52SPhilipp Zabel  *
10b7482f52SPhilipp Zabel  * Modified by Richard Purdie <richard@openedhand.com> to fit into SoC
11b7482f52SPhilipp Zabel  * codec model.
12b7482f52SPhilipp Zabel  *
13b7482f52SPhilipp Zabel  * Copyright (c) 2005 Giorgio Padrin <giorgio@mandarinlogiq.org>
14b7482f52SPhilipp Zabel  * Copyright 2005 Openedhand Ltd.
15b7482f52SPhilipp Zabel  */
16b7482f52SPhilipp Zabel 
17b7482f52SPhilipp Zabel #include <linux/module.h>
18b7482f52SPhilipp Zabel #include <linux/init.h>
19b7482f52SPhilipp Zabel #include <linux/types.h>
20b7482f52SPhilipp Zabel #include <linux/slab.h>
21b7482f52SPhilipp Zabel #include <linux/errno.h>
221abd9184SPhilipp Zabel #include <linux/gpio.h>
23b7482f52SPhilipp Zabel #include <linux/delay.h>
24b7482f52SPhilipp Zabel #include <linux/i2c.h>
25ef9e5e5cSPhilipp Zabel #include <linux/workqueue.h>
26b7482f52SPhilipp Zabel #include <sound/core.h>
27b7482f52SPhilipp Zabel #include <sound/control.h>
28b7482f52SPhilipp Zabel #include <sound/initval.h>
29b7482f52SPhilipp Zabel #include <sound/soc.h>
30b7482f52SPhilipp Zabel #include <sound/soc-dapm.h>
31b7482f52SPhilipp Zabel #include <sound/tlv.h>
321abd9184SPhilipp Zabel #include <sound/uda1380.h>
33b7482f52SPhilipp Zabel 
34b7482f52SPhilipp Zabel #include "uda1380.h"
35b7482f52SPhilipp Zabel 
36ef9e5e5cSPhilipp Zabel static struct snd_soc_codec *uda1380_codec;
37ef9e5e5cSPhilipp Zabel 
381abd9184SPhilipp Zabel /* codec private data */
391abd9184SPhilipp Zabel struct uda1380_priv {
401abd9184SPhilipp Zabel 	struct snd_soc_codec codec;
411abd9184SPhilipp Zabel 	u16 reg_cache[UDA1380_CACHEREGNUM];
421abd9184SPhilipp Zabel 	unsigned int dac_clk;
431abd9184SPhilipp Zabel 	struct work_struct work;
441abd9184SPhilipp Zabel };
451abd9184SPhilipp Zabel 
46b7482f52SPhilipp Zabel /*
47b7482f52SPhilipp Zabel  * uda1380 register cache
48b7482f52SPhilipp Zabel  */
49b7482f52SPhilipp Zabel static const u16 uda1380_reg[UDA1380_CACHEREGNUM] = {
50b7482f52SPhilipp Zabel 	0x0502, 0x0000, 0x0000, 0x3f3f,
51b7482f52SPhilipp Zabel 	0x0202, 0x0000, 0x0000, 0x0000,
52b7482f52SPhilipp Zabel 	0x0000, 0x0000, 0x0000, 0x0000,
53b7482f52SPhilipp Zabel 	0x0000, 0x0000, 0x0000, 0x0000,
54b7482f52SPhilipp Zabel 	0x0000, 0xff00, 0x0000, 0x4800,
55b7482f52SPhilipp Zabel 	0x0000, 0x0000, 0x0000, 0x0000,
56b7482f52SPhilipp Zabel 	0x0000, 0x0000, 0x0000, 0x0000,
57b7482f52SPhilipp Zabel 	0x0000, 0x0000, 0x0000, 0x0000,
58b7482f52SPhilipp Zabel 	0x0000, 0x8000, 0x0002, 0x0000,
59b7482f52SPhilipp Zabel };
60b7482f52SPhilipp Zabel 
61ef9e5e5cSPhilipp Zabel static unsigned long uda1380_cache_dirty;
62ef9e5e5cSPhilipp Zabel 
63b7482f52SPhilipp Zabel /*
64b7482f52SPhilipp Zabel  * read uda1380 register cache
65b7482f52SPhilipp Zabel  */
66b7482f52SPhilipp Zabel static inline unsigned int uda1380_read_reg_cache(struct snd_soc_codec *codec,
67b7482f52SPhilipp Zabel 	unsigned int reg)
68b7482f52SPhilipp Zabel {
69b7482f52SPhilipp Zabel 	u16 *cache = codec->reg_cache;
70b7482f52SPhilipp Zabel 	if (reg == UDA1380_RESET)
71b7482f52SPhilipp Zabel 		return 0;
72b7482f52SPhilipp Zabel 	if (reg >= UDA1380_CACHEREGNUM)
73b7482f52SPhilipp Zabel 		return -1;
74b7482f52SPhilipp Zabel 	return cache[reg];
75b7482f52SPhilipp Zabel }
76b7482f52SPhilipp Zabel 
77b7482f52SPhilipp Zabel /*
78b7482f52SPhilipp Zabel  * write uda1380 register cache
79b7482f52SPhilipp Zabel  */
80b7482f52SPhilipp Zabel static inline void uda1380_write_reg_cache(struct snd_soc_codec *codec,
81b7482f52SPhilipp Zabel 	u16 reg, unsigned int value)
82b7482f52SPhilipp Zabel {
83b7482f52SPhilipp Zabel 	u16 *cache = codec->reg_cache;
84ef9e5e5cSPhilipp Zabel 
85b7482f52SPhilipp Zabel 	if (reg >= UDA1380_CACHEREGNUM)
86b7482f52SPhilipp Zabel 		return;
87ef9e5e5cSPhilipp Zabel 	if ((reg >= 0x10) && (cache[reg] != value))
88ef9e5e5cSPhilipp Zabel 		set_bit(reg - 0x10, &uda1380_cache_dirty);
89b7482f52SPhilipp Zabel 	cache[reg] = value;
90b7482f52SPhilipp Zabel }
91b7482f52SPhilipp Zabel 
92b7482f52SPhilipp Zabel /*
93b7482f52SPhilipp Zabel  * write to the UDA1380 register space
94b7482f52SPhilipp Zabel  */
95b7482f52SPhilipp Zabel static int uda1380_write(struct snd_soc_codec *codec, unsigned int reg,
96b7482f52SPhilipp Zabel 	unsigned int value)
97b7482f52SPhilipp Zabel {
98b7482f52SPhilipp Zabel 	u8 data[3];
99b7482f52SPhilipp Zabel 
100b7482f52SPhilipp Zabel 	/* data is
101b7482f52SPhilipp Zabel 	 *   data[0] is register offset
102b7482f52SPhilipp Zabel 	 *   data[1] is MS byte
103b7482f52SPhilipp Zabel 	 *   data[2] is LS byte
104b7482f52SPhilipp Zabel 	 */
105b7482f52SPhilipp Zabel 	data[0] = reg;
106b7482f52SPhilipp Zabel 	data[1] = (value & 0xff00) >> 8;
107b7482f52SPhilipp Zabel 	data[2] = value & 0x00ff;
108b7482f52SPhilipp Zabel 
109b7482f52SPhilipp Zabel 	uda1380_write_reg_cache(codec, reg, value);
110b7482f52SPhilipp Zabel 
111b7482f52SPhilipp Zabel 	/* the interpolator & decimator regs must only be written when the
112b7482f52SPhilipp Zabel 	 * codec DAI is active.
113b7482f52SPhilipp Zabel 	 */
114b7482f52SPhilipp Zabel 	if (!codec->active && (reg >= UDA1380_MVOL))
115b7482f52SPhilipp Zabel 		return 0;
116b7482f52SPhilipp Zabel 	pr_debug("uda1380: hw write %x val %x\n", reg, value);
117b7482f52SPhilipp Zabel 	if (codec->hw_write(codec->control_data, data, 3) == 3) {
118b7482f52SPhilipp Zabel 		unsigned int val;
119b7482f52SPhilipp Zabel 		i2c_master_send(codec->control_data, data, 1);
120b7482f52SPhilipp Zabel 		i2c_master_recv(codec->control_data, data, 2);
121b7482f52SPhilipp Zabel 		val = (data[0]<<8) | data[1];
122b7482f52SPhilipp Zabel 		if (val != value) {
123b7482f52SPhilipp Zabel 			pr_debug("uda1380: READ BACK VAL %x\n",
124b7482f52SPhilipp Zabel 					(data[0]<<8) | data[1]);
125b7482f52SPhilipp Zabel 			return -EIO;
126b7482f52SPhilipp Zabel 		}
127ef9e5e5cSPhilipp Zabel 		if (reg >= 0x10)
128ef9e5e5cSPhilipp Zabel 			clear_bit(reg - 0x10, &uda1380_cache_dirty);
129b7482f52SPhilipp Zabel 		return 0;
130b7482f52SPhilipp Zabel 	} else
131b7482f52SPhilipp Zabel 		return -EIO;
132b7482f52SPhilipp Zabel }
133b7482f52SPhilipp Zabel 
134b7482f52SPhilipp Zabel #define uda1380_reset(c)	uda1380_write(c, UDA1380_RESET, 0)
135b7482f52SPhilipp Zabel 
136ef9e5e5cSPhilipp Zabel static void uda1380_flush_work(struct work_struct *work)
137ef9e5e5cSPhilipp Zabel {
138ef9e5e5cSPhilipp Zabel 	int bit, reg;
139ef9e5e5cSPhilipp Zabel 
140*984b3f57SAkinobu Mita 	for_each_set_bit(bit, &uda1380_cache_dirty, UDA1380_CACHEREGNUM - 0x10) {
141ef9e5e5cSPhilipp Zabel 		reg = 0x10 + bit;
142ef9e5e5cSPhilipp Zabel 		pr_debug("uda1380: flush reg %x val %x:\n", reg,
143ef9e5e5cSPhilipp Zabel 				uda1380_read_reg_cache(uda1380_codec, reg));
144ef9e5e5cSPhilipp Zabel 		uda1380_write(uda1380_codec, reg,
145ef9e5e5cSPhilipp Zabel 				uda1380_read_reg_cache(uda1380_codec, reg));
146ef9e5e5cSPhilipp Zabel 		clear_bit(bit, &uda1380_cache_dirty);
147ef9e5e5cSPhilipp Zabel 	}
148ef9e5e5cSPhilipp Zabel }
149ef9e5e5cSPhilipp Zabel 
150b7482f52SPhilipp Zabel /* declarations of ALSA reg_elem_REAL controls */
151b7482f52SPhilipp Zabel static const char *uda1380_deemp[] = {
152b7482f52SPhilipp Zabel 	"None",
153b7482f52SPhilipp Zabel 	"32kHz",
154b7482f52SPhilipp Zabel 	"44.1kHz",
155b7482f52SPhilipp Zabel 	"48kHz",
156b7482f52SPhilipp Zabel 	"96kHz",
157b7482f52SPhilipp Zabel };
158b7482f52SPhilipp Zabel static const char *uda1380_input_sel[] = {
159b7482f52SPhilipp Zabel 	"Line",
160b7482f52SPhilipp Zabel 	"Mic + Line R",
161b7482f52SPhilipp Zabel 	"Line L",
162b7482f52SPhilipp Zabel 	"Mic",
163b7482f52SPhilipp Zabel };
164b7482f52SPhilipp Zabel static const char *uda1380_output_sel[] = {
165b7482f52SPhilipp Zabel 	"DAC",
166b7482f52SPhilipp Zabel 	"Analog Mixer",
167b7482f52SPhilipp Zabel };
168b7482f52SPhilipp Zabel static const char *uda1380_spf_mode[] = {
169b7482f52SPhilipp Zabel 	"Flat",
170b7482f52SPhilipp Zabel 	"Minimum1",
171b7482f52SPhilipp Zabel 	"Minimum2",
172b7482f52SPhilipp Zabel 	"Maximum"
173b7482f52SPhilipp Zabel };
174b7482f52SPhilipp Zabel static const char *uda1380_capture_sel[] = {
175b7482f52SPhilipp Zabel 	"ADC",
176b7482f52SPhilipp Zabel 	"Digital Mixer"
177b7482f52SPhilipp Zabel };
178b7482f52SPhilipp Zabel static const char *uda1380_sel_ns[] = {
179b7482f52SPhilipp Zabel 	"3rd-order",
180b7482f52SPhilipp Zabel 	"5th-order"
181b7482f52SPhilipp Zabel };
182b7482f52SPhilipp Zabel static const char *uda1380_mix_control[] = {
183b7482f52SPhilipp Zabel 	"off",
184b7482f52SPhilipp Zabel 	"PCM only",
185b7482f52SPhilipp Zabel 	"before sound processing",
186b7482f52SPhilipp Zabel 	"after sound processing"
187b7482f52SPhilipp Zabel };
188b7482f52SPhilipp Zabel static const char *uda1380_sdet_setting[] = {
189b7482f52SPhilipp Zabel 	"3200",
190b7482f52SPhilipp Zabel 	"4800",
191b7482f52SPhilipp Zabel 	"9600",
192b7482f52SPhilipp Zabel 	"19200"
193b7482f52SPhilipp Zabel };
194b7482f52SPhilipp Zabel static const char *uda1380_os_setting[] = {
195b7482f52SPhilipp Zabel 	"single-speed",
196b7482f52SPhilipp Zabel 	"double-speed (no mixing)",
197b7482f52SPhilipp Zabel 	"quad-speed (no mixing)"
198b7482f52SPhilipp Zabel };
199b7482f52SPhilipp Zabel 
200b7482f52SPhilipp Zabel static const struct soc_enum uda1380_deemp_enum[] = {
201b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_DEEMP, 8, 5, uda1380_deemp),
202b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_DEEMP, 0, 5, uda1380_deemp),
203b7482f52SPhilipp Zabel };
204b7482f52SPhilipp Zabel static const struct soc_enum uda1380_input_sel_enum =
205b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_ADC, 2, 4, uda1380_input_sel);		/* SEL_MIC, SEL_LNA */
206b7482f52SPhilipp Zabel static const struct soc_enum uda1380_output_sel_enum =
207b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_PM, 7, 2, uda1380_output_sel);		/* R02_EN_AVC */
208b7482f52SPhilipp Zabel static const struct soc_enum uda1380_spf_enum =
209b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_MODE, 14, 4, uda1380_spf_mode);		/* M */
210b7482f52SPhilipp Zabel static const struct soc_enum uda1380_capture_sel_enum =
211b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_IFACE, 6, 2, uda1380_capture_sel);	/* SEL_SOURCE */
212b7482f52SPhilipp Zabel static const struct soc_enum uda1380_sel_ns_enum =
213b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_MIXER, 14, 2, uda1380_sel_ns);		/* SEL_NS */
214b7482f52SPhilipp Zabel static const struct soc_enum uda1380_mix_enum =
215b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_MIXER, 12, 4, uda1380_mix_control);	/* MIX, MIX_POS */
216b7482f52SPhilipp Zabel static const struct soc_enum uda1380_sdet_enum =
217b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_MIXER, 4, 4, uda1380_sdet_setting);	/* SD_VALUE */
218b7482f52SPhilipp Zabel static const struct soc_enum uda1380_os_enum =
219b7482f52SPhilipp Zabel 	SOC_ENUM_SINGLE(UDA1380_MIXER, 0, 3, uda1380_os_setting);	/* OS */
220b7482f52SPhilipp Zabel 
221b7482f52SPhilipp Zabel /*
222b7482f52SPhilipp Zabel  * from -48 dB in 1.5 dB steps (mute instead of -49.5 dB)
223b7482f52SPhilipp Zabel  */
224b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(amix_tlv, -4950, 150, 1);
225b7482f52SPhilipp Zabel 
226b7482f52SPhilipp Zabel /*
227b7482f52SPhilipp Zabel  * from -78 dB in 1 dB steps (3 dB steps, really. LSB are ignored),
228b7482f52SPhilipp Zabel  * from -66 dB in 0.5 dB steps (2 dB steps, really) and
229b7482f52SPhilipp Zabel  * from -52 dB in 0.25 dB steps
230b7482f52SPhilipp Zabel  */
231b7482f52SPhilipp Zabel static const unsigned int mvol_tlv[] = {
232b7482f52SPhilipp Zabel 	TLV_DB_RANGE_HEAD(3),
233b7482f52SPhilipp Zabel 	0, 15, TLV_DB_SCALE_ITEM(-8200, 100, 1),
234b7482f52SPhilipp Zabel 	16, 43, TLV_DB_SCALE_ITEM(-6600, 50, 0),
235b7482f52SPhilipp Zabel 	44, 252, TLV_DB_SCALE_ITEM(-5200, 25, 0),
236b7482f52SPhilipp Zabel };
237b7482f52SPhilipp Zabel 
238b7482f52SPhilipp Zabel /*
239b7482f52SPhilipp Zabel  * from -72 dB in 1.5 dB steps (6 dB steps really),
240b7482f52SPhilipp Zabel  * from -66 dB in 0.75 dB steps (3 dB steps really),
241b7482f52SPhilipp Zabel  * from -60 dB in 0.5 dB steps (2 dB steps really) and
242b7482f52SPhilipp Zabel  * from -46 dB in 0.25 dB steps
243b7482f52SPhilipp Zabel  */
244b7482f52SPhilipp Zabel static const unsigned int vc_tlv[] = {
245b7482f52SPhilipp Zabel 	TLV_DB_RANGE_HEAD(4),
246b7482f52SPhilipp Zabel 	0, 7, TLV_DB_SCALE_ITEM(-7800, 150, 1),
247b7482f52SPhilipp Zabel 	8, 15, TLV_DB_SCALE_ITEM(-6600, 75, 0),
248b7482f52SPhilipp Zabel 	16, 43, TLV_DB_SCALE_ITEM(-6000, 50, 0),
249b7482f52SPhilipp Zabel 	44, 228, TLV_DB_SCALE_ITEM(-4600, 25, 0),
250b7482f52SPhilipp Zabel };
251b7482f52SPhilipp Zabel 
252b7482f52SPhilipp Zabel /* from 0 to 6 dB in 2 dB steps if SPF mode != flat */
253b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(tr_tlv, 0, 200, 0);
254b7482f52SPhilipp Zabel 
255b7482f52SPhilipp Zabel /* from 0 to 24 dB in 2 dB steps, if SPF mode == maximum, otherwise cuts
256b7482f52SPhilipp Zabel  * off at 18 dB max) */
257b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(bb_tlv, 0, 200, 0);
258b7482f52SPhilipp Zabel 
259b7482f52SPhilipp Zabel /* from -63 to 24 dB in 0.5 dB steps (-128...48) */
260b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(dec_tlv, -6400, 50, 1);
261b7482f52SPhilipp Zabel 
262b7482f52SPhilipp Zabel /* from 0 to 24 dB in 3 dB steps */
263b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(pga_tlv, 0, 300, 0);
264b7482f52SPhilipp Zabel 
265b7482f52SPhilipp Zabel /* from 0 to 30 dB in 2 dB steps */
266b7482f52SPhilipp Zabel static DECLARE_TLV_DB_SCALE(vga_tlv, 0, 200, 0);
267b7482f52SPhilipp Zabel 
268b7482f52SPhilipp Zabel static const struct snd_kcontrol_new uda1380_snd_controls[] = {
269b7482f52SPhilipp Zabel 	SOC_DOUBLE_TLV("Analog Mixer Volume", UDA1380_AMIX, 0, 8, 44, 1, amix_tlv),	/* AVCR, AVCL */
270b7482f52SPhilipp Zabel 	SOC_DOUBLE_TLV("Master Playback Volume", UDA1380_MVOL, 0, 8, 252, 1, mvol_tlv),	/* MVCL, MVCR */
271b7482f52SPhilipp Zabel 	SOC_SINGLE_TLV("ADC Playback Volume", UDA1380_MIXVOL, 8, 228, 1, vc_tlv),	/* VC2 */
272b7482f52SPhilipp Zabel 	SOC_SINGLE_TLV("PCM Playback Volume", UDA1380_MIXVOL, 0, 228, 1, vc_tlv),	/* VC1 */
273b7482f52SPhilipp Zabel 	SOC_ENUM("Sound Processing Filter", uda1380_spf_enum),				/* M */
274b7482f52SPhilipp Zabel 	SOC_DOUBLE_TLV("Tone Control - Treble", UDA1380_MODE, 4, 12, 3, 0, tr_tlv), 	/* TRL, TRR */
275b7482f52SPhilipp Zabel 	SOC_DOUBLE_TLV("Tone Control - Bass", UDA1380_MODE, 0, 8, 15, 0, bb_tlv),	/* BBL, BBR */
276b7482f52SPhilipp Zabel /**/	SOC_SINGLE("Master Playback Switch", UDA1380_DEEMP, 14, 1, 1),		/* MTM */
277b7482f52SPhilipp Zabel 	SOC_SINGLE("ADC Playback Switch", UDA1380_DEEMP, 11, 1, 1),		/* MT2 from decimation filter */
278b7482f52SPhilipp Zabel 	SOC_ENUM("ADC Playback De-emphasis", uda1380_deemp_enum[0]),		/* DE2 */
279b7482f52SPhilipp Zabel 	SOC_SINGLE("PCM Playback Switch", UDA1380_DEEMP, 3, 1, 1),		/* MT1, from digital data input */
280b7482f52SPhilipp Zabel 	SOC_ENUM("PCM Playback De-emphasis", uda1380_deemp_enum[1]),		/* DE1 */
281b7482f52SPhilipp Zabel 	SOC_SINGLE("DAC Polarity inverting Switch", UDA1380_MIXER, 15, 1, 0),	/* DA_POL_INV */
282b7482f52SPhilipp Zabel 	SOC_ENUM("Noise Shaper", uda1380_sel_ns_enum),				/* SEL_NS */
283b7482f52SPhilipp Zabel 	SOC_ENUM("Digital Mixer Signal Control", uda1380_mix_enum),		/* MIX_POS, MIX */
284b7482f52SPhilipp Zabel 	SOC_SINGLE("Silence Detector Switch", UDA1380_MIXER, 6, 1, 0),		/* SDET_ON */
285b7482f52SPhilipp Zabel 	SOC_ENUM("Silence Detector Setting", uda1380_sdet_enum),		/* SD_VALUE */
286b7482f52SPhilipp Zabel 	SOC_ENUM("Oversampling Input", uda1380_os_enum),			/* OS */
287b7482f52SPhilipp Zabel 	SOC_DOUBLE_S8_TLV("ADC Capture Volume", UDA1380_DEC, -128, 48, dec_tlv),	/* ML_DEC, MR_DEC */
288b7482f52SPhilipp Zabel /**/	SOC_SINGLE("ADC Capture Switch", UDA1380_PGA, 15, 1, 1),		/* MT_ADC */
289b7482f52SPhilipp Zabel 	SOC_DOUBLE_TLV("Line Capture Volume", UDA1380_PGA, 0, 8, 8, 0, pga_tlv), /* PGA_GAINCTRLL, PGA_GAINCTRLR */
290b7482f52SPhilipp Zabel 	SOC_SINGLE("ADC Polarity inverting Switch", UDA1380_ADC, 12, 1, 0),	/* ADCPOL_INV */
291b7482f52SPhilipp Zabel 	SOC_SINGLE_TLV("Mic Capture Volume", UDA1380_ADC, 8, 15, 0, vga_tlv),	/* VGA_CTRL */
292b7482f52SPhilipp Zabel 	SOC_SINGLE("DC Filter Bypass Switch", UDA1380_ADC, 1, 1, 0),		/* SKIP_DCFIL (before decimator) */
293b7482f52SPhilipp Zabel 	SOC_SINGLE("DC Filter Enable Switch", UDA1380_ADC, 0, 1, 0),		/* EN_DCFIL (at output of decimator) */
294b7482f52SPhilipp Zabel 	SOC_SINGLE("AGC Timing", UDA1380_AGC, 8, 7, 0),			/* TODO: enum, see table 62 */
295b7482f52SPhilipp Zabel 	SOC_SINGLE("AGC Target level", UDA1380_AGC, 2, 3, 1),			/* AGC_LEVEL */
296b7482f52SPhilipp Zabel 	/* -5.5, -8, -11.5, -14 dBFS */
297b7482f52SPhilipp Zabel 	SOC_SINGLE("AGC Switch", UDA1380_AGC, 0, 1, 0),
298b7482f52SPhilipp Zabel };
299b7482f52SPhilipp Zabel 
300b7482f52SPhilipp Zabel /* Input mux */
301b7482f52SPhilipp Zabel static const struct snd_kcontrol_new uda1380_input_mux_control =
302b7482f52SPhilipp Zabel 	SOC_DAPM_ENUM("Route", uda1380_input_sel_enum);
303b7482f52SPhilipp Zabel 
304b7482f52SPhilipp Zabel /* Output mux */
305b7482f52SPhilipp Zabel static const struct snd_kcontrol_new uda1380_output_mux_control =
306b7482f52SPhilipp Zabel 	SOC_DAPM_ENUM("Route", uda1380_output_sel_enum);
307b7482f52SPhilipp Zabel 
308b7482f52SPhilipp Zabel /* Capture mux */
309b7482f52SPhilipp Zabel static const struct snd_kcontrol_new uda1380_capture_mux_control =
310b7482f52SPhilipp Zabel 	SOC_DAPM_ENUM("Route", uda1380_capture_sel_enum);
311b7482f52SPhilipp Zabel 
312b7482f52SPhilipp Zabel 
313b7482f52SPhilipp Zabel static const struct snd_soc_dapm_widget uda1380_dapm_widgets[] = {
314b7482f52SPhilipp Zabel 	SND_SOC_DAPM_MUX("Input Mux", SND_SOC_NOPM, 0, 0,
315b7482f52SPhilipp Zabel 		&uda1380_input_mux_control),
316b7482f52SPhilipp Zabel 	SND_SOC_DAPM_MUX("Output Mux", SND_SOC_NOPM, 0, 0,
317b7482f52SPhilipp Zabel 		&uda1380_output_mux_control),
318b7482f52SPhilipp Zabel 	SND_SOC_DAPM_MUX("Capture Mux", SND_SOC_NOPM, 0, 0,
319b7482f52SPhilipp Zabel 		&uda1380_capture_mux_control),
320b7482f52SPhilipp Zabel 	SND_SOC_DAPM_PGA("Left PGA", UDA1380_PM, 3, 0, NULL, 0),
321b7482f52SPhilipp Zabel 	SND_SOC_DAPM_PGA("Right PGA", UDA1380_PM, 1, 0, NULL, 0),
322b7482f52SPhilipp Zabel 	SND_SOC_DAPM_PGA("Mic LNA", UDA1380_PM, 4, 0, NULL, 0),
323b7482f52SPhilipp Zabel 	SND_SOC_DAPM_ADC("Left ADC", "Left Capture", UDA1380_PM, 2, 0),
324b7482f52SPhilipp Zabel 	SND_SOC_DAPM_ADC("Right ADC", "Right Capture", UDA1380_PM, 0, 0),
325b7482f52SPhilipp Zabel 	SND_SOC_DAPM_INPUT("VINM"),
326b7482f52SPhilipp Zabel 	SND_SOC_DAPM_INPUT("VINL"),
327b7482f52SPhilipp Zabel 	SND_SOC_DAPM_INPUT("VINR"),
328b7482f52SPhilipp Zabel 	SND_SOC_DAPM_MIXER("Analog Mixer", UDA1380_PM, 6, 0, NULL, 0),
329b7482f52SPhilipp Zabel 	SND_SOC_DAPM_OUTPUT("VOUTLHP"),
330b7482f52SPhilipp Zabel 	SND_SOC_DAPM_OUTPUT("VOUTRHP"),
331b7482f52SPhilipp Zabel 	SND_SOC_DAPM_OUTPUT("VOUTL"),
332b7482f52SPhilipp Zabel 	SND_SOC_DAPM_OUTPUT("VOUTR"),
333b7482f52SPhilipp Zabel 	SND_SOC_DAPM_DAC("DAC", "Playback", UDA1380_PM, 10, 0),
334b7482f52SPhilipp Zabel 	SND_SOC_DAPM_PGA("HeadPhone Driver", UDA1380_PM, 13, 0, NULL, 0),
335b7482f52SPhilipp Zabel };
336b7482f52SPhilipp Zabel 
337b7482f52SPhilipp Zabel static const struct snd_soc_dapm_route audio_map[] = {
338b7482f52SPhilipp Zabel 
339b7482f52SPhilipp Zabel 	/* output mux */
340b7482f52SPhilipp Zabel 	{"HeadPhone Driver", NULL, "Output Mux"},
341b7482f52SPhilipp Zabel 	{"VOUTR", NULL, "Output Mux"},
342b7482f52SPhilipp Zabel 	{"VOUTL", NULL, "Output Mux"},
343b7482f52SPhilipp Zabel 
344b7482f52SPhilipp Zabel 	{"Analog Mixer", NULL, "VINR"},
345b7482f52SPhilipp Zabel 	{"Analog Mixer", NULL, "VINL"},
346b7482f52SPhilipp Zabel 	{"Analog Mixer", NULL, "DAC"},
347b7482f52SPhilipp Zabel 
348b7482f52SPhilipp Zabel 	{"Output Mux", "DAC", "DAC"},
349b7482f52SPhilipp Zabel 	{"Output Mux", "Analog Mixer", "Analog Mixer"},
350b7482f52SPhilipp Zabel 
351b7482f52SPhilipp Zabel 	/* {"DAC", "Digital Mixer", "I2S" } */
352b7482f52SPhilipp Zabel 
353b7482f52SPhilipp Zabel 	/* headphone driver */
354b7482f52SPhilipp Zabel 	{"VOUTLHP", NULL, "HeadPhone Driver"},
355b7482f52SPhilipp Zabel 	{"VOUTRHP", NULL, "HeadPhone Driver"},
356b7482f52SPhilipp Zabel 
357b7482f52SPhilipp Zabel 	/* input mux */
358b7482f52SPhilipp Zabel 	{"Left ADC", NULL, "Input Mux"},
359b7482f52SPhilipp Zabel 	{"Input Mux", "Mic", "Mic LNA"},
360b7482f52SPhilipp Zabel 	{"Input Mux", "Mic + Line R", "Mic LNA"},
361b7482f52SPhilipp Zabel 	{"Input Mux", "Line L", "Left PGA"},
362b7482f52SPhilipp Zabel 	{"Input Mux", "Line", "Left PGA"},
363b7482f52SPhilipp Zabel 
364b7482f52SPhilipp Zabel 	/* right input */
365b7482f52SPhilipp Zabel 	{"Right ADC", "Mic + Line R", "Right PGA"},
366b7482f52SPhilipp Zabel 	{"Right ADC", "Line", "Right PGA"},
367b7482f52SPhilipp Zabel 
368b7482f52SPhilipp Zabel 	/* inputs */
369b7482f52SPhilipp Zabel 	{"Mic LNA", NULL, "VINM"},
370b7482f52SPhilipp Zabel 	{"Left PGA", NULL, "VINL"},
371b7482f52SPhilipp Zabel 	{"Right PGA", NULL, "VINR"},
372b7482f52SPhilipp Zabel };
373b7482f52SPhilipp Zabel 
374b7482f52SPhilipp Zabel static int uda1380_add_widgets(struct snd_soc_codec *codec)
375b7482f52SPhilipp Zabel {
376b7482f52SPhilipp Zabel 	snd_soc_dapm_new_controls(codec, uda1380_dapm_widgets,
377b7482f52SPhilipp Zabel 				  ARRAY_SIZE(uda1380_dapm_widgets));
378b7482f52SPhilipp Zabel 
379b7482f52SPhilipp Zabel 	snd_soc_dapm_add_routes(codec, audio_map, ARRAY_SIZE(audio_map));
380b7482f52SPhilipp Zabel 
381b7482f52SPhilipp Zabel 	return 0;
382b7482f52SPhilipp Zabel }
383b7482f52SPhilipp Zabel 
3845b247442SPhilipp Zabel static int uda1380_set_dai_fmt_both(struct snd_soc_dai *codec_dai,
385b7482f52SPhilipp Zabel 		unsigned int fmt)
386b7482f52SPhilipp Zabel {
387b7482f52SPhilipp Zabel 	struct snd_soc_codec *codec = codec_dai->codec;
388b7482f52SPhilipp Zabel 	int iface;
389b7482f52SPhilipp Zabel 
390b7482f52SPhilipp Zabel 	/* set up DAI based upon fmt */
391b7482f52SPhilipp Zabel 	iface = uda1380_read_reg_cache(codec, UDA1380_IFACE);
392b7482f52SPhilipp Zabel 	iface &= ~(R01_SFORI_MASK | R01_SIM | R01_SFORO_MASK);
393b7482f52SPhilipp Zabel 
394b7482f52SPhilipp Zabel 	switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
395b7482f52SPhilipp Zabel 	case SND_SOC_DAIFMT_I2S:
396b7482f52SPhilipp Zabel 		iface |= R01_SFORI_I2S | R01_SFORO_I2S;
397b7482f52SPhilipp Zabel 		break;
398b7482f52SPhilipp Zabel 	case SND_SOC_DAIFMT_LSB:
3995b247442SPhilipp Zabel 		iface |= R01_SFORI_LSB16 | R01_SFORO_LSB16;
400b7482f52SPhilipp Zabel 		break;
401b7482f52SPhilipp Zabel 	case SND_SOC_DAIFMT_MSB:
4025b247442SPhilipp Zabel 		iface |= R01_SFORI_MSB | R01_SFORO_MSB;
4035b247442SPhilipp Zabel 	}
4045b247442SPhilipp Zabel 
4055f2a9384SPhilipp Zabel 	/* DATAI is slave only, so in single-link mode, this has to be slave */
4065f2a9384SPhilipp Zabel 	if ((fmt & SND_SOC_DAIFMT_MASTER_MASK) != SND_SOC_DAIFMT_CBS_CFS)
4075f2a9384SPhilipp Zabel 		return -EINVAL;
4085b247442SPhilipp Zabel 
4095b247442SPhilipp Zabel 	uda1380_write(codec, UDA1380_IFACE, iface);
4105b247442SPhilipp Zabel 
4115b247442SPhilipp Zabel 	return 0;
4125b247442SPhilipp Zabel }
4135b247442SPhilipp Zabel 
4145b247442SPhilipp Zabel static int uda1380_set_dai_fmt_playback(struct snd_soc_dai *codec_dai,
4155b247442SPhilipp Zabel 		unsigned int fmt)
4165b247442SPhilipp Zabel {
4175b247442SPhilipp Zabel 	struct snd_soc_codec *codec = codec_dai->codec;
4185b247442SPhilipp Zabel 	int iface;
4195b247442SPhilipp Zabel 
4205b247442SPhilipp Zabel 	/* set up DAI based upon fmt */
4215b247442SPhilipp Zabel 	iface = uda1380_read_reg_cache(codec, UDA1380_IFACE);
4225b247442SPhilipp Zabel 	iface &= ~R01_SFORI_MASK;
4235b247442SPhilipp Zabel 
4245b247442SPhilipp Zabel 	switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
4255b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_I2S:
4265b247442SPhilipp Zabel 		iface |= R01_SFORI_I2S;
4275b247442SPhilipp Zabel 		break;
4285b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_LSB:
4295b247442SPhilipp Zabel 		iface |= R01_SFORI_LSB16;
4305b247442SPhilipp Zabel 		break;
4315b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_MSB:
4325b247442SPhilipp Zabel 		iface |= R01_SFORI_MSB;
4335b247442SPhilipp Zabel 	}
4345b247442SPhilipp Zabel 
4355f2a9384SPhilipp Zabel 	/* DATAI is slave only, so this has to be slave */
4365f2a9384SPhilipp Zabel 	if ((fmt & SND_SOC_DAIFMT_MASTER_MASK) != SND_SOC_DAIFMT_CBS_CFS)
4375f2a9384SPhilipp Zabel 		return -EINVAL;
4385f2a9384SPhilipp Zabel 
4395b247442SPhilipp Zabel 	uda1380_write(codec, UDA1380_IFACE, iface);
4405b247442SPhilipp Zabel 
4415b247442SPhilipp Zabel 	return 0;
4425b247442SPhilipp Zabel }
4435b247442SPhilipp Zabel 
4445b247442SPhilipp Zabel static int uda1380_set_dai_fmt_capture(struct snd_soc_dai *codec_dai,
4455b247442SPhilipp Zabel 		unsigned int fmt)
4465b247442SPhilipp Zabel {
4475b247442SPhilipp Zabel 	struct snd_soc_codec *codec = codec_dai->codec;
4485b247442SPhilipp Zabel 	int iface;
4495b247442SPhilipp Zabel 
4505b247442SPhilipp Zabel 	/* set up DAI based upon fmt */
4515b247442SPhilipp Zabel 	iface = uda1380_read_reg_cache(codec, UDA1380_IFACE);
4525b247442SPhilipp Zabel 	iface &= ~(R01_SIM | R01_SFORO_MASK);
4535b247442SPhilipp Zabel 
4545b247442SPhilipp Zabel 	switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
4555b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_I2S:
4565b247442SPhilipp Zabel 		iface |= R01_SFORO_I2S;
4575b247442SPhilipp Zabel 		break;
4585b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_LSB:
4595b247442SPhilipp Zabel 		iface |= R01_SFORO_LSB16;
4605b247442SPhilipp Zabel 		break;
4615b247442SPhilipp Zabel 	case SND_SOC_DAIFMT_MSB:
4625b247442SPhilipp Zabel 		iface |= R01_SFORO_MSB;
463b7482f52SPhilipp Zabel 	}
464b7482f52SPhilipp Zabel 
465b7482f52SPhilipp Zabel 	if ((fmt & SND_SOC_DAIFMT_MASTER_MASK) == SND_SOC_DAIFMT_CBM_CFM)
466b7482f52SPhilipp Zabel 		iface |= R01_SIM;
467b7482f52SPhilipp Zabel 
468b7482f52SPhilipp Zabel 	uda1380_write(codec, UDA1380_IFACE, iface);
469b7482f52SPhilipp Zabel 
470b7482f52SPhilipp Zabel 	return 0;
471b7482f52SPhilipp Zabel }
472b7482f52SPhilipp Zabel 
473ef9e5e5cSPhilipp Zabel static int uda1380_trigger(struct snd_pcm_substream *substream, int cmd,
474dee89c4dSMark Brown 		struct snd_soc_dai *dai)
475b7482f52SPhilipp Zabel {
476b7482f52SPhilipp Zabel 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
477b7482f52SPhilipp Zabel 	struct snd_soc_device *socdev = rtd->socdev;
4786627a653SMark Brown 	struct snd_soc_codec *codec = socdev->card->codec;
4791abd9184SPhilipp Zabel 	struct uda1380_priv *uda1380 = codec->private_data;
480ef9e5e5cSPhilipp Zabel 	int mixer = uda1380_read_reg_cache(codec, UDA1380_MIXER);
481b7482f52SPhilipp Zabel 
482ef9e5e5cSPhilipp Zabel 	switch (cmd) {
483ef9e5e5cSPhilipp Zabel 	case SNDRV_PCM_TRIGGER_START:
484ef9e5e5cSPhilipp Zabel 	case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
485ef9e5e5cSPhilipp Zabel 		uda1380_write_reg_cache(codec, UDA1380_MIXER,
486ef9e5e5cSPhilipp Zabel 					mixer & ~R14_SILENCE);
4871abd9184SPhilipp Zabel 		schedule_work(&uda1380->work);
488ef9e5e5cSPhilipp Zabel 		break;
489ef9e5e5cSPhilipp Zabel 	case SNDRV_PCM_TRIGGER_STOP:
490ef9e5e5cSPhilipp Zabel 	case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
491ef9e5e5cSPhilipp Zabel 		uda1380_write_reg_cache(codec, UDA1380_MIXER,
492ef9e5e5cSPhilipp Zabel 					mixer | R14_SILENCE);
4931abd9184SPhilipp Zabel 		schedule_work(&uda1380->work);
494ef9e5e5cSPhilipp Zabel 		break;
495b7482f52SPhilipp Zabel 	}
496b7482f52SPhilipp Zabel 	return 0;
497b7482f52SPhilipp Zabel }
498b7482f52SPhilipp Zabel 
499b7482f52SPhilipp Zabel static int uda1380_pcm_hw_params(struct snd_pcm_substream *substream,
500dee89c4dSMark Brown 				 struct snd_pcm_hw_params *params,
501dee89c4dSMark Brown 				 struct snd_soc_dai *dai)
502b7482f52SPhilipp Zabel {
503b7482f52SPhilipp Zabel 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
504b7482f52SPhilipp Zabel 	struct snd_soc_device *socdev = rtd->socdev;
5056627a653SMark Brown 	struct snd_soc_codec *codec = socdev->card->codec;
506b7482f52SPhilipp Zabel 	u16 clk = uda1380_read_reg_cache(codec, UDA1380_CLK);
507b7482f52SPhilipp Zabel 
508b7482f52SPhilipp Zabel 	/* set WSPLL power and divider if running from this clock */
509b7482f52SPhilipp Zabel 	if (clk & R00_DAC_CLK) {
510b7482f52SPhilipp Zabel 		int rate = params_rate(params);
511b7482f52SPhilipp Zabel 		u16 pm = uda1380_read_reg_cache(codec, UDA1380_PM);
512b7482f52SPhilipp Zabel 		clk &= ~0x3; /* clear SEL_LOOP_DIV */
513b7482f52SPhilipp Zabel 		switch (rate) {
514b7482f52SPhilipp Zabel 		case 6250 ... 12500:
515b7482f52SPhilipp Zabel 			clk |= 0x0;
516b7482f52SPhilipp Zabel 			break;
517b7482f52SPhilipp Zabel 		case 12501 ... 25000:
518b7482f52SPhilipp Zabel 			clk |= 0x1;
519b7482f52SPhilipp Zabel 			break;
520b7482f52SPhilipp Zabel 		case 25001 ... 50000:
521b7482f52SPhilipp Zabel 			clk |= 0x2;
522b7482f52SPhilipp Zabel 			break;
523b7482f52SPhilipp Zabel 		case 50001 ... 100000:
524b7482f52SPhilipp Zabel 			clk |= 0x3;
525b7482f52SPhilipp Zabel 			break;
526b7482f52SPhilipp Zabel 		}
527b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_PM, R02_PON_PLL | pm);
528b7482f52SPhilipp Zabel 	}
529b7482f52SPhilipp Zabel 
530b7482f52SPhilipp Zabel 	if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
531b7482f52SPhilipp Zabel 		clk |= R00_EN_DAC | R00_EN_INT;
532b7482f52SPhilipp Zabel 	else
533b7482f52SPhilipp Zabel 		clk |= R00_EN_ADC | R00_EN_DEC;
534b7482f52SPhilipp Zabel 
535b7482f52SPhilipp Zabel 	uda1380_write(codec, UDA1380_CLK, clk);
536b7482f52SPhilipp Zabel 	return 0;
537b7482f52SPhilipp Zabel }
538b7482f52SPhilipp Zabel 
539dee89c4dSMark Brown static void uda1380_pcm_shutdown(struct snd_pcm_substream *substream,
540dee89c4dSMark Brown 				 struct snd_soc_dai *dai)
541b7482f52SPhilipp Zabel {
542b7482f52SPhilipp Zabel 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
543b7482f52SPhilipp Zabel 	struct snd_soc_device *socdev = rtd->socdev;
5446627a653SMark Brown 	struct snd_soc_codec *codec = socdev->card->codec;
545b7482f52SPhilipp Zabel 	u16 clk = uda1380_read_reg_cache(codec, UDA1380_CLK);
546b7482f52SPhilipp Zabel 
547b7482f52SPhilipp Zabel 	/* shut down WSPLL power if running from this clock */
548b7482f52SPhilipp Zabel 	if (clk & R00_DAC_CLK) {
549b7482f52SPhilipp Zabel 		u16 pm = uda1380_read_reg_cache(codec, UDA1380_PM);
550b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_PM, ~R02_PON_PLL & pm);
551b7482f52SPhilipp Zabel 	}
552b7482f52SPhilipp Zabel 
553b7482f52SPhilipp Zabel 	if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
554b7482f52SPhilipp Zabel 		clk &= ~(R00_EN_DAC | R00_EN_INT);
555b7482f52SPhilipp Zabel 	else
556b7482f52SPhilipp Zabel 		clk &= ~(R00_EN_ADC | R00_EN_DEC);
557b7482f52SPhilipp Zabel 
558b7482f52SPhilipp Zabel 	uda1380_write(codec, UDA1380_CLK, clk);
559b7482f52SPhilipp Zabel }
560b7482f52SPhilipp Zabel 
561b7482f52SPhilipp Zabel static int uda1380_set_bias_level(struct snd_soc_codec *codec,
562b7482f52SPhilipp Zabel 	enum snd_soc_bias_level level)
563b7482f52SPhilipp Zabel {
564b7482f52SPhilipp Zabel 	int pm = uda1380_read_reg_cache(codec, UDA1380_PM);
565b7482f52SPhilipp Zabel 
566b7482f52SPhilipp Zabel 	switch (level) {
567b7482f52SPhilipp Zabel 	case SND_SOC_BIAS_ON:
568b7482f52SPhilipp Zabel 	case SND_SOC_BIAS_PREPARE:
569b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_PM, R02_PON_BIAS | pm);
570b7482f52SPhilipp Zabel 		break;
571b7482f52SPhilipp Zabel 	case SND_SOC_BIAS_STANDBY:
572b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_PM, R02_PON_BIAS);
573b7482f52SPhilipp Zabel 		break;
574b7482f52SPhilipp Zabel 	case SND_SOC_BIAS_OFF:
575b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_PM, 0x0);
576b7482f52SPhilipp Zabel 		break;
577b7482f52SPhilipp Zabel 	}
578b7482f52SPhilipp Zabel 	codec->bias_level = level;
579b7482f52SPhilipp Zabel 	return 0;
580b7482f52SPhilipp Zabel }
581b7482f52SPhilipp Zabel 
582b7482f52SPhilipp Zabel #define UDA1380_RATES (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_11025 |\
583b7482f52SPhilipp Zabel 		       SNDRV_PCM_RATE_16000 | SNDRV_PCM_RATE_22050 |\
584b7482f52SPhilipp Zabel 		       SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000)
585b7482f52SPhilipp Zabel 
5866335d055SEric Miao static struct snd_soc_dai_ops uda1380_dai_ops = {
5876335d055SEric Miao 	.hw_params	= uda1380_pcm_hw_params,
5886335d055SEric Miao 	.shutdown	= uda1380_pcm_shutdown,
58965ec1cd1SMark Brown 	.trigger	= uda1380_trigger,
5906335d055SEric Miao 	.set_fmt	= uda1380_set_dai_fmt_both,
5916335d055SEric Miao };
5926335d055SEric Miao 
5936335d055SEric Miao static struct snd_soc_dai_ops uda1380_dai_ops_playback = {
5946335d055SEric Miao 	.hw_params	= uda1380_pcm_hw_params,
5956335d055SEric Miao 	.shutdown	= uda1380_pcm_shutdown,
59665ec1cd1SMark Brown 	.trigger	= uda1380_trigger,
5976335d055SEric Miao 	.set_fmt	= uda1380_set_dai_fmt_playback,
5986335d055SEric Miao };
5996335d055SEric Miao 
6006335d055SEric Miao static struct snd_soc_dai_ops uda1380_dai_ops_capture = {
6016335d055SEric Miao 	.hw_params	= uda1380_pcm_hw_params,
6026335d055SEric Miao 	.shutdown	= uda1380_pcm_shutdown,
60365ec1cd1SMark Brown 	.trigger	= uda1380_trigger,
6046335d055SEric Miao 	.set_fmt	= uda1380_set_dai_fmt_capture,
6056335d055SEric Miao };
6066335d055SEric Miao 
607e550e17fSLiam Girdwood struct snd_soc_dai uda1380_dai[] = {
608b7482f52SPhilipp Zabel {
609b7482f52SPhilipp Zabel 	.name = "UDA1380",
610b7482f52SPhilipp Zabel 	.playback = {
611b7482f52SPhilipp Zabel 		.stream_name = "Playback",
612b7482f52SPhilipp Zabel 		.channels_min = 1,
613b7482f52SPhilipp Zabel 		.channels_max = 2,
614b7482f52SPhilipp Zabel 		.rates = UDA1380_RATES,
615b7482f52SPhilipp Zabel 		.formats = SNDRV_PCM_FMTBIT_S16_LE,},
616b7482f52SPhilipp Zabel 	.capture = {
617b7482f52SPhilipp Zabel 		.stream_name = "Capture",
618b7482f52SPhilipp Zabel 		.channels_min = 1,
619b7482f52SPhilipp Zabel 		.channels_max = 2,
620b7482f52SPhilipp Zabel 		.rates = UDA1380_RATES,
621b7482f52SPhilipp Zabel 		.formats = SNDRV_PCM_FMTBIT_S16_LE,},
6226335d055SEric Miao 	.ops = &uda1380_dai_ops,
623b7482f52SPhilipp Zabel },
624b7482f52SPhilipp Zabel { /* playback only - dual interface */
625b7482f52SPhilipp Zabel 	.name = "UDA1380",
626b7482f52SPhilipp Zabel 	.playback = {
627b7482f52SPhilipp Zabel 		.stream_name = "Playback",
628b7482f52SPhilipp Zabel 		.channels_min = 1,
629b7482f52SPhilipp Zabel 		.channels_max = 2,
630b7482f52SPhilipp Zabel 		.rates = UDA1380_RATES,
631b7482f52SPhilipp Zabel 		.formats = SNDRV_PCM_FMTBIT_S16_LE,
632b7482f52SPhilipp Zabel 	},
6336335d055SEric Miao 	.ops = &uda1380_dai_ops_playback,
634b7482f52SPhilipp Zabel },
635b7482f52SPhilipp Zabel { /* capture only - dual interface*/
636b7482f52SPhilipp Zabel 	.name = "UDA1380",
637b7482f52SPhilipp Zabel 	.capture = {
638b7482f52SPhilipp Zabel 		.stream_name = "Capture",
639b7482f52SPhilipp Zabel 		.channels_min = 1,
640b7482f52SPhilipp Zabel 		.channels_max = 2,
641b7482f52SPhilipp Zabel 		.rates = UDA1380_RATES,
642b7482f52SPhilipp Zabel 		.formats = SNDRV_PCM_FMTBIT_S16_LE,
643b7482f52SPhilipp Zabel 	},
6446335d055SEric Miao 	.ops = &uda1380_dai_ops_capture,
645b7482f52SPhilipp Zabel },
646b7482f52SPhilipp Zabel };
647b7482f52SPhilipp Zabel EXPORT_SYMBOL_GPL(uda1380_dai);
648b7482f52SPhilipp Zabel 
649b7482f52SPhilipp Zabel static int uda1380_suspend(struct platform_device *pdev, pm_message_t state)
650b7482f52SPhilipp Zabel {
651b7482f52SPhilipp Zabel 	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
6526627a653SMark Brown 	struct snd_soc_codec *codec = socdev->card->codec;
653b7482f52SPhilipp Zabel 
654b7482f52SPhilipp Zabel 	uda1380_set_bias_level(codec, SND_SOC_BIAS_OFF);
655b7482f52SPhilipp Zabel 	return 0;
656b7482f52SPhilipp Zabel }
657b7482f52SPhilipp Zabel 
658b7482f52SPhilipp Zabel static int uda1380_resume(struct platform_device *pdev)
659b7482f52SPhilipp Zabel {
660b7482f52SPhilipp Zabel 	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
6616627a653SMark Brown 	struct snd_soc_codec *codec = socdev->card->codec;
662b7482f52SPhilipp Zabel 	int i;
663b7482f52SPhilipp Zabel 	u8 data[2];
664b7482f52SPhilipp Zabel 	u16 *cache = codec->reg_cache;
665b7482f52SPhilipp Zabel 
666b7482f52SPhilipp Zabel 	/* Sync reg_cache with the hardware */
667b7482f52SPhilipp Zabel 	for (i = 0; i < ARRAY_SIZE(uda1380_reg); i++) {
668b7482f52SPhilipp Zabel 		data[0] = (i << 1) | ((cache[i] >> 8) & 0x0001);
669b7482f52SPhilipp Zabel 		data[1] = cache[i] & 0x00ff;
670b7482f52SPhilipp Zabel 		codec->hw_write(codec->control_data, data, 2);
671b7482f52SPhilipp Zabel 	}
672b7482f52SPhilipp Zabel 	uda1380_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
673b7482f52SPhilipp Zabel 	uda1380_set_bias_level(codec, codec->suspend_bias_level);
674b7482f52SPhilipp Zabel 	return 0;
675b7482f52SPhilipp Zabel }
676b7482f52SPhilipp Zabel 
6771abd9184SPhilipp Zabel static int uda1380_probe(struct platform_device *pdev)
678b7482f52SPhilipp Zabel {
6791abd9184SPhilipp Zabel 	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
6801abd9184SPhilipp Zabel 	struct snd_soc_codec *codec;
6811abd9184SPhilipp Zabel 	struct uda1380_platform_data *pdata;
682b7482f52SPhilipp Zabel 	int ret = 0;
683b7482f52SPhilipp Zabel 
6841abd9184SPhilipp Zabel 	if (uda1380_codec == NULL) {
6851abd9184SPhilipp Zabel 		dev_err(&pdev->dev, "Codec device not registered\n");
6861abd9184SPhilipp Zabel 		return -ENODEV;
6871abd9184SPhilipp Zabel 	}
688b7482f52SPhilipp Zabel 
6891abd9184SPhilipp Zabel 	socdev->card->codec = uda1380_codec;
6901abd9184SPhilipp Zabel 	codec = uda1380_codec;
6911abd9184SPhilipp Zabel 	pdata = codec->dev->platform_data;
692ef9e5e5cSPhilipp Zabel 
693b7482f52SPhilipp Zabel 	/* register pcms */
694b7482f52SPhilipp Zabel 	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
695b7482f52SPhilipp Zabel 	if (ret < 0) {
6961abd9184SPhilipp Zabel 		dev_err(codec->dev, "failed to create pcms: %d\n", ret);
697b7482f52SPhilipp Zabel 		goto pcm_err;
698b7482f52SPhilipp Zabel 	}
699b7482f52SPhilipp Zabel 
700b7482f52SPhilipp Zabel 	/* power on device */
701b7482f52SPhilipp Zabel 	uda1380_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
702b7482f52SPhilipp Zabel 	/* set clock input */
7031abd9184SPhilipp Zabel 	switch (pdata->dac_clk) {
704b7482f52SPhilipp Zabel 	case UDA1380_DAC_CLK_SYSCLK:
705b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_CLK, 0);
706b7482f52SPhilipp Zabel 		break;
707b7482f52SPhilipp Zabel 	case UDA1380_DAC_CLK_WSPLL:
708b7482f52SPhilipp Zabel 		uda1380_write(codec, UDA1380_CLK, R00_DAC_CLK);
709b7482f52SPhilipp Zabel 		break;
710b7482f52SPhilipp Zabel 	}
711b7482f52SPhilipp Zabel 
7123e8e1952SIan Molton 	snd_soc_add_controls(codec, uda1380_snd_controls,
7133e8e1952SIan Molton 				ARRAY_SIZE(uda1380_snd_controls));
714b7482f52SPhilipp Zabel 	uda1380_add_widgets(codec);
715b7482f52SPhilipp Zabel 
716b7482f52SPhilipp Zabel 	return ret;
717b7482f52SPhilipp Zabel 
718b7482f52SPhilipp Zabel pcm_err:
719b7482f52SPhilipp Zabel 	return ret;
720b7482f52SPhilipp Zabel }
721b7482f52SPhilipp Zabel 
7221abd9184SPhilipp Zabel /* power down chip */
7231abd9184SPhilipp Zabel static int uda1380_remove(struct platform_device *pdev)
7241abd9184SPhilipp Zabel {
7251abd9184SPhilipp Zabel 	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
7261abd9184SPhilipp Zabel 	struct snd_soc_codec *codec = socdev->card->codec;
7271abd9184SPhilipp Zabel 
7281abd9184SPhilipp Zabel 	if (codec->control_data)
7291abd9184SPhilipp Zabel 		uda1380_set_bias_level(codec, SND_SOC_BIAS_OFF);
7301abd9184SPhilipp Zabel 
7311abd9184SPhilipp Zabel 	snd_soc_free_pcms(socdev);
7321abd9184SPhilipp Zabel 	snd_soc_dapm_free(socdev);
7331abd9184SPhilipp Zabel 
7341abd9184SPhilipp Zabel 	return 0;
7351abd9184SPhilipp Zabel }
7361abd9184SPhilipp Zabel 
7371abd9184SPhilipp Zabel struct snd_soc_codec_device soc_codec_dev_uda1380 = {
7381abd9184SPhilipp Zabel 	.probe = 	uda1380_probe,
7391abd9184SPhilipp Zabel 	.remove = 	uda1380_remove,
7401abd9184SPhilipp Zabel 	.suspend = 	uda1380_suspend,
7411abd9184SPhilipp Zabel 	.resume =	uda1380_resume,
7421abd9184SPhilipp Zabel };
7431abd9184SPhilipp Zabel EXPORT_SYMBOL_GPL(soc_codec_dev_uda1380);
7441abd9184SPhilipp Zabel 
7451abd9184SPhilipp Zabel static int uda1380_register(struct uda1380_priv *uda1380)
7461abd9184SPhilipp Zabel {
7471abd9184SPhilipp Zabel 	int ret, i;
7481abd9184SPhilipp Zabel 	struct snd_soc_codec *codec = &uda1380->codec;
7491abd9184SPhilipp Zabel 	struct uda1380_platform_data *pdata = codec->dev->platform_data;
7501abd9184SPhilipp Zabel 
7511abd9184SPhilipp Zabel 	if (uda1380_codec) {
7521abd9184SPhilipp Zabel 		dev_err(codec->dev, "Another UDA1380 is registered\n");
7531abd9184SPhilipp Zabel 		return -EINVAL;
7541abd9184SPhilipp Zabel 	}
7551abd9184SPhilipp Zabel 
7561abd9184SPhilipp Zabel 	if (!pdata || !pdata->gpio_power || !pdata->gpio_reset)
7571abd9184SPhilipp Zabel 		return -EINVAL;
7581abd9184SPhilipp Zabel 
7591abd9184SPhilipp Zabel 	ret = gpio_request(pdata->gpio_power, "uda1380 power");
7601abd9184SPhilipp Zabel 	if (ret)
7611abd9184SPhilipp Zabel 		goto err_out;
7621abd9184SPhilipp Zabel 	ret = gpio_request(pdata->gpio_reset, "uda1380 reset");
7631abd9184SPhilipp Zabel 	if (ret)
7641abd9184SPhilipp Zabel 		goto err_gpio;
7651abd9184SPhilipp Zabel 
7661abd9184SPhilipp Zabel 	gpio_direction_output(pdata->gpio_power, 1);
7671abd9184SPhilipp Zabel 
7681abd9184SPhilipp Zabel 	/* we may need to have the clock running here - pH5 */
7691abd9184SPhilipp Zabel 	gpio_direction_output(pdata->gpio_reset, 1);
7701abd9184SPhilipp Zabel 	udelay(5);
7711abd9184SPhilipp Zabel 	gpio_set_value(pdata->gpio_reset, 0);
7721abd9184SPhilipp Zabel 
7731abd9184SPhilipp Zabel 	mutex_init(&codec->mutex);
7741abd9184SPhilipp Zabel 	INIT_LIST_HEAD(&codec->dapm_widgets);
7751abd9184SPhilipp Zabel 	INIT_LIST_HEAD(&codec->dapm_paths);
7761abd9184SPhilipp Zabel 
7771abd9184SPhilipp Zabel 	codec->private_data = uda1380;
7781abd9184SPhilipp Zabel 	codec->name = "UDA1380";
7791abd9184SPhilipp Zabel 	codec->owner = THIS_MODULE;
7801abd9184SPhilipp Zabel 	codec->read = uda1380_read_reg_cache;
7811abd9184SPhilipp Zabel 	codec->write = uda1380_write;
7821abd9184SPhilipp Zabel 	codec->bias_level = SND_SOC_BIAS_OFF;
7831abd9184SPhilipp Zabel 	codec->set_bias_level = uda1380_set_bias_level;
7841abd9184SPhilipp Zabel 	codec->dai = uda1380_dai;
7851abd9184SPhilipp Zabel 	codec->num_dai = ARRAY_SIZE(uda1380_dai);
7861abd9184SPhilipp Zabel 	codec->reg_cache_size = ARRAY_SIZE(uda1380_reg);
7871abd9184SPhilipp Zabel 	codec->reg_cache = &uda1380->reg_cache;
7881abd9184SPhilipp Zabel 	codec->reg_cache_step = 1;
7891abd9184SPhilipp Zabel 
7901abd9184SPhilipp Zabel 	memcpy(codec->reg_cache, uda1380_reg, sizeof(uda1380_reg));
7911abd9184SPhilipp Zabel 
7921abd9184SPhilipp Zabel 	ret = uda1380_reset(codec);
7931abd9184SPhilipp Zabel 	if (ret < 0) {
7941abd9184SPhilipp Zabel 		dev_err(codec->dev, "Failed to issue reset\n");
7951abd9184SPhilipp Zabel 		goto err_reset;
7961abd9184SPhilipp Zabel 	}
7971abd9184SPhilipp Zabel 
7981abd9184SPhilipp Zabel 	INIT_WORK(&uda1380->work, uda1380_flush_work);
7991abd9184SPhilipp Zabel 
8001abd9184SPhilipp Zabel 	for (i = 0; i < ARRAY_SIZE(uda1380_dai); i++)
8011abd9184SPhilipp Zabel 		uda1380_dai[i].dev = codec->dev;
8021abd9184SPhilipp Zabel 
8031abd9184SPhilipp Zabel 	uda1380_codec = codec;
8041abd9184SPhilipp Zabel 
8051abd9184SPhilipp Zabel 	ret = snd_soc_register_codec(codec);
8061abd9184SPhilipp Zabel 	if (ret != 0) {
8071abd9184SPhilipp Zabel 		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
8081abd9184SPhilipp Zabel 		goto err_reset;
8091abd9184SPhilipp Zabel 	}
8101abd9184SPhilipp Zabel 
8111abd9184SPhilipp Zabel 	ret = snd_soc_register_dais(uda1380_dai, ARRAY_SIZE(uda1380_dai));
8121abd9184SPhilipp Zabel 	if (ret != 0) {
8131abd9184SPhilipp Zabel 		dev_err(codec->dev, "Failed to register DAIs: %d\n", ret);
8141abd9184SPhilipp Zabel 		goto err_dai;
8151abd9184SPhilipp Zabel 	}
8161abd9184SPhilipp Zabel 
8171abd9184SPhilipp Zabel 	return 0;
8181abd9184SPhilipp Zabel 
8191abd9184SPhilipp Zabel err_dai:
8201abd9184SPhilipp Zabel 	snd_soc_unregister_codec(codec);
8211abd9184SPhilipp Zabel err_reset:
8221abd9184SPhilipp Zabel 	gpio_set_value(pdata->gpio_power, 0);
8231abd9184SPhilipp Zabel 	gpio_free(pdata->gpio_reset);
8241abd9184SPhilipp Zabel err_gpio:
8251abd9184SPhilipp Zabel 	gpio_free(pdata->gpio_power);
8261abd9184SPhilipp Zabel err_out:
8271abd9184SPhilipp Zabel 	return ret;
8281abd9184SPhilipp Zabel }
8291abd9184SPhilipp Zabel 
8301abd9184SPhilipp Zabel static void uda1380_unregister(struct uda1380_priv *uda1380)
8311abd9184SPhilipp Zabel {
8321abd9184SPhilipp Zabel 	struct snd_soc_codec *codec = &uda1380->codec;
8331abd9184SPhilipp Zabel 	struct uda1380_platform_data *pdata = codec->dev->platform_data;
8341abd9184SPhilipp Zabel 
8351abd9184SPhilipp Zabel 	snd_soc_unregister_dais(uda1380_dai, ARRAY_SIZE(uda1380_dai));
8361abd9184SPhilipp Zabel 	snd_soc_unregister_codec(&uda1380->codec);
8371abd9184SPhilipp Zabel 
8381abd9184SPhilipp Zabel 	gpio_set_value(pdata->gpio_power, 0);
8391abd9184SPhilipp Zabel 	gpio_free(pdata->gpio_reset);
8401abd9184SPhilipp Zabel 	gpio_free(pdata->gpio_power);
8411abd9184SPhilipp Zabel 
8421abd9184SPhilipp Zabel 	kfree(uda1380);
8431abd9184SPhilipp Zabel 	uda1380_codec = NULL;
8441abd9184SPhilipp Zabel }
845b7482f52SPhilipp Zabel 
846b7482f52SPhilipp Zabel #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
8471abd9184SPhilipp Zabel static __devinit int uda1380_i2c_probe(struct i2c_client *i2c,
84888fc39d7SJean Delvare 				      const struct i2c_device_id *id)
849b7482f52SPhilipp Zabel {
8501abd9184SPhilipp Zabel 	struct uda1380_priv *uda1380;
8511abd9184SPhilipp Zabel 	struct snd_soc_codec *codec;
852b7482f52SPhilipp Zabel 	int ret;
853b7482f52SPhilipp Zabel 
8541abd9184SPhilipp Zabel 	uda1380 = kzalloc(sizeof(struct uda1380_priv), GFP_KERNEL);
8551abd9184SPhilipp Zabel 	if (uda1380 == NULL)
8561abd9184SPhilipp Zabel 		return -ENOMEM;
8571abd9184SPhilipp Zabel 
8581abd9184SPhilipp Zabel 	codec = &uda1380->codec;
8591abd9184SPhilipp Zabel 	codec->hw_write = (hw_write_t)i2c_master_send;
8601abd9184SPhilipp Zabel 
8611abd9184SPhilipp Zabel 	i2c_set_clientdata(i2c, uda1380);
862b7482f52SPhilipp Zabel 	codec->control_data = i2c;
863b7482f52SPhilipp Zabel 
8641abd9184SPhilipp Zabel 	codec->dev = &i2c->dev;
8651abd9184SPhilipp Zabel 
8661abd9184SPhilipp Zabel 	ret = uda1380_register(uda1380);
8671abd9184SPhilipp Zabel 	if (ret != 0)
8681abd9184SPhilipp Zabel 		kfree(uda1380);
869b7482f52SPhilipp Zabel 
870b7482f52SPhilipp Zabel 	return ret;
871b7482f52SPhilipp Zabel }
872b7482f52SPhilipp Zabel 
8731abd9184SPhilipp Zabel static int __devexit uda1380_i2c_remove(struct i2c_client *i2c)
874b7482f52SPhilipp Zabel {
8751abd9184SPhilipp Zabel 	struct uda1380_priv *uda1380 = i2c_get_clientdata(i2c);
8761abd9184SPhilipp Zabel 	uda1380_unregister(uda1380);
877b7482f52SPhilipp Zabel 	return 0;
878b7482f52SPhilipp Zabel }
879b7482f52SPhilipp Zabel 
88088fc39d7SJean Delvare static const struct i2c_device_id uda1380_i2c_id[] = {
88188fc39d7SJean Delvare 	{ "uda1380", 0 },
88288fc39d7SJean Delvare 	{ }
88388fc39d7SJean Delvare };
88488fc39d7SJean Delvare MODULE_DEVICE_TABLE(i2c, uda1380_i2c_id);
885b7482f52SPhilipp Zabel 
886b7482f52SPhilipp Zabel static struct i2c_driver uda1380_i2c_driver = {
887b7482f52SPhilipp Zabel 	.driver = {
888b7482f52SPhilipp Zabel 		.name =  "UDA1380 I2C Codec",
889b7482f52SPhilipp Zabel 		.owner = THIS_MODULE,
890b7482f52SPhilipp Zabel 	},
89188fc39d7SJean Delvare 	.probe =    uda1380_i2c_probe,
8921abd9184SPhilipp Zabel 	.remove =   __devexit_p(uda1380_i2c_remove),
89388fc39d7SJean Delvare 	.id_table = uda1380_i2c_id,
894b7482f52SPhilipp Zabel };
895b7482f52SPhilipp Zabel #endif
896b7482f52SPhilipp Zabel 
897c9b3a40fSTakashi Iwai static int __init uda1380_modinit(void)
89864089b84SMark Brown {
8991abd9184SPhilipp Zabel 	int ret;
9001abd9184SPhilipp Zabel #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
9011abd9184SPhilipp Zabel 	ret = i2c_add_driver(&uda1380_i2c_driver);
9021abd9184SPhilipp Zabel 	if (ret != 0)
9031abd9184SPhilipp Zabel 		pr_err("Failed to register UDA1380 I2C driver: %d\n", ret);
9041abd9184SPhilipp Zabel #endif
9051abd9184SPhilipp Zabel 	return 0;
90664089b84SMark Brown }
90764089b84SMark Brown module_init(uda1380_modinit);
90864089b84SMark Brown 
90964089b84SMark Brown static void __exit uda1380_exit(void)
91064089b84SMark Brown {
9111abd9184SPhilipp Zabel #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
9121abd9184SPhilipp Zabel 	i2c_del_driver(&uda1380_i2c_driver);
9131abd9184SPhilipp Zabel #endif
91464089b84SMark Brown }
91564089b84SMark Brown module_exit(uda1380_exit);
91664089b84SMark Brown 
917b7482f52SPhilipp Zabel MODULE_AUTHOR("Giorgio Padrin");
918b7482f52SPhilipp Zabel MODULE_DESCRIPTION("Audio support for codec Philips UDA1380");
919b7482f52SPhilipp Zabel MODULE_LICENSE("GPL");
920