xref: /OK3568_Linux_fs/kernel/sound/soc/codecs/es8396.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0
2*4882a593Smuzhiyun //
3*4882a593Smuzhiyun // es8396.c  --  ES8396 ALSA SoC Audio Codec
4*4882a593Smuzhiyun //
5*4882a593Smuzhiyun // Copyright (C) 2014 Everest Semiconductor Co., Ltd
6*4882a593Smuzhiyun //
7*4882a593Smuzhiyun // Authors:  David Yang(yangxiaohua@everest-semi.com)
8*4882a593Smuzhiyun 
9*4882a593Smuzhiyun #include <linux/module.h>
10*4882a593Smuzhiyun #include <linux/kernel.h>
11*4882a593Smuzhiyun #include <linux/init.h>
12*4882a593Smuzhiyun #include <linux/delay.h>
13*4882a593Smuzhiyun #include <linux/pm.h>
14*4882a593Smuzhiyun #include <linux/i2c.h>
15*4882a593Smuzhiyun #include <linux/slab.h>
16*4882a593Smuzhiyun #include <linux/regmap.h>
17*4882a593Smuzhiyun #include <linux/stddef.h>
18*4882a593Smuzhiyun #include <sound/core.h>
19*4882a593Smuzhiyun #include <sound/pcm.h>
20*4882a593Smuzhiyun #include <sound/pcm_params.h>
21*4882a593Smuzhiyun #include <sound/tlv.h>
22*4882a593Smuzhiyun #include <sound/soc.h>
23*4882a593Smuzhiyun #include <sound/initval.h>
24*4882a593Smuzhiyun #include <linux/gpio.h>
25*4882a593Smuzhiyun #include <linux/of_gpio.h>
26*4882a593Smuzhiyun #include <linux/mutex.h>
27*4882a593Smuzhiyun #include <linux/clk.h>
28*4882a593Smuzhiyun #include "es8396.h"
29*4882a593Smuzhiyun 
30*4882a593Smuzhiyun static int es8396_set_bias_level(struct snd_soc_component *component,
31*4882a593Smuzhiyun 				 enum snd_soc_bias_level level);
32*4882a593Smuzhiyun 
33*4882a593Smuzhiyun /*
34*4882a593Smuzhiyun  * ES8396 register cache
35*4882a593Smuzhiyun  */
36*4882a593Smuzhiyun static struct reg_default es8396_reg_defaults[] = {
37*4882a593Smuzhiyun 	{0x00, 0x00},
38*4882a593Smuzhiyun 	{0x01, 0x00},
39*4882a593Smuzhiyun 	{0x02, 0x80},
40*4882a593Smuzhiyun 	{0x03, 0x00},
41*4882a593Smuzhiyun 	{0x04, 0x00},
42*4882a593Smuzhiyun 	{0x05, 0x00},
43*4882a593Smuzhiyun 	{0x06, 0x00},
44*4882a593Smuzhiyun 	{0x07, 0x00},
45*4882a593Smuzhiyun 	{0x08, 0x50},
46*4882a593Smuzhiyun 	{0x09, 0x04},
47*4882a593Smuzhiyun 	{0x0a, 0x00},
48*4882a593Smuzhiyun 	{0x0b, 0x20},
49*4882a593Smuzhiyun 	{0x0c, 0x20},
50*4882a593Smuzhiyun 	{0x0d, 0x00},
51*4882a593Smuzhiyun 	{0x0e, 0x00},
52*4882a593Smuzhiyun 	{0x0f, 0x00},
53*4882a593Smuzhiyun 
54*4882a593Smuzhiyun 	{0x10, 0x00},
55*4882a593Smuzhiyun 	{0x11, 0x00},
56*4882a593Smuzhiyun 	{0x12, 0x00},
57*4882a593Smuzhiyun 	{0x13, 0x00},
58*4882a593Smuzhiyun 	{0x14, 0x00},
59*4882a593Smuzhiyun 	{0x15, 0x00},
60*4882a593Smuzhiyun 	{0x16, 0x00},
61*4882a593Smuzhiyun 	{0x17, 0x00},
62*4882a593Smuzhiyun 	{0x18, 0x00},
63*4882a593Smuzhiyun 	{0x19, 0x00},
64*4882a593Smuzhiyun 	{0x1a, 0x00},
65*4882a593Smuzhiyun 	{0x1b, 0x00},
66*4882a593Smuzhiyun 	{0x1c, 0x00},
67*4882a593Smuzhiyun 	{0x1d, 0x00},
68*4882a593Smuzhiyun 	{0x1e, 0x00},
69*4882a593Smuzhiyun 	{0x1f, 0x00},
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun 	{0x20, 0x00},
72*4882a593Smuzhiyun 	{0x21, 0x00},
73*4882a593Smuzhiyun 	{0x22, 0x00},
74*4882a593Smuzhiyun 	{0x23, 0x00},
75*4882a593Smuzhiyun 	{0x24, 0x00},
76*4882a593Smuzhiyun 	{0x25, 0x00},
77*4882a593Smuzhiyun 	{0x26, 0x11},
78*4882a593Smuzhiyun 	{0x27, 0x00},
79*4882a593Smuzhiyun 	{0x28, 0x00},
80*4882a593Smuzhiyun 	{0x29, 0x04},
81*4882a593Smuzhiyun 	{0x2a, 0x00},
82*4882a593Smuzhiyun 	{0x2b, 0x33},
83*4882a593Smuzhiyun 	{0x2c, 0x00},
84*4882a593Smuzhiyun 	{0x2d, 0x04},
85*4882a593Smuzhiyun 	{0x2e, 0x00},
86*4882a593Smuzhiyun 	{0x2f, 0x11},
87*4882a593Smuzhiyun 
88*4882a593Smuzhiyun 	{0x30, 0x00},
89*4882a593Smuzhiyun 	{0x31, 0x04},
90*4882a593Smuzhiyun 	{0x32, 0x00},
91*4882a593Smuzhiyun 	{0x33, 0x11},
92*4882a593Smuzhiyun 	{0x34, 0x00},
93*4882a593Smuzhiyun 	{0x35, 0x04},
94*4882a593Smuzhiyun 	{0x36, 0x00},
95*4882a593Smuzhiyun 	{0x37, 0x11},
96*4882a593Smuzhiyun 	{0x38, 0x00},
97*4882a593Smuzhiyun 	{0x39, 0x04},
98*4882a593Smuzhiyun 	{0x3a, 0x44},
99*4882a593Smuzhiyun 	{0x3b, 0x00},
100*4882a593Smuzhiyun 	{0x3c, 0x20},
101*4882a593Smuzhiyun 	{0x3d, 0x00},
102*4882a593Smuzhiyun 	{0x3e, 0x00},
103*4882a593Smuzhiyun 	{0x3f, 0x00},
104*4882a593Smuzhiyun 
105*4882a593Smuzhiyun 	{0x40, 0x08},
106*4882a593Smuzhiyun 	{0x41, 0x88},
107*4882a593Smuzhiyun 	{0x42, 0x20},
108*4882a593Smuzhiyun 	{0x43, 0x82},
109*4882a593Smuzhiyun 	{0x44, 0x03},
110*4882a593Smuzhiyun 	{0x45, 0xa0},
111*4882a593Smuzhiyun 	{0x46, 0x00},
112*4882a593Smuzhiyun 	{0x47, 0x00},
113*4882a593Smuzhiyun 	{0x48, 0x01},
114*4882a593Smuzhiyun 	{0x49, 0x01},
115*4882a593Smuzhiyun 	{0x4a, 0x80},
116*4882a593Smuzhiyun 	{0x4b, 0x80},
117*4882a593Smuzhiyun 	{0x4c, 0x80},
118*4882a593Smuzhiyun 	{0x4d, 0x80},
119*4882a593Smuzhiyun 	{0x4e, 0x84},
120*4882a593Smuzhiyun 	{0x4f, 0x84},
121*4882a593Smuzhiyun 
122*4882a593Smuzhiyun 	{0x50, 0x84},
123*4882a593Smuzhiyun 	{0x51, 0x84},
124*4882a593Smuzhiyun 	{0x52, 0xc0},
125*4882a593Smuzhiyun 	{0x53, 0x80},
126*4882a593Smuzhiyun 	{0x54, 0x00},
127*4882a593Smuzhiyun 	{0x55, 0x00},
128*4882a593Smuzhiyun 	{0x56, 0xc0},
129*4882a593Smuzhiyun 	{0x57, 0xc0},
130*4882a593Smuzhiyun 	{0x58, 0x0b},
131*4882a593Smuzhiyun 	{0x59, 0x32},
132*4882a593Smuzhiyun 	{0x5a, 0x00},
133*4882a593Smuzhiyun 	{0x5b, 0x1f},
134*4882a593Smuzhiyun 	{0x5c, 0xc0},
135*4882a593Smuzhiyun 	{0x5d, 0x00},
136*4882a593Smuzhiyun 	{0x5e, 0xfc},
137*4882a593Smuzhiyun 	{0x5f, 0x02},
138*4882a593Smuzhiyun 
139*4882a593Smuzhiyun 	{0x60, 0x00},
140*4882a593Smuzhiyun 	{0x61, 0x00},
141*4882a593Smuzhiyun 	{0x62, 0x00},
142*4882a593Smuzhiyun 	{0x63, 0x00},
143*4882a593Smuzhiyun 	{0x64, 0x00},
144*4882a593Smuzhiyun 	{0x65, 0x00},
145*4882a593Smuzhiyun 	{0x66, 0x80},
146*4882a593Smuzhiyun 	{0x67, 0x00},
147*4882a593Smuzhiyun 	{0x68, 0x00},
148*4882a593Smuzhiyun 	{0x69, 0x00},
149*4882a593Smuzhiyun 	{0x6a, 0xc0},
150*4882a593Smuzhiyun 	{0x6b, 0xc0},
151*4882a593Smuzhiyun 	{0x6c, 0x00},
152*4882a593Smuzhiyun 	{0x6d, 0x00},
153*4882a593Smuzhiyun 	{0x6e, 0xc8},
154*4882a593Smuzhiyun 	{0x6f, 0x00},
155*4882a593Smuzhiyun 
156*4882a593Smuzhiyun 	{0x70, 0xd3},
157*4882a593Smuzhiyun 	{0x71, 0x90},
158*4882a593Smuzhiyun 	{0x72, 0x00},
159*4882a593Smuzhiyun 	{0x73, 0x00},
160*4882a593Smuzhiyun 	{0x74, 0x88},
161*4882a593Smuzhiyun 	{0x75, 0xc1},
162*4882a593Smuzhiyun 	{0x76, 0x00},
163*4882a593Smuzhiyun 	{0x77, 0x00},
164*4882a593Smuzhiyun 	{0x7a, 0x00},
165*4882a593Smuzhiyun 	{0x7b, 0x00},
166*4882a593Smuzhiyun };
167*4882a593Smuzhiyun 
168*4882a593Smuzhiyun static u8 es8396_equalizer_lpf_bt_incall[] = {
169*4882a593Smuzhiyun 	0x6D, 0x27, 0x64, 0x09, 0x4C, 0xA3, 0x53, 0x07, 0x6D, 0x27, 0x64, 0x09,
170*4882a593Smuzhiyun 	0x8D, 0xE5, 0x23, 0x00, 0x2A, 0xA3, 0x4A, 0x22,
171*4882a593Smuzhiyun 	0x6D, 0x27, 0x64, 0x09, 0x4C, 0xA3, 0x53, 0x07, 0x6D, 0x27, 0x64, 0x09,
172*4882a593Smuzhiyun 	0x8D, 0xE5, 0x23, 0x00, 0x2A, 0xA3, 0x4A, 0x22,
173*4882a593Smuzhiyun 	0x6D, 0x27, 0x64, 0x09, 0x4C, 0xA3, 0x53, 0x07, 0x6D, 0x27, 0x64, 0x09,
174*4882a593Smuzhiyun 	0x8D, 0xE5, 0x23, 0x00, 0x2A, 0xA3, 0x4A, 0x22,
175*4882a593Smuzhiyun };
176*4882a593Smuzhiyun 
177*4882a593Smuzhiyun struct sp_config {
178*4882a593Smuzhiyun 	u8 spc, mmcc, spfs;
179*4882a593Smuzhiyun 	u32 srate;
180*4882a593Smuzhiyun 	u8 lrcdiv;
181*4882a593Smuzhiyun 	u8 sclkdiv;
182*4882a593Smuzhiyun };
183*4882a593Smuzhiyun 
184*4882a593Smuzhiyun /* codec private data */
185*4882a593Smuzhiyun struct es8396_private {
186*4882a593Smuzhiyun 	struct snd_soc_component *component;
187*4882a593Smuzhiyun 	struct sp_config config[3];
188*4882a593Smuzhiyun 	struct regmap *regmap;
189*4882a593Smuzhiyun 	u8 sysclk[3];
190*4882a593Smuzhiyun 	u32 mclk[3];
191*4882a593Smuzhiyun 	struct clk *mclk_clock;
192*4882a593Smuzhiyun 
193*4882a593Smuzhiyun 	/* platform dependent DVDD voltage configuration */
194*4882a593Smuzhiyun 	u8 dvdd_pwr_vol;
195*4882a593Smuzhiyun 
196*4882a593Smuzhiyun 	/* platform dependent CLASS D Mono mode configuration */
197*4882a593Smuzhiyun 	bool spkmono;
198*4882a593Smuzhiyun 	/* platform dependent earpiece mode configuration */
199*4882a593Smuzhiyun 	bool earpiece;
200*4882a593Smuzhiyun 	/* platform dependent monon/p differential mode configuration */
201*4882a593Smuzhiyun 	bool monoin_differential;
202*4882a593Smuzhiyun 	/* platform dependent lout/rout differential mode configuration */
203*4882a593Smuzhiyun 	bool lno_differential;
204*4882a593Smuzhiyun 
205*4882a593Smuzhiyun 	/* platform dependent analog ldo level configuration */
206*4882a593Smuzhiyun 	u8 ana_ldo_lvl;
207*4882a593Smuzhiyun 	/* platform dependent speaker ldo level configuration */
208*4882a593Smuzhiyun 	u8 spk_ldo_lvl;
209*4882a593Smuzhiyun 	/* platform dependent mic bias voltage configuration */
210*4882a593Smuzhiyun 	u8 mic_bias_lvl;
211*4882a593Smuzhiyun 	u8 dmic_amic;
212*4882a593Smuzhiyun 
213*4882a593Smuzhiyun 	bool jackdet_enable;
214*4882a593Smuzhiyun 
215*4882a593Smuzhiyun 	u8 gpio_int_pol;
216*4882a593Smuzhiyun 
217*4882a593Smuzhiyun 	int shutdwn_delay;
218*4882a593Smuzhiyun 	int pon_delay;
219*4882a593Smuzhiyun 	struct gpio_desc *spk_ctl_gpio;
220*4882a593Smuzhiyun 	struct gpio_desc *lineout_ctl_gpio;
221*4882a593Smuzhiyun 
222*4882a593Smuzhiyun 	bool calibrate;
223*4882a593Smuzhiyun 	u8 output_device_selected;
224*4882a593Smuzhiyun 	u8 aif1_select;
225*4882a593Smuzhiyun 	u8 aif2_select;
226*4882a593Smuzhiyun 	/*
227*4882a593Smuzhiyun 	 * Add a delay work-quenue, to debug DC calibration
228*4882a593Smuzhiyun 	 */
229*4882a593Smuzhiyun 	struct mutex adc_depop_mlock;
230*4882a593Smuzhiyun 	struct delayed_work adc_depop_work;
231*4882a593Smuzhiyun 
232*4882a593Smuzhiyun 	/* for playback pop noise */
233*4882a593Smuzhiyun 	struct mutex pcm_depop_mlock;
234*4882a593Smuzhiyun 	struct delayed_work pcm_pop_work;
235*4882a593Smuzhiyun 	/* for playback pop noise */
236*4882a593Smuzhiyun 	struct mutex pcm_shutdown_depop_mlock;
237*4882a593Smuzhiyun 	struct delayed_work pcm_shutdown_depop_work;
238*4882a593Smuzhiyun 
239*4882a593Smuzhiyun 	/* for voice pop noise */
240*4882a593Smuzhiyun 	struct mutex voice_depop_mlock;
241*4882a593Smuzhiyun 	struct delayed_work voice_pop_work;
242*4882a593Smuzhiyun 	/* for voice pop noise */
243*4882a593Smuzhiyun 	struct mutex voice_shutdown_depop_mlock;
244*4882a593Smuzhiyun 	struct delayed_work voice_shutdown_depop_work;
245*4882a593Smuzhiyun 
246*4882a593Smuzhiyun 	/* for hp calibration */
247*4882a593Smuzhiyun 	struct mutex init_cali_mlock;
248*4882a593Smuzhiyun 	struct delayed_work init_cali_work;
249*4882a593Smuzhiyun 	int pcm_pop_work_retry;
250*4882a593Smuzhiyun };
251*4882a593Smuzhiyun 
es8396_valid_micbias(u8 micbias)252*4882a593Smuzhiyun static bool es8396_valid_micbias(u8 micbias)
253*4882a593Smuzhiyun {
254*4882a593Smuzhiyun 	switch (micbias) {
255*4882a593Smuzhiyun 	case MICBIAS_3V:
256*4882a593Smuzhiyun 	case MICBIAS_2_8V:
257*4882a593Smuzhiyun 	case MICBIAS_2_5V:
258*4882a593Smuzhiyun 	case MICBIAS_2_3V:
259*4882a593Smuzhiyun 	case MICBIAS_2V:
260*4882a593Smuzhiyun 	case MICBIAS_1_5V:
261*4882a593Smuzhiyun 		return true;
262*4882a593Smuzhiyun 	default:
263*4882a593Smuzhiyun 		break;
264*4882a593Smuzhiyun 	}
265*4882a593Smuzhiyun 	return false;
266*4882a593Smuzhiyun }
267*4882a593Smuzhiyun 
es8396_valid_analdo(u8 ldolvl)268*4882a593Smuzhiyun static bool es8396_valid_analdo(u8 ldolvl)
269*4882a593Smuzhiyun {
270*4882a593Smuzhiyun 	switch (ldolvl) {
271*4882a593Smuzhiyun 	case ANA_LDO_3V:
272*4882a593Smuzhiyun 	case ANA_LDO_2_9V:
273*4882a593Smuzhiyun 	case ANA_LDO_2_8V:
274*4882a593Smuzhiyun 	case ANA_LDO_2_7V:
275*4882a593Smuzhiyun 	case ANA_LDO_2_4V:
276*4882a593Smuzhiyun 	case ANA_LDO_2_3V:
277*4882a593Smuzhiyun 	case ANA_LDO_2_2V:
278*4882a593Smuzhiyun 	case ANA_LDO_2_1V:
279*4882a593Smuzhiyun 		return true;
280*4882a593Smuzhiyun 	default:
281*4882a593Smuzhiyun 		break;
282*4882a593Smuzhiyun 	}
283*4882a593Smuzhiyun 	return false;
284*4882a593Smuzhiyun }
285*4882a593Smuzhiyun 
es8396_valid_spkldo(u8 ldolvl)286*4882a593Smuzhiyun static bool es8396_valid_spkldo(u8 ldolvl)
287*4882a593Smuzhiyun {
288*4882a593Smuzhiyun 	switch (ldolvl) {
289*4882a593Smuzhiyun 	case SPK_LDO_3_3V:
290*4882a593Smuzhiyun 	case SPK_LDO_3_2V:
291*4882a593Smuzhiyun 	case SPK_LDO_3V:
292*4882a593Smuzhiyun 	case SPK_LDO_2_9V:
293*4882a593Smuzhiyun 	case SPK_LDO_2_8V:
294*4882a593Smuzhiyun 	case SPK_LDO_2_6V:
295*4882a593Smuzhiyun 	case SPK_LDO_2_5V:
296*4882a593Smuzhiyun 	case SPK_LDO_2_4V:
297*4882a593Smuzhiyun 		return true;
298*4882a593Smuzhiyun 	default:
299*4882a593Smuzhiyun 		break;
300*4882a593Smuzhiyun 	}
301*4882a593Smuzhiyun 	return false;
302*4882a593Smuzhiyun }
303*4882a593Smuzhiyun 
pcm_shutdown_depop_events(struct work_struct * work)304*4882a593Smuzhiyun static void pcm_shutdown_depop_events(struct work_struct *work)
305*4882a593Smuzhiyun {
306*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
307*4882a593Smuzhiyun 						     pcm_shutdown_depop_work.work);
308*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
309*4882a593Smuzhiyun 
310*4882a593Smuzhiyun 	mutex_lock(&es8396->pcm_shutdown_depop_mlock);
311*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP1_IN_FMT_REG1F,
312*4882a593Smuzhiyun 				      0x40, 0x40);
313*4882a593Smuzhiyun 	es8396->aif1_select &= 0xfe;
314*4882a593Smuzhiyun 	mutex_unlock(&es8396->pcm_shutdown_depop_mlock);
315*4882a593Smuzhiyun }
316*4882a593Smuzhiyun 
voice_shutdown_depop_events(struct work_struct * work)317*4882a593Smuzhiyun static void voice_shutdown_depop_events(struct work_struct *work)
318*4882a593Smuzhiyun {
319*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
320*4882a593Smuzhiyun 						     voice_shutdown_depop_work.work);
321*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
322*4882a593Smuzhiyun 
323*4882a593Smuzhiyun 	mutex_lock(&es8396->voice_shutdown_depop_mlock);
324*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP2_IN_FMT_REG22,
325*4882a593Smuzhiyun 				      0x7F, 0x53);
326*4882a593Smuzhiyun 	es8396->aif2_select &= 0xfe;
327*4882a593Smuzhiyun 	if (es8396->aif1_select != 0) {
328*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x1A, 0x00);
329*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x67, 0x00);
330*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x69, 0x00);
331*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x66, 0x00);
332*4882a593Smuzhiyun 	}
333*4882a593Smuzhiyun 	mutex_unlock(&es8396->voice_shutdown_depop_mlock);
334*4882a593Smuzhiyun }
335*4882a593Smuzhiyun 
init_cali_work_events(struct work_struct * work)336*4882a593Smuzhiyun static void init_cali_work_events(struct work_struct *work)
337*4882a593Smuzhiyun {
338*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
339*4882a593Smuzhiyun 						     init_cali_work.work);
340*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
341*4882a593Smuzhiyun 
342*4882a593Smuzhiyun 	mutex_lock(&es8396->init_cali_mlock);
343*4882a593Smuzhiyun 	pr_debug("init_cali_work_events\n");
344*4882a593Smuzhiyun 	if (es8396->pcm_pop_work_retry > 0) {
345*4882a593Smuzhiyun 		es8396->pcm_pop_work_retry--;
346*4882a593Smuzhiyun 		pr_debug("Enter into %s  %d\n", __func__, __LINE__);
347*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_OFFSET_CALI_REG6F, 0x83);
348*4882a593Smuzhiyun 		if (es8396->pcm_pop_work_retry) {
349*4882a593Smuzhiyun 			schedule_delayed_work(&es8396->init_cali_work,
350*4882a593Smuzhiyun 					      msecs_to_jiffies(100));
351*4882a593Smuzhiyun 		}
352*4882a593Smuzhiyun 	}
353*4882a593Smuzhiyun 	snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x3C);
354*4882a593Smuzhiyun 
355*4882a593Smuzhiyun 	/* use line  out */
356*4882a593Smuzhiyun 	msleep(100);
357*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4E, 0x80);
358*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4F, 0x81);
359*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4A, 0x60);
360*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4B, 0x60);
361*4882a593Smuzhiyun 
362*4882a593Smuzhiyun 	mutex_unlock(&es8396->init_cali_mlock);
363*4882a593Smuzhiyun }
364*4882a593Smuzhiyun 
voice_pop_work_events(struct work_struct * work)365*4882a593Smuzhiyun static void voice_pop_work_events(struct work_struct *work)
366*4882a593Smuzhiyun {
367*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
368*4882a593Smuzhiyun 						     voice_pop_work.work);
369*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
370*4882a593Smuzhiyun 	int i;
371*4882a593Smuzhiyun 
372*4882a593Smuzhiyun 	mutex_lock(&es8396->voice_depop_mlock);
373*4882a593Smuzhiyun 	pr_debug("voice_pop_work_events\n");
374*4882a593Smuzhiyun 	/*
375*4882a593Smuzhiyun 	 * set the clock source to pll out
376*4882a593Smuzhiyun 	 * set divider for voice playback
377*4882a593Smuzhiyun 	 * set Equalizer
378*4882a593Smuzhiyun 	 * set DAC source from equalizer
379*4882a593Smuzhiyun 	 */
380*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP2_IN_FMT_REG22,
381*4882a593Smuzhiyun 				      0x3F, 0x13);
382*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP2_OUT_FMT_REG23,
383*4882a593Smuzhiyun 				      0x7F, 0x33);
384*4882a593Smuzhiyun 	/* use line out */
385*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4E, 0x80);
386*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4F, 0x81);
387*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4A, 0x60);
388*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4B, 0x60);
389*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x1A, 0x40);	/* Enable HPOUT */
390*4882a593Smuzhiyun 
391*4882a593Smuzhiyun 	/* unmute dac */
392*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x66, 0x00);
393*4882a593Smuzhiyun 
394*4882a593Smuzhiyun 	for (i = 0; i < 120; i = i + 2) {
395*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x6A, 120 - i);
396*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x6B, 120 - i);
397*4882a593Smuzhiyun 		usleep_range(100, 200);
398*4882a593Smuzhiyun 	}
399*4882a593Smuzhiyun 
400*4882a593Smuzhiyun 	mutex_unlock(&es8396->voice_depop_mlock);
401*4882a593Smuzhiyun }
402*4882a593Smuzhiyun 
pcm_pop_work_events(struct work_struct * work)403*4882a593Smuzhiyun static void pcm_pop_work_events(struct work_struct *work)
404*4882a593Smuzhiyun {
405*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
406*4882a593Smuzhiyun 						     pcm_pop_work.work);
407*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
408*4882a593Smuzhiyun 	int i;
409*4882a593Smuzhiyun 
410*4882a593Smuzhiyun 	mutex_lock(&es8396->pcm_depop_mlock);
411*4882a593Smuzhiyun 	pr_debug("pcm_pop_work_events\n");
412*4882a593Smuzhiyun 
413*4882a593Smuzhiyun 	snd_soc_component_write(component, ES8396_SYS_VMID_REF_REG71, 0xFC);
414*4882a593Smuzhiyun 
415*4882a593Smuzhiyun 	/* use line out */
416*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4E, 0x80);
417*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4F, 0x81);
418*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4A, 0x60);
419*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4B, 0x60);
420*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0x03, 0x00);
421*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP1_IN_FMT_REG1F, 0x40, 0x00);
422*4882a593Smuzhiyun 	for (i = 0; i < 120; i = i + 2) {
423*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x6A, 120 - i);
424*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x6B, 120 - i);
425*4882a593Smuzhiyun 		usleep_range(100, 200);
426*4882a593Smuzhiyun 	}
427*4882a593Smuzhiyun 	mutex_unlock(&es8396->pcm_depop_mlock);
428*4882a593Smuzhiyun }
429*4882a593Smuzhiyun 
430*4882a593Smuzhiyun /*********************************************************************
431*4882a593Smuzhiyun  * to power on/off class d with min pop noise
432*4882a593Smuzhiyun  *********************************************************************/
classd_event(struct snd_soc_dapm_widget * w,struct snd_kcontrol * kcontrol,int event)433*4882a593Smuzhiyun static int classd_event(struct snd_soc_dapm_widget *w,
434*4882a593Smuzhiyun 			struct snd_kcontrol *kcontrol, int event)
435*4882a593Smuzhiyun {
436*4882a593Smuzhiyun 	unsigned int regv1, regv2, lvl;
437*4882a593Smuzhiyun 	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
438*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
439*4882a593Smuzhiyun 
440*4882a593Smuzhiyun 	switch (event) {
441*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMU:	/* prepare power up */
442*4882a593Smuzhiyun 		/* power up class d */
443*4882a593Smuzhiyun 		pr_debug("SND_SOC_DAPM_PRE_PMU = 0x%x\n", event);
444*4882a593Smuzhiyun 		/* read the clock configure */
445*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
446*4882a593Smuzhiyun 		regv1 &= 0xcf;
447*4882a593Smuzhiyun 		/* enable class d clock */
448*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, regv1);
449*4882a593Smuzhiyun 		/* dac csm startup, dac digital still on */
450*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0xFE, 0x00);
451*4882a593Smuzhiyun 		/* dac analog power on */
452*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_DAC_REF_PWR_CTRL_REG6E,
453*4882a593Smuzhiyun 					      0xff, 0x34);
454*4882a593Smuzhiyun 
455*4882a593Smuzhiyun 		regv2 = snd_soc_component_read(component, ES8396_SPK_CTRL_1_REG3C);
456*4882a593Smuzhiyun 		/* set speaker ldo level */
457*4882a593Smuzhiyun 		if (es8396_valid_spkldo(es8396->spk_ldo_lvl) == false) {
458*4882a593Smuzhiyun 			pr_err("speaker LDO Level error.\n");
459*4882a593Smuzhiyun 			return -EINVAL;
460*4882a593Smuzhiyun 		} else {
461*4882a593Smuzhiyun 			regv1 = regv2 & 0xD8;
462*4882a593Smuzhiyun 			lvl = es8396->spk_ldo_lvl;
463*4882a593Smuzhiyun 			lvl &= 0x07;
464*4882a593Smuzhiyun 			regv1 |= lvl;
465*4882a593Smuzhiyun 			regv1 |= 0x10;
466*4882a593Smuzhiyun 		}
467*4882a593Smuzhiyun 		if (es8396->spkmono == 1) {	/* speaker in mono mode */
468*4882a593Smuzhiyun 			regv1 = regv1 | 0x40;
469*4882a593Smuzhiyun 		} else {
470*4882a593Smuzhiyun 			regv1 = regv1 & 0xbf;
471*4882a593Smuzhiyun 		}
472*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_CTRL_1_REG3C, regv1);
473*4882a593Smuzhiyun 
474*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_CTRL_2_REG3D, 0x10);
475*4882a593Smuzhiyun 
476*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_SPK_MIXER_REG26);
477*4882a593Smuzhiyun 		/* clear pdnspkl_biasgen, clear pdnspkr_biasgen */
478*4882a593Smuzhiyun 		regv1 &= 0xee;
479*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_MIXER_REG26, regv1);
480*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_MIXER_VOL_REG28, 0x33);
481*4882a593Smuzhiyun 
482*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_CTRL_SRC_REG3A, 0xA9);
483*4882a593Smuzhiyun 		/* L&R DAC Vol=-6db */
484*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_LDAC_VOL_REG6A, 0x00);
485*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_RDAC_VOL_REG6B, 0x00);
486*4882a593Smuzhiyun 
487*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_HP_MIXER_BOOST_REG2B);
488*4882a593Smuzhiyun 		regv1 &= 0xcc;
489*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_HP_MIXER_BOOST_REG2B, regv1);
490*4882a593Smuzhiyun 
491*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_CPHP_CTRL_3_REG44);
492*4882a593Smuzhiyun 		regv1 &= 0xcc;
493*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CPHP_CTRL_3_REG44, regv1);
494*4882a593Smuzhiyun 
495*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_CPHP_CTRL_1_REG42);
496*4882a593Smuzhiyun 		regv1 &= 0xdf;
497*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CPHP_CTRL_1_REG42, regv1);
498*4882a593Smuzhiyun 
499*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_CPHP_CTRL_2_REG43);
500*4882a593Smuzhiyun 		regv1 &= 0x7f;
501*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CPHP_CTRL_2_REG43, regv1);
502*4882a593Smuzhiyun 		es8396->output_device_selected = 0;
503*4882a593Smuzhiyun 		break;
504*4882a593Smuzhiyun 	case SND_SOC_DAPM_POST_PMU:	/* after power up */
505*4882a593Smuzhiyun 		pr_debug("SND_SOC_DAPM_POST_PMU = 0x%x\n", event);
506*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->pcm_pop_work,
507*4882a593Smuzhiyun 				      msecs_to_jiffies(50));
508*4882a593Smuzhiyun 		break;
509*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMD:	/* prepare power down */
510*4882a593Smuzhiyun 		pr_debug("SND_SOC_DAPM_PRE_PMD = 0x%x\n", event);
511*4882a593Smuzhiyun 		/* read the clock configure */
512*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
513*4882a593Smuzhiyun 		regv1 |= 0x10;
514*4882a593Smuzhiyun 		/* stop class d clock */
515*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, regv1);
516*4882a593Smuzhiyun 		/* dac csm startup, dac digital still on */
517*4882a593Smuzhiyun 		/* snd_soc_component_update_bits(w->component, ES8396_DAC_CSM_REG66,
518*4882a593Smuzhiyun 				       0x01, 0x01); */
519*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_SPK_EN_VOL_REG3B);
520*4882a593Smuzhiyun 		regv1 &= 0x77;
521*4882a593Smuzhiyun 		/* clear enspk_l,enspk_r */
522*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_EN_VOL_REG3B, regv1);
523*4882a593Smuzhiyun 
524*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_SPK_CTRL_SRC_REG3A);
525*4882a593Smuzhiyun 		regv1 |= 0x44;	/* set pdnspkl_biasgen, set pdnspkr_biasgen */
526*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_CTRL_SRC_REG3A, regv1);
527*4882a593Smuzhiyun 		regv1 = snd_soc_component_read(component, ES8396_SPK_MIXER_REG26);
528*4882a593Smuzhiyun 		/* clear pdnspkl_biasgen, clear pdnspkr_biasgen */
529*4882a593Smuzhiyun 		regv1 |= 0x11;
530*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SPK_MIXER_REG26, regv1);
531*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SPK_CTRL_1_REG3C, 0x20,
532*4882a593Smuzhiyun 					      0x20);
533*4882a593Smuzhiyun 		break;
534*4882a593Smuzhiyun 	case SND_SOC_DAPM_POST_PMD:	/* after power down */
535*4882a593Smuzhiyun 		pr_debug("SND_SOC_DAPM_POST_PMD = 0x%x\n", event);
536*4882a593Smuzhiyun 		break;
537*4882a593Smuzhiyun 	default:
538*4882a593Smuzhiyun 		break;
539*4882a593Smuzhiyun 	}
540*4882a593Smuzhiyun 	return 0;
541*4882a593Smuzhiyun }
542*4882a593Smuzhiyun 
micbias_event(struct snd_soc_dapm_widget * w,struct snd_kcontrol * kcontrol,int event)543*4882a593Smuzhiyun static int micbias_event(struct snd_soc_dapm_widget *w,
544*4882a593Smuzhiyun 			 struct snd_kcontrol *kcontrol, int event)
545*4882a593Smuzhiyun {
546*4882a593Smuzhiyun 	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
547*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
548*4882a593Smuzhiyun 	unsigned int regv;
549*4882a593Smuzhiyun 
550*4882a593Smuzhiyun 	switch (event) {
551*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMU:
552*4882a593Smuzhiyun 		if (es8396_valid_micbias(es8396->mic_bias_lvl) == false) {
553*4882a593Smuzhiyun 			pr_err("MIC BIAS Level error.\n");
554*4882a593Smuzhiyun 			return -EINVAL;
555*4882a593Smuzhiyun 		} else {
556*4882a593Smuzhiyun 			regv = es8396->mic_bias_lvl;
557*4882a593Smuzhiyun 			regv &= 0x07;
558*4882a593Smuzhiyun 			regv = (regv << 4) | 0x08;
559*4882a593Smuzhiyun 			/* enable micbias1 */
560*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_SYS_MICBIAS_CTRL_REG74,
561*4882a593Smuzhiyun 						regv);
562*4882a593Smuzhiyun 		}
563*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_ALRCK_GPIO_SEL_REG15);
564*4882a593Smuzhiyun 		if (es8396->dmic_amic == MIC_DMIC) {
565*4882a593Smuzhiyun 			regv &= 0xf0;	/* enable DMIC CLK */
566*4882a593Smuzhiyun 			regv |= 0x0A;
567*4882a593Smuzhiyun 		} else {
568*4882a593Smuzhiyun 			regv &= 0xf0;	/* disable DMIC CLK */
569*4882a593Smuzhiyun 		}
570*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ALRCK_GPIO_SEL_REG15, regv);
571*4882a593Smuzhiyun 		break;
572*4882a593Smuzhiyun 	case SND_SOC_DAPM_POST_PMD:
573*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_ALRCK_GPIO_SEL_REG15);
574*4882a593Smuzhiyun 		regv &= 0xf0;	/* disable DMIC CLK */
575*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ALRCK_GPIO_SEL_REG15, regv);
576*4882a593Smuzhiyun 		break;
577*4882a593Smuzhiyun 	default:
578*4882a593Smuzhiyun 		break;
579*4882a593Smuzhiyun 	}
580*4882a593Smuzhiyun 
581*4882a593Smuzhiyun 	return 0;
582*4882a593Smuzhiyun }
583*4882a593Smuzhiyun 
adc_depop_work_events(struct work_struct * work)584*4882a593Smuzhiyun static void adc_depop_work_events(struct work_struct *work)
585*4882a593Smuzhiyun {
586*4882a593Smuzhiyun 	struct es8396_private *es8396 = container_of(work, struct es8396_private,
587*4882a593Smuzhiyun 						     adc_depop_work.work);
588*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
589*4882a593Smuzhiyun 
590*4882a593Smuzhiyun 	pr_debug("adc_depop_work_events\n");
591*4882a593Smuzhiyun 	mutex_lock(&es8396->adc_depop_mlock);
592*4882a593Smuzhiyun 	snd_soc_component_update_bits(component, ES8396_SDP1_OUT_FMT_REG20, 0x40, 0x00);
593*4882a593Smuzhiyun 	mutex_unlock(&es8396->adc_depop_mlock);
594*4882a593Smuzhiyun }
595*4882a593Smuzhiyun 
adc_event(struct snd_soc_dapm_widget * w,struct snd_kcontrol * kcontrol,int event)596*4882a593Smuzhiyun static int adc_event(struct snd_soc_dapm_widget *w,
597*4882a593Smuzhiyun 		     struct snd_kcontrol *kcontrol, int event)
598*4882a593Smuzhiyun {
599*4882a593Smuzhiyun 	unsigned int regv;
600*4882a593Smuzhiyun 	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
601*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
602*4882a593Smuzhiyun 
603*4882a593Smuzhiyun 	pr_debug("Enter into %s  %d\n", __func__, __LINE__);
604*4882a593Smuzhiyun 	switch (event) {
605*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMU:
606*4882a593Smuzhiyun 		pr_debug("Enter into SND_SOC_DAPM_PRE_PMU %s  %d\n", __func__,
607*4882a593Smuzhiyun 			 __LINE__);
608*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP1_OUT_FMT_REG20, 0x40,
609*4882a593Smuzhiyun 					      0x40);
610*4882a593Smuzhiyun 		/* set adc alc */
611*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_1_REG58, 0xC6);
612*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_2_REG59, 0x12);
613*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_4_REG5B, 0x04);
614*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_5_REG5C, 0xC8);
615*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_6_REG5D, 0x11);
616*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x0);
617*4882a593Smuzhiyun 		/* Enable MIC BOOST */
618*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_MIC_IBIAS_EN_REG75, 0x02);
619*4882a593Smuzhiyun 
620*4882a593Smuzhiyun 		/* axMixer Gain boost */
621*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_AX_MIXER_BOOST_REG2F);
622*4882a593Smuzhiyun 		regv |= 0x88;
623*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_BOOST_REG2F, regv);
624*4882a593Smuzhiyun 		/* axmixer vol = +12db */
625*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_VOL_REG30, 0xaa);
626*4882a593Smuzhiyun 		/* axmixer high driver capacility */
627*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_REF_LP_REG31, 0x02);
628*4882a593Smuzhiyun 
629*4882a593Smuzhiyun 		/* MNMixer Gain boost */
630*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_MN_MIXER_BOOST_REG37);
631*4882a593Smuzhiyun 		regv |= 0x88;
632*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_BOOST_REG37, regv);
633*4882a593Smuzhiyun 		/* mnmixer vol = +12db */
634*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_VOL_REG38, 0x44);
635*4882a593Smuzhiyun 		/* mnmixer high driver capacility */
636*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_REF_LP_REG39, 0x02);
637*4882a593Smuzhiyun 
638*4882a593Smuzhiyun 		msleep(200);
639*4882a593Smuzhiyun 		/* ADC STM and Digital Startup, ADC DS Mode */
640*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x00);
641*4882a593Smuzhiyun 		/* force adc stm to normal */
642*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x40);
643*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x0);
644*4882a593Smuzhiyun 		/* ADC Volume =0db */
645*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_LADC_VOL_REG56, 0x0);
646*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_RADC_VOL_REG57, 0x0);
647*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CLK_DIV_REG09, 0x04);
648*4882a593Smuzhiyun 
649*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->adc_depop_work,
650*4882a593Smuzhiyun 				      msecs_to_jiffies(150));
651*4882a593Smuzhiyun 		break;
652*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMD:
653*4882a593Smuzhiyun 		pr_debug("Enter into SND_SOC_DAPM_PRE_PMD %s  %d\n", __func__,
654*4882a593Smuzhiyun 			 __LINE__);
655*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x20);
656*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CLK_DIV_REG09, 0x04);
657*4882a593Smuzhiyun 		break;
658*4882a593Smuzhiyun 	default:
659*4882a593Smuzhiyun 		break;
660*4882a593Smuzhiyun 	}
661*4882a593Smuzhiyun 
662*4882a593Smuzhiyun 	return 0;
663*4882a593Smuzhiyun }
664*4882a593Smuzhiyun 
665*4882a593Smuzhiyun /*********************************************************************
666*4882a593Smuzhiyun  * to power on/off headphone with min pop noise
667*4882a593Smuzhiyun  ********************************************************************/
hpamp_event(struct snd_soc_dapm_widget * w,struct snd_kcontrol * kcontrol,int event)668*4882a593Smuzhiyun static int hpamp_event(struct snd_soc_dapm_widget *w,
669*4882a593Smuzhiyun 		       struct snd_kcontrol *kcontrol, int event)
670*4882a593Smuzhiyun {
671*4882a593Smuzhiyun 	unsigned int regv;
672*4882a593Smuzhiyun 	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
673*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
674*4882a593Smuzhiyun 
675*4882a593Smuzhiyun 	pr_debug("Enter into %s  %d\n", __func__, __LINE__);
676*4882a593Smuzhiyun 	switch (event) {
677*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMU:
678*4882a593Smuzhiyun 		pr_debug("Enter into %s  %d, event = SND_SOC_DAPM_PRE_PMU\n",
679*4882a593Smuzhiyun 			 __func__, __LINE__);
680*4882a593Smuzhiyun 		es8396->output_device_selected = 1;
681*4882a593Smuzhiyun 		break;
682*4882a593Smuzhiyun 	case SND_SOC_DAPM_POST_PMU:
683*4882a593Smuzhiyun 		pr_debug("Enter into %s  %d, event = SND_SOC_DAPM_POST_PMU\n",
684*4882a593Smuzhiyun 			 __func__, __LINE__);
685*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->pcm_pop_work,
686*4882a593Smuzhiyun 				      msecs_to_jiffies(50));
687*4882a593Smuzhiyun 		break;
688*4882a593Smuzhiyun 	case SND_SOC_DAPM_PRE_PMD:
689*4882a593Smuzhiyun 		pr_debug("Enter into %s  %d, event = SND_SOC_DAPM_PRE_PMD\n",
690*4882a593Smuzhiyun 			 __func__, __LINE__);
691*4882a593Smuzhiyun 		/* dac analog power down */
692*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0x42, 0x00);
693*4882a593Smuzhiyun 		break;
694*4882a593Smuzhiyun 	case SND_SOC_DAPM_POST_PMD:
695*4882a593Smuzhiyun 		pr_debug("Enter into %s  %d, event = SND_SOC_DAPM_POST_PMD\n",
696*4882a593Smuzhiyun 			 __func__, __LINE__);
697*4882a593Smuzhiyun 		/* dac analog power down */
698*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0x40, 0x40);
699*4882a593Smuzhiyun 		/* dac analog power down */
700*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_DAC_REF_PWR_CTRL_REG6E,
701*4882a593Smuzhiyun 					      0xC0, 0xC0);
702*4882a593Smuzhiyun 		/* read the clock configure */
703*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
704*4882a593Smuzhiyun 		regv |= 0x20;
705*4882a593Smuzhiyun 		/* stop charge pump clock */
706*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, regv);
707*4882a593Smuzhiyun 
708*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_HP_MIXER_BOOST_REG2B);
709*4882a593Smuzhiyun 		regv |= 0x11;
710*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_HP_MIXER_BOOST_REG2B, regv);
711*4882a593Smuzhiyun 		break;
712*4882a593Smuzhiyun 	default:
713*4882a593Smuzhiyun 		break;
714*4882a593Smuzhiyun 	}
715*4882a593Smuzhiyun 
716*4882a593Smuzhiyun 	return 0;
717*4882a593Smuzhiyun }
718*4882a593Smuzhiyun 
719*4882a593Smuzhiyun /*
720*4882a593Smuzhiyun  * ES8396 Controls
721*4882a593Smuzhiyun  */
722*4882a593Smuzhiyun static const DECLARE_TLV_DB_RANGE(mixvol_tlv,
723*4882a593Smuzhiyun 				  0, 4, TLV_DB_SCALE_ITEM(-1200, 150, 0),
724*4882a593Smuzhiyun 				  8, 11, TLV_DB_SCALE_ITEM(-600, 150, 0));
725*4882a593Smuzhiyun static const DECLARE_TLV_DB_RANGE(boost_tlv,
726*4882a593Smuzhiyun 				  0, 1, TLV_DB_SCALE_ITEM(0, 2000, 0),
727*4882a593Smuzhiyun 				  1, 3, TLV_DB_SCALE_ITEM(2000, 0, 0));
728*4882a593Smuzhiyun 
729*4882a593Smuzhiyun /* -34.5db min scale, 1.5db steps, no mute */
730*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(vol_tlv, -600, 150, 0);
731*4882a593Smuzhiyun /* -34.5db min scale, 1.5db steps, no mute */
732*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(spk_vol_tlv, 0, 150, 0);
733*4882a593Smuzhiyun /* -46.5db min scale, 1.5db steps, no mute */
734*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(hp_tlv, -4800, 1200, 0);
735*4882a593Smuzhiyun /* -16.5db min scale, 1.5db steps, no mute */
736*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(adc_rec_tlv, -9600, 50, 0);
737*4882a593Smuzhiyun 
738*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(lineout_tlv, -1200, 1200, 0);
739*4882a593Smuzhiyun 
740*4882a593Smuzhiyun /* 0db min scale, 6 db steps, no mute */
741*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(dig_tlv, 0, 600, 0);
742*4882a593Smuzhiyun /* 0db min scalem 0.75db steps, no mute */
743*4882a593Smuzhiyun static const DECLARE_TLV_DB_SCALE(vdac_tlv, -9600, 50, 0);
744*4882a593Smuzhiyun 
745*4882a593Smuzhiyun static const char *const alc_func_txt[] = { "Off", "LOn", "ROn", "StereoOn" };
746*4882a593Smuzhiyun 
747*4882a593Smuzhiyun static const struct soc_enum alc_func =
748*4882a593Smuzhiyun SOC_ENUM_SINGLE(ES8396_ADC_ALC_CTRL_1_REG58, 6, 4, alc_func_txt);
749*4882a593Smuzhiyun 
750*4882a593Smuzhiyun /*
751*4882a593Smuzhiyun  *define the line in,mic in, phone in ,and aif1-2 in volume/switch
752*4882a593Smuzhiyun  */
753*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_snd_controls[] = {
754*4882a593Smuzhiyun 	SOC_DOUBLE_R_TLV("DAC Playback Volume",
755*4882a593Smuzhiyun 			 ES8396_DAC_LDAC_VOL_REG6A, ES8396_DAC_RDAC_VOL_REG6B,
756*4882a593Smuzhiyun 			 0, 127, 1, vdac_tlv),
757*4882a593Smuzhiyun 	SOC_DOUBLE_TLV("MNIN MIXER Volume",
758*4882a593Smuzhiyun 		       ES8396_MN_MIXER_VOL_REG38, 4, 0, 3, 1, mixvol_tlv),
759*4882a593Smuzhiyun 
760*4882a593Smuzhiyun 	SOC_DOUBLE_TLV("LIN MIXER Volume",
761*4882a593Smuzhiyun 		       ES8396_LN_MIXER_VOL_REG34, 4, 0, 4, 0, mixvol_tlv),
762*4882a593Smuzhiyun 
763*4882a593Smuzhiyun 	SOC_DOUBLE_TLV("AXIN MIXER Volume",
764*4882a593Smuzhiyun 		       ES8396_AX_MIXER_VOL_REG30, 4, 0, 4, 0, mixvol_tlv),
765*4882a593Smuzhiyun 	SOC_DOUBLE_TLV("Mic Boost Volume",
766*4882a593Smuzhiyun 		       ES8396_ADC_MICBOOST_REG60, 4, 0, 3, 0, boost_tlv),
767*4882a593Smuzhiyun 
768*4882a593Smuzhiyun 	SOC_DOUBLE_R_TLV("ADC Capture Volume",
769*4882a593Smuzhiyun 			 ES8396_ADC_LADC_VOL_REG56, ES8396_ADC_RADC_VOL_REG57,
770*4882a593Smuzhiyun 			 0, 127, 1, adc_rec_tlv),
771*4882a593Smuzhiyun 
772*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Speakerl Playback Volume",
773*4882a593Smuzhiyun 		       ES8396_SPK_EN_VOL_REG3B, 4, 7, 0, spk_vol_tlv),
774*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Speakerr Playback Volume",
775*4882a593Smuzhiyun 		       ES8396_SPK_EN_VOL_REG3B, 0, 7, 0, spk_vol_tlv),
776*4882a593Smuzhiyun 
777*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Headphonel Playback Volume",
778*4882a593Smuzhiyun 		       ES8396_CPHP_ICAL_VOL_REG41, 4, 3, 1, hp_tlv),
779*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Headphoner Playback Volume",
780*4882a593Smuzhiyun 		       ES8396_CPHP_ICAL_VOL_REG41, 0, 3, 1, hp_tlv),
781*4882a593Smuzhiyun 	/*
782*4882a593Smuzhiyun 	 * lineout playback volume
783*4882a593Smuzhiyun 	 */
784*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Lineoutp Playback Volume",
785*4882a593Smuzhiyun 		       ES8396_LNOUT_LO1_GAIN_CTRL_REG4E, 5, 1, 1, lineout_tlv),
786*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Lineoutn Playback Volume",
787*4882a593Smuzhiyun 		       ES8396_LNOUT_RO1_GAIN_CTRL_REG4F, 5, 1, 1, lineout_tlv),
788*4882a593Smuzhiyun 	/*
789*4882a593Smuzhiyun 	 * monoout playback volume
790*4882a593Smuzhiyun 	 */
791*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Monooutp Playback Volume",
792*4882a593Smuzhiyun 		       ES8396_MONOHP_P_BOOST_MUTE_REG48, 3, 1, 1, lineout_tlv),
793*4882a593Smuzhiyun 	SOC_SINGLE_TLV("Monooutn Playback Volume",
794*4882a593Smuzhiyun 		       ES8396_MONOHP_N_BOOST_MUTE_REG49, 3, 1, 1, lineout_tlv),
795*4882a593Smuzhiyun 	SOC_ENUM("ALC Capture Function", alc_func),
796*4882a593Smuzhiyun };
797*4882a593Smuzhiyun 
798*4882a593Smuzhiyun /*
799*4882a593Smuzhiyun  * DAPM Controls
800*4882a593Smuzhiyun  */
801*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_dac_controls =
802*4882a593Smuzhiyun SOC_DAPM_SINGLE("Switch", ES8396_DAC_CSM_REG66, 3, 1, 1);
803*4882a593Smuzhiyun 
804*4882a593Smuzhiyun static const struct snd_kcontrol_new hp_amp_ctl =
805*4882a593Smuzhiyun SOC_DAPM_SINGLE("Switch", ES8396_CP_CLK_DIV_REG0B, 1, 1, 1);
806*4882a593Smuzhiyun 
807*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_hpl_mixer_controls[] = {
808*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LNMUX2HPMIX_L Switch", ES8396_HP_MIXER_REG2A, 6, 1, 0),
809*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AXMUX2HPMIX_L Switch", ES8396_HP_MIXER_REG2A, 5, 1, 0),
810*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("DACL2HPMIX Switch", ES8396_HP_MIXER_REF_LP_REG2D,
811*4882a593Smuzhiyun 			5, 1, 0),
812*4882a593Smuzhiyun };
813*4882a593Smuzhiyun 
814*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_hpr_mixer_controls[] = {
815*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LNMUX2HPMIX_R Switch", ES8396_HP_MIXER_REG2A, 2, 1, 0),
816*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AXMUX2HPMIX_R Switch", ES8396_HP_MIXER_REG2A, 1, 1, 0),
817*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("DACR2HPMIX Switch", ES8396_HP_MIXER_REF_LP_REG2D,
818*4882a593Smuzhiyun 			4, 1, 0),
819*4882a593Smuzhiyun };
820*4882a593Smuzhiyun 
821*4882a593Smuzhiyun /*
822*4882a593Smuzhiyun  * Only used mono out p mixer for differential output
823*4882a593Smuzhiyun  */
824*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_mono_p_mixer_controls[] = {
825*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LHPMIX2MNMIXP Switch", ES8396_MONOHP_P_MIXER_REG47, 7,
826*4882a593Smuzhiyun 			1, 0),
827*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RHPMIX2MNOMIXP Switch", ES8396_MONOHP_P_MIXER_REG47, 6,
828*4882a593Smuzhiyun 			1, 0),
829*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RMNMIX2MNOMIXP Switch", ES8396_MONOHP_P_MIXER_REG47, 5,
830*4882a593Smuzhiyun 			1, 0),
831*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMIX2MNOMIXP Switch",
832*4882a593Smuzhiyun 			ES8396_MONOHP_P_MIXER_REG47, 4, 1, 0),
833*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMIX2MNOMIXP Switch",
834*4882a593Smuzhiyun 			ES8396_MONOHP_P_MIXER_REG47, 3, 1, 0),
835*4882a593Smuzhiyun };
836*4882a593Smuzhiyun 
837*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_mono_n_mixer_controls[] = {
838*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LMNMIX2MNMIXN Switch", ES8396_MONOHP_N_MIXER_REG46, 7,
839*4882a593Smuzhiyun 			1, 0),
840*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RHPMIX2MNOMIXN Switch", ES8396_MONOHP_N_MIXER_REG46, 6,
841*4882a593Smuzhiyun 			1, 0),
842*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MOPINV2MNOMIXN Switch", ES8396_MONOHP_N_MIXER_REG46, 5,
843*4882a593Smuzhiyun 			1, 0),
844*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMIX2MNOMIXN Switch",
845*4882a593Smuzhiyun 			ES8396_MONOHP_N_MIXER_REG46, 4, 1, 0),
846*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LAXMIX2MNOMIXN Switch",
847*4882a593Smuzhiyun 			ES8396_MONOHP_N_MIXER_REG46, 3, 1, 0),
848*4882a593Smuzhiyun };
849*4882a593Smuzhiyun 
850*4882a593Smuzhiyun /*
851*4882a593Smuzhiyun  * define the stereo class d speaker mixer
852*4882a593Smuzhiyun  */
853*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_speaker_lmixer_controls[] = {
854*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMUX2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 6, 1,
855*4882a593Smuzhiyun 			0),
856*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LAXMUX2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 5, 1,
857*4882a593Smuzhiyun 			0),
858*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LDAC2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 7, 1, 0),
859*4882a593Smuzhiyun };
860*4882a593Smuzhiyun 
861*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_speaker_rmixer_controls[] = {
862*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RLNMUX2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 2, 1,
863*4882a593Smuzhiyun 			0),
864*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMUX2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 1, 1,
865*4882a593Smuzhiyun 			0),
866*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RDAC2SPKMIX Switch", ES8396_SPK_MIXER_REG26, 3, 1, 0),
867*4882a593Smuzhiyun };
868*4882a593Smuzhiyun 
869*4882a593Smuzhiyun /*
870*4882a593Smuzhiyun  * Only used line out1 p mixer for differential output
871*4882a593Smuzhiyun  */
872*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_lout1_mixer_controls[] = {
873*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LDAC2LO1MIXP Switch", SND_SOC_NOPM,
874*4882a593Smuzhiyun 			5, 1, 0),
875*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LAXMIX2LO1MIXP Switch",
876*4882a593Smuzhiyun 			ES8396_LNOUT_LO1EN_LO1MIX_REG4A, 4, 1, 0),
877*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMIX2LO1MIXP Switch",
878*4882a593Smuzhiyun 			ES8396_LNOUT_LO1EN_LO1MIX_REG4A, 3, 1, 0),
879*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LMNMIX2LO1MIXP Switch",
880*4882a593Smuzhiyun 			ES8396_LNOUT_LO1EN_LO1MIX_REG4A, 2, 1, 0),
881*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RO1INV2LO1MIXP Switch",
882*4882a593Smuzhiyun 			ES8396_LNOUT_LO1EN_LO1MIX_REG4A, 1, 1, 0),
883*4882a593Smuzhiyun };
884*4882a593Smuzhiyun 
885*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_rout1_mixer_controls[] = {
886*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RDAC2RO1MIXN Switch", SND_SOC_NOPM,
887*4882a593Smuzhiyun 			5, 1, 0),
888*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMIX2RO1MIXN Switch",
889*4882a593Smuzhiyun 			ES8396_LNOUT_RO1EN_RO1MIX_REG4B, 4, 1, 0),
890*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RLNMIX2RO1MIXN Switch",
891*4882a593Smuzhiyun 			ES8396_LNOUT_RO1EN_RO1MIX_REG4B, 3, 1, 0),
892*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RMNMIX2RO1MIXN Switch",
893*4882a593Smuzhiyun 			ES8396_LNOUT_RO1EN_RO1MIX_REG4B, 2, 1, 0),
894*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LO1INV2RO1MIXN Switch",
895*4882a593Smuzhiyun 			ES8396_LNOUT_RO1EN_RO1MIX_REG4B, 1, 1, 0),
896*4882a593Smuzhiyun };
897*4882a593Smuzhiyun 
898*4882a593Smuzhiyun /*
899*4882a593Smuzhiyun  *left LNMIX mixer
900*4882a593Smuzhiyun  */
901*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_lnmix_l_mixer_controls[] = {
902*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AINL2LLNMIX Switch", ES8396_LN_MIXER_REG32, 7, 1, 0),
903*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMUX2LLNMIX Switch", ES8396_LN_MIXER_REG32, 6, 1, 0),
904*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MIC1P2LLNMIX Switch", ES8396_LN_MIXER_REG32, 5, 1, 0),
905*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("PMICDSE2LLNMIX Switch", ES8396_LN_MIXER_REG32, 4, 1, 0),
906*4882a593Smuzhiyun };
907*4882a593Smuzhiyun 
908*4882a593Smuzhiyun /*
909*4882a593Smuzhiyun  *right LNMIX mixer
910*4882a593Smuzhiyun  */
911*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_lnmix_r_mixer_controls[] = {
912*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AINR2RLNMIX Switch", ES8396_LN_MIXER_REG32, 3, 1, 0),
913*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RLNMUX2RLNMIX Switch", ES8396_LN_MIXER_REG32, 2, 1, 0),
914*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MIC1N2LLNMIX Switch", ES8396_LN_MIXER_REG32, 1, 1, 0),
915*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("NMICDSE2RLNMIX Switch", ES8396_LN_MIXER_REG32, 0, 1, 0),
916*4882a593Smuzhiyun };
917*4882a593Smuzhiyun 
918*4882a593Smuzhiyun /*
919*4882a593Smuzhiyun  *left AXMIX mixer
920*4882a593Smuzhiyun  */
921*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_axmix_l_mixer_controls[] = {
922*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LAXMUX2LAXMIX Switch", ES8396_AX_MIXER_REG2E, 7, 1, 0),
923*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MONOP2LAXMIX Switch", ES8396_AX_MIXER_REG2E, 6, 1, 0),
924*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MIC2P2LAXMIX Switch", ES8396_AX_MIXER_REG2E, 5, 1, 0),
925*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("PMICDSE2LAXMIX Switch", ES8396_AX_MIXER_REG2E, 4, 1, 0),
926*4882a593Smuzhiyun };
927*4882a593Smuzhiyun 
928*4882a593Smuzhiyun /*
929*4882a593Smuzhiyun  *right AXMIX mixer
930*4882a593Smuzhiyun  */
931*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_axmix_r_mixer_controls[] = {
932*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMUX2RAXMIX Switch", ES8396_AX_MIXER_REG2E, 3, 1, 0),
933*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MONON2RAXMIX Switch", ES8396_AX_MIXER_REG2E, 2, 1, 0),
934*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MIC2N2RAXMIX Switch", ES8396_AX_MIXER_REG2E, 1, 1, 0),
935*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("NMICDSE2RAXMIX Switch", ES8396_AX_MIXER_REG2E, 0, 1, 0),
936*4882a593Smuzhiyun };
937*4882a593Smuzhiyun 
938*4882a593Smuzhiyun /*
939*4882a593Smuzhiyun  *left MNMIX mixer
940*4882a593Smuzhiyun  */
941*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_mnmix_l_mixer_controls[] = {
942*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LDAC2LMNMIX Switch", ES8396_MN_MIXER_REG36, 7, 1, 0),
943*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MONOP2LMNMIX Switch", ES8396_MN_MIXER_REG36, 6, 1, 0),
944*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AINL2LMNMIX Switch", ES8396_MN_MIXER_REG36, 5, 1, 0),
945*4882a593Smuzhiyun };
946*4882a593Smuzhiyun 
947*4882a593Smuzhiyun /*
948*4882a593Smuzhiyun  *right MNMIX mixer
949*4882a593Smuzhiyun  */
950*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_mnmix_r_mixer_controls[] = {
951*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RDAC2RMNMIX Switch", ES8396_MN_MIXER_REG36, 3, 1, 0),
952*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("MONON2RMNMIX Switch", ES8396_MN_MIXER_REG36, 2, 1, 0),
953*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("AINR2RMNMIX Switch", ES8396_MN_MIXER_REG36, 1, 1, 0),
954*4882a593Smuzhiyun };
955*4882a593Smuzhiyun 
956*4882a593Smuzhiyun /*
957*4882a593Smuzhiyun  * Left Record Mixer
958*4882a593Smuzhiyun  */
959*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_capture_l_mixer_controls[] = {
960*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RLNMIX2LPGA Switch", ES8396_ADC_LPGA_MIXER_REG62, 7, 1, 0),
961*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMIX2LPGA Switch", ES8396_ADC_LPGA_MIXER_REG62, 6, 1, 0),
962*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RMNMIX2LPGA Switch", ES8396_ADC_LPGA_MIXER_REG62, 5, 1, 0),
963*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LMNMIX2LPGA Switch", ES8396_ADC_LPGA_MIXER_REG62, 4, 1, 0),
964*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LLNMIX2LPGA Switch", ES8396_ADC_LPGA_MIXER_REG62, 3, 1, 0),
965*4882a593Smuzhiyun 
966*4882a593Smuzhiyun };
967*4882a593Smuzhiyun 
968*4882a593Smuzhiyun /*
969*4882a593Smuzhiyun  * Right Record Mixer
970*4882a593Smuzhiyun  */
971*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_capture_r_mixer_controls[] = {
972*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RLNMIX2RPGA Switch", ES8396_ADC_RPGA_MIXER_REG63, 7, 1, 0),
973*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RAXMIX2RPGA Switch", ES8396_ADC_RPGA_MIXER_REG63, 6, 1, 0),
974*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("RMNMIX2RPGA Switch", ES8396_ADC_RPGA_MIXER_REG63, 5, 1, 0),
975*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LMNMIX2RPGA Switch", ES8396_ADC_RPGA_MIXER_REG63, 4, 1, 0),
976*4882a593Smuzhiyun 	SOC_DAPM_SINGLE("LAXMIX2RPGA Switch", ES8396_ADC_RPGA_MIXER_REG63, 3, 1, 0),
977*4882a593Smuzhiyun };
978*4882a593Smuzhiyun 
979*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_adc_controls =
980*4882a593Smuzhiyun SOC_DAPM_SINGLE("Switch", ES8396_ADC_CSM_REG53, 6, 1, 1);
981*4882a593Smuzhiyun 
982*4882a593Smuzhiyun /*
983*4882a593Smuzhiyun  * MIC INPUT MUX
984*4882a593Smuzhiyun  */
985*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_micin_mux_controls =
986*4882a593Smuzhiyun SOC_DAPM_SINGLE("Switch", ES8396_SYS_MIC_IBIAS_EN_REG75, 1, 1, 0);
987*4882a593Smuzhiyun 
988*4882a593Smuzhiyun /*
989*4882a593Smuzhiyun  * left LN MUX
990*4882a593Smuzhiyun  */
991*4882a593Smuzhiyun static const char *const es8396_left_lnmux_txt[] = {
992*4882a593Smuzhiyun 	"NO IN",
993*4882a593Smuzhiyun 	"RPGAP",
994*4882a593Smuzhiyun 	"LPGAP",
995*4882a593Smuzhiyun 	"MONOP",
996*4882a593Smuzhiyun 	"AINL"
997*4882a593Smuzhiyun };
998*4882a593Smuzhiyun 
999*4882a593Smuzhiyun static const unsigned int es8396_left_lnmux_values[] = {
1000*4882a593Smuzhiyun 	0, 1, 2, 4, 8
1001*4882a593Smuzhiyun };
1002*4882a593Smuzhiyun 
1003*4882a593Smuzhiyun static const struct soc_enum es8396_left_lnmux_enum =
1004*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_ADC_LN_MUX_REG64, 0, 15,
1005*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_lnmux_txt),
1006*4882a593Smuzhiyun 		      es8396_left_lnmux_txt,
1007*4882a593Smuzhiyun 		      es8396_left_lnmux_values);
1008*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_left_lnmux_controls =
1009*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_left_lnmux_enum);
1010*4882a593Smuzhiyun 
1011*4882a593Smuzhiyun /*
1012*4882a593Smuzhiyun  * Right LN MUX
1013*4882a593Smuzhiyun  */
1014*4882a593Smuzhiyun static const char *const es8396_right_lnmux_txt[] = {
1015*4882a593Smuzhiyun 	"NO IN",
1016*4882a593Smuzhiyun 	"RPGAP",
1017*4882a593Smuzhiyun 	"LPGAP",
1018*4882a593Smuzhiyun 	"MONON",
1019*4882a593Smuzhiyun 	"AINR"
1020*4882a593Smuzhiyun };
1021*4882a593Smuzhiyun 
1022*4882a593Smuzhiyun static const struct soc_enum es8396_right_lnmux_enum =
1023*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_ADC_LN_MUX_REG64, 4, 15,
1024*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_right_lnmux_txt),
1025*4882a593Smuzhiyun 		      es8396_right_lnmux_txt,
1026*4882a593Smuzhiyun 		      es8396_left_lnmux_values);
1027*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_right_lnmux_controls =
1028*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_right_lnmux_enum);
1029*4882a593Smuzhiyun 
1030*4882a593Smuzhiyun /*
1031*4882a593Smuzhiyun  * left AX MUX
1032*4882a593Smuzhiyun  */
1033*4882a593Smuzhiyun static const struct soc_enum es8396_left_axmux_enum =
1034*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_ADC_AX_MUX_REG65, 0, 15,
1035*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_lnmux_txt),
1036*4882a593Smuzhiyun 		      es8396_left_lnmux_txt,
1037*4882a593Smuzhiyun 		      es8396_left_lnmux_values);
1038*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_left_axmux_controls =
1039*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_left_axmux_enum);
1040*4882a593Smuzhiyun 
1041*4882a593Smuzhiyun /*
1042*4882a593Smuzhiyun  * Right AX MUX
1043*4882a593Smuzhiyun  */
1044*4882a593Smuzhiyun static const struct soc_enum es8396_right_axmux_enum =
1045*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_ADC_AX_MUX_REG65, 4, 15,
1046*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_right_lnmux_txt),
1047*4882a593Smuzhiyun 		      es8396_right_lnmux_txt,
1048*4882a593Smuzhiyun 		      es8396_left_lnmux_values);
1049*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_right_axmux_controls =
1050*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_right_axmux_enum);
1051*4882a593Smuzhiyun 
1052*4882a593Smuzhiyun /*
1053*4882a593Smuzhiyun  * Left SPKOUT MUX
1054*4882a593Smuzhiyun  */
1055*4882a593Smuzhiyun static const char *const es8396_left_spkout_mux_txt[] = {
1056*4882a593Smuzhiyun 	"NO Out",
1057*4882a593Smuzhiyun 	"SPKR Route",
1058*4882a593Smuzhiyun 	"SPKL Route"
1059*4882a593Smuzhiyun };
1060*4882a593Smuzhiyun 
1061*4882a593Smuzhiyun static const unsigned int es8396_left_spkout_mux_values[] = {
1062*4882a593Smuzhiyun 	0, 1, 2
1063*4882a593Smuzhiyun };
1064*4882a593Smuzhiyun 
1065*4882a593Smuzhiyun static const struct soc_enum es8396_left_spkout_mux_enum =
1066*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_SPK_CTRL_SRC_REG3A, 4, 3,
1067*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_spkout_mux_txt),
1068*4882a593Smuzhiyun 		      es8396_left_spkout_mux_txt,
1069*4882a593Smuzhiyun 		      es8396_left_spkout_mux_values);
1070*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_left_spkout_mux_controls =
1071*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_left_spkout_mux_enum);
1072*4882a593Smuzhiyun 
1073*4882a593Smuzhiyun /*
1074*4882a593Smuzhiyun  * Right SPKOUT MUX
1075*4882a593Smuzhiyun  */
1076*4882a593Smuzhiyun static const struct soc_enum es8396_right_spkout_mux_enum =
1077*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_SPK_CTRL_SRC_REG3A, 0, 3,
1078*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_spkout_mux_txt),
1079*4882a593Smuzhiyun 		      es8396_left_spkout_mux_txt,
1080*4882a593Smuzhiyun 		      es8396_left_spkout_mux_values);
1081*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_right_spkout_mux_controls =
1082*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_right_spkout_mux_enum);
1083*4882a593Smuzhiyun 
1084*4882a593Smuzhiyun /*
1085*4882a593Smuzhiyun  * SPKLDO POWER SWITCH
1086*4882a593Smuzhiyun  */
1087*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_spkldo_pwrswitch_controls =
1088*4882a593Smuzhiyun SOC_DAPM_SINGLE("Switch", ES8396_DAMP_CLK_DIV_REG0C, 1, 1, 1);
1089*4882a593Smuzhiyun 
1090*4882a593Smuzhiyun /*
1091*4882a593Smuzhiyun  * Dmic MUX
1092*4882a593Smuzhiyun  */
1093*4882a593Smuzhiyun static const char *const es8396_dmic_mux_txt[] = {
1094*4882a593Smuzhiyun 	/* 0  can be used for stereo amic */
1095*4882a593Smuzhiyun 	"dmic disable,use adc",
1096*4882a593Smuzhiyun 	"ldata use ladc,rdata use ldmic at low clk",
1097*4882a593Smuzhiyun 	"ldata use ladc,rdata use rdmic at low clk",
1098*4882a593Smuzhiyun 	"ldata use ladc,rdata use rdmic at high clk",
1099*4882a593Smuzhiyun 	"ldata use ldmic at high clk,rdata use radc",
1100*4882a593Smuzhiyun 	"ldata use ldmic at high clk,rdata use ldmic at low clk",
1101*4882a593Smuzhiyun 	/* can be used for stereo dmic */
1102*4882a593Smuzhiyun 	"ldata use ldmic at high clk,rdata use rdmic at low clk",
1103*4882a593Smuzhiyun 	"ldata use ldmic at high clk,rdata use rdmic at high clk",
1104*4882a593Smuzhiyun 	"ldata use rdmic at high clk,rdata use radc",
1105*4882a593Smuzhiyun 	/* can be used for stereo dmic */
1106*4882a593Smuzhiyun 	"ldata use rdmic at high clk,rdata use ldmic at low clk",
1107*4882a593Smuzhiyun 	"ldata use rdmic at high clk,rdata use rdmic at low clk",
1108*4882a593Smuzhiyun 	"ldata use rdmic at high clk,rdata use rdmic at high clk",
1109*4882a593Smuzhiyun 	"ldata use ldmic at low clk,rdata use radc",
1110*4882a593Smuzhiyun 	"ldata use ldmic at low clk,rdata use ldmic at low clk",
1111*4882a593Smuzhiyun 	"ldata use ldmic at low clk,rdata use rdmic at low clk",
1112*4882a593Smuzhiyun 	/* can be used for stereo dmic */
1113*4882a593Smuzhiyun 	"ldata use ldmic at low clk,rdata use rdmic at high clk",
1114*4882a593Smuzhiyun };
1115*4882a593Smuzhiyun 
1116*4882a593Smuzhiyun static const unsigned int es8396_dmic_mux_values[] = {
1117*4882a593Smuzhiyun 	0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15
1118*4882a593Smuzhiyun };
1119*4882a593Smuzhiyun 
1120*4882a593Smuzhiyun static const struct soc_enum es8396_dmic_mux_enum =
1121*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_ADC_DMIC_RAMPRATE_REG54, 4, 15,
1122*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_dmic_mux_txt),
1123*4882a593Smuzhiyun 		      es8396_dmic_mux_txt,
1124*4882a593Smuzhiyun 		      es8396_dmic_mux_values);
1125*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_dmic_mux_controls =
1126*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_dmic_mux_enum);
1127*4882a593Smuzhiyun 
1128*4882a593Smuzhiyun /*
1129*4882a593Smuzhiyun  * Digital mixer1 left
1130*4882a593Smuzhiyun  */
1131*4882a593Smuzhiyun static const char *const es8396_left_digital_mixer_txt[] = {
1132*4882a593Smuzhiyun 	"left SDP1 in",
1133*4882a593Smuzhiyun 	"left SDP2 in",
1134*4882a593Smuzhiyun 	"left SDP3 in",
1135*4882a593Smuzhiyun 	"left ADC out",
1136*4882a593Smuzhiyun 	"right SDP1 in",
1137*4882a593Smuzhiyun 	"right SDP2 in",
1138*4882a593Smuzhiyun 	"right SDP3 in",
1139*4882a593Smuzhiyun 	"right ADC out"
1140*4882a593Smuzhiyun };
1141*4882a593Smuzhiyun 
1142*4882a593Smuzhiyun static const unsigned int es8396_left_digital_mixer_values[] = {
1143*4882a593Smuzhiyun 	0, 1, 2, 3, 4, 5, 6, 7
1144*4882a593Smuzhiyun };
1145*4882a593Smuzhiyun 
1146*4882a593Smuzhiyun static const struct soc_enum es8396_left_digital_mixer_enum =
1147*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DMIX_SRC_1_REG18, 4, 15,
1148*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_digital_mixer_txt),
1149*4882a593Smuzhiyun 		      es8396_left_digital_mixer_txt,
1150*4882a593Smuzhiyun 		      es8396_left_digital_mixer_values);
1151*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_left_digital_mixer_controls =
1152*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_left_digital_mixer_enum);
1153*4882a593Smuzhiyun 
1154*4882a593Smuzhiyun /*
1155*4882a593Smuzhiyun  * Digital mixer1 right
1156*4882a593Smuzhiyun  */
1157*4882a593Smuzhiyun static const char *const es8396_right_digital_mixer_txt[] = {
1158*4882a593Smuzhiyun 	"right SDP1 in",
1159*4882a593Smuzhiyun 	"right SDP2 in",
1160*4882a593Smuzhiyun 	"right SDP3 in",
1161*4882a593Smuzhiyun 	"right ADC out",
1162*4882a593Smuzhiyun 	"left SDP1 in",
1163*4882a593Smuzhiyun 	"left SDP2 in",
1164*4882a593Smuzhiyun 	"left SDP3 in",
1165*4882a593Smuzhiyun 	"left ADC out"
1166*4882a593Smuzhiyun };
1167*4882a593Smuzhiyun 
1168*4882a593Smuzhiyun static const struct soc_enum es8396_right_digital_mixer_enum =
1169*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DMIX_SRC_1_REG18, 0, 15,
1170*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_right_digital_mixer_txt),
1171*4882a593Smuzhiyun 		      es8396_right_digital_mixer_txt,
1172*4882a593Smuzhiyun 		      es8396_left_digital_mixer_values);
1173*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_right_digital_mixer_controls =
1174*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_right_digital_mixer_enum);
1175*4882a593Smuzhiyun 
1176*4882a593Smuzhiyun /*
1177*4882a593Smuzhiyun  * Digital mixer2 left
1178*4882a593Smuzhiyun  */
1179*4882a593Smuzhiyun static const struct soc_enum es8396_left_digital2_mixer_enum =
1180*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DMIX_SRC_2_REG19, 4, 15,
1181*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_left_digital_mixer_txt),
1182*4882a593Smuzhiyun 		      es8396_left_digital_mixer_txt,
1183*4882a593Smuzhiyun 		      es8396_left_digital_mixer_values);
1184*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_left_digital2_mixer_controls =
1185*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_left_digital2_mixer_enum);
1186*4882a593Smuzhiyun 
1187*4882a593Smuzhiyun /*
1188*4882a593Smuzhiyun  * Digital mixer2 right
1189*4882a593Smuzhiyun  */
1190*4882a593Smuzhiyun static const struct soc_enum es8396_right_digital2_mixer_enum =
1191*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DMIX_SRC_2_REG19, 0, 15,
1192*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_right_digital_mixer_txt),
1193*4882a593Smuzhiyun 		      es8396_right_digital_mixer_txt,
1194*4882a593Smuzhiyun 		      es8396_left_digital_mixer_values);
1195*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_right_digital2_mixer_controls =
1196*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_right_digital2_mixer_enum);
1197*4882a593Smuzhiyun 
1198*4882a593Smuzhiyun /*
1199*4882a593Smuzhiyun  * equalizer clk mux
1200*4882a593Smuzhiyun  */
1201*4882a593Smuzhiyun static const char *const es8396_eq_clk_mux_txt[] = {
1202*4882a593Smuzhiyun 	"from dac mclk",
1203*4882a593Smuzhiyun 	"from adc mclk",
1204*4882a593Smuzhiyun 	"from clk1",
1205*4882a593Smuzhiyun 	"from clk2"
1206*4882a593Smuzhiyun };
1207*4882a593Smuzhiyun 
1208*4882a593Smuzhiyun static const unsigned int es8396_eq_clk_mux_values[] = {
1209*4882a593Smuzhiyun 	0, 1, 2, 3
1210*4882a593Smuzhiyun };
1211*4882a593Smuzhiyun 
1212*4882a593Smuzhiyun static const struct soc_enum es8396_eq_clk_mux_enum =
1213*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_EQ_CLK_OSR_SEL_REG1C, 4, 3,
1214*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_eq_clk_mux_txt),
1215*4882a593Smuzhiyun 		      es8396_eq_clk_mux_txt,
1216*4882a593Smuzhiyun 		      es8396_eq_clk_mux_values);
1217*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_eq_clk_mux_controls =
1218*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_eq_clk_mux_enum);
1219*4882a593Smuzhiyun 
1220*4882a593Smuzhiyun /*
1221*4882a593Smuzhiyun  * equalizer osr mux
1222*4882a593Smuzhiyun  */
1223*4882a593Smuzhiyun static const char *const es8396_eq_osr_mux_txt[] = {
1224*4882a593Smuzhiyun 	"1FS OSR",
1225*4882a593Smuzhiyun 	"2FS OSR",
1226*4882a593Smuzhiyun 	"3FS OSR",
1227*4882a593Smuzhiyun 	"4FS OSR",
1228*4882a593Smuzhiyun 	"5FS OSR",
1229*4882a593Smuzhiyun 	"6FS OSR"
1230*4882a593Smuzhiyun };
1231*4882a593Smuzhiyun 
1232*4882a593Smuzhiyun static const unsigned int es8396_eq_osr_mux_values[] = {
1233*4882a593Smuzhiyun 	0, 1, 2, 3, 4, 5
1234*4882a593Smuzhiyun };
1235*4882a593Smuzhiyun 
1236*4882a593Smuzhiyun static const struct soc_enum es8396_eq_osr_mux_enum =
1237*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_EQ_CLK_OSR_SEL_REG1C, 0, 7,
1238*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_eq_osr_mux_txt),
1239*4882a593Smuzhiyun 		      es8396_eq_osr_mux_txt,
1240*4882a593Smuzhiyun 		      es8396_eq_osr_mux_values);
1241*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_eq_osr_mux_controls =
1242*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_eq_osr_mux_enum);
1243*4882a593Smuzhiyun 
1244*4882a593Smuzhiyun /*
1245*4882a593Smuzhiyun  * DAC source mux
1246*4882a593Smuzhiyun  */
1247*4882a593Smuzhiyun static const char *const es8396_dac_src_mux_txt[] = {
1248*4882a593Smuzhiyun 	"SDP1 in",
1249*4882a593Smuzhiyun 	"SDP2 in",
1250*4882a593Smuzhiyun 	"SDP3 in",
1251*4882a593Smuzhiyun 	"ADC out",
1252*4882a593Smuzhiyun 	"EQ stereo",
1253*4882a593Smuzhiyun 	"EQ left",
1254*4882a593Smuzhiyun 	"EQ right",
1255*4882a593Smuzhiyun };
1256*4882a593Smuzhiyun 
1257*4882a593Smuzhiyun static const unsigned int es8396_dac_src_mux_values[] = {
1258*4882a593Smuzhiyun 	0, 1, 2, 3, 4, 5, 6
1259*4882a593Smuzhiyun };
1260*4882a593Smuzhiyun 
1261*4882a593Smuzhiyun static const struct soc_enum es8396_dac_src_mux_enum =
1262*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DAC_SRC_SDP1O_SRC_REG1A, 4, 7,
1263*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_dac_src_mux_txt),
1264*4882a593Smuzhiyun 		      es8396_dac_src_mux_txt,
1265*4882a593Smuzhiyun 		      es8396_dac_src_mux_values);
1266*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_dac_src_mux_controls =
1267*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_dac_src_mux_enum);
1268*4882a593Smuzhiyun 
1269*4882a593Smuzhiyun /*
1270*4882a593Smuzhiyun  * I2S1 out mux
1271*4882a593Smuzhiyun  */
1272*4882a593Smuzhiyun static const char *const es8396_i2s1_out_mux_txt[] = {
1273*4882a593Smuzhiyun 	"ADC out",
1274*4882a593Smuzhiyun 	"SDP1 in",
1275*4882a593Smuzhiyun 	"SDP2 in",
1276*4882a593Smuzhiyun 	"SDP3 in",
1277*4882a593Smuzhiyun 	"EQ stereo",
1278*4882a593Smuzhiyun 	"EQ left",
1279*4882a593Smuzhiyun 	"EQ right",
1280*4882a593Smuzhiyun };
1281*4882a593Smuzhiyun 
1282*4882a593Smuzhiyun static const unsigned int es8396_i2s1_out_mux_values[] = {
1283*4882a593Smuzhiyun 	0, 1, 2, 3, 4, 5, 6
1284*4882a593Smuzhiyun };
1285*4882a593Smuzhiyun 
1286*4882a593Smuzhiyun static const struct soc_enum es8396_i2s1_out_mux_enum =
1287*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_DAC_SRC_SDP1O_SRC_REG1A, 0, 7,
1288*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_i2s1_out_mux_txt),
1289*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_txt,
1290*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_values);
1291*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_i2s1_out_mux_controls =
1292*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_i2s1_out_mux_enum);
1293*4882a593Smuzhiyun 
1294*4882a593Smuzhiyun /*
1295*4882a593Smuzhiyun  * I2S2 out mux
1296*4882a593Smuzhiyun  */
1297*4882a593Smuzhiyun static const struct soc_enum es8396_i2s2_out_mux_enum =
1298*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_SDP2O_SDP3O_SRC_REG1B, 4, 7,
1299*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_i2s1_out_mux_txt),
1300*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_txt,
1301*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_values);
1302*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_i2s2_out_mux_controls =
1303*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_i2s2_out_mux_enum);
1304*4882a593Smuzhiyun 
1305*4882a593Smuzhiyun /*
1306*4882a593Smuzhiyun  * I2S3 out mux
1307*4882a593Smuzhiyun  */
1308*4882a593Smuzhiyun static const struct soc_enum es8396_i2s3_out_mux_enum =
1309*4882a593Smuzhiyun SOC_VALUE_ENUM_SINGLE(ES8396_SDP2O_SDP3O_SRC_REG1B, 0, 7,
1310*4882a593Smuzhiyun 		      ARRAY_SIZE(es8396_i2s1_out_mux_txt),
1311*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_txt,
1312*4882a593Smuzhiyun 		      es8396_i2s1_out_mux_values);
1313*4882a593Smuzhiyun static const struct snd_kcontrol_new es8396_i2s3_out_mux_controls =
1314*4882a593Smuzhiyun SOC_DAPM_ENUM("Route", es8396_i2s3_out_mux_enum);
1315*4882a593Smuzhiyun 
1316*4882a593Smuzhiyun static const struct snd_soc_dapm_widget es8396_dapm_widgets[] = {
1317*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("DMIC"),
1318*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("LINP"),
1319*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("RINN"),
1320*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("MONOINP"),
1321*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("MONOINN"),
1322*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("AINL"),
1323*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("AINR"),
1324*4882a593Smuzhiyun 	SND_SOC_DAPM_INPUT("MIC"),
1325*4882a593Smuzhiyun 	SND_SOC_DAPM_SUPPLY("MIC Bias", SND_SOC_NOPM, 0, 0,
1326*4882a593Smuzhiyun 			    micbias_event,
1327*4882a593Smuzhiyun 			    SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
1328*4882a593Smuzhiyun 	/*
1329*4882a593Smuzhiyun 	 * AIF OUT AND MUX
1330*4882a593Smuzhiyun 	 */
1331*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("VOICESDPOL", "SDP1 Capture", 0,
1332*4882a593Smuzhiyun 			     ES8396_SDP1_OUT_FMT_REG20, 6, 1),
1333*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("VOICESDPOR", "SDP1 Capture", 0,
1334*4882a593Smuzhiyun 			     ES8396_SDP1_OUT_FMT_REG20, 6, 1),
1335*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("VOICESDPO Mux", SND_SOC_NOPM, 0, 0, &es8396_i2s1_out_mux_controls),
1336*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("MASTERSDPOL", "SDP2 Capture", 0,
1337*4882a593Smuzhiyun 			     ES8396_SDP2_OUT_FMT_REG23, 6, 1),
1338*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("MASTERSDPOR", "SDP2 Capture", 0,
1339*4882a593Smuzhiyun 			     ES8396_SDP2_OUT_FMT_REG23, 6, 1),
1340*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("MASTERSDPO Mux", SND_SOC_NOPM, 0, 0,
1341*4882a593Smuzhiyun 			 &es8396_i2s2_out_mux_controls),
1342*4882a593Smuzhiyun 
1343*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("AUXSDPOL", "SDP3 Capture", 0,
1344*4882a593Smuzhiyun 			     ES8396_SDP3_OUT_FMT_REG25, 6, 1),
1345*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_OUT("AUXSDPOR", "SDP3 Capture", 0,
1346*4882a593Smuzhiyun 			     ES8396_SDP3_OUT_FMT_REG25, 6, 1),
1347*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("AUXSDPO Mux", SND_SOC_NOPM, 0, 0,
1348*4882a593Smuzhiyun 			 &es8396_i2s3_out_mux_controls),
1349*4882a593Smuzhiyun 
1350*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("VOICEOUT AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1351*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("MASTEROUT AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1352*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("AUXOUT AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1353*4882a593Smuzhiyun 
1354*4882a593Smuzhiyun 	/* capature  */
1355*4882a593Smuzhiyun 
1356*4882a593Smuzhiyun 	/*
1357*4882a593Smuzhiyun 	 *left and right mixer
1358*4882a593Smuzhiyun 	 */
1359*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER_NAMED_CTL("PGA Left Mix", SND_SOC_NOPM, 0, 0,
1360*4882a593Smuzhiyun 				     &es8396_capture_l_mixer_controls[0],
1361*4882a593Smuzhiyun 				     ARRAY_SIZE
1362*4882a593Smuzhiyun 				     (es8396_capture_l_mixer_controls)),
1363*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER_NAMED_CTL("PGA Right Mix", SND_SOC_NOPM, 0, 0,
1364*4882a593Smuzhiyun 				     &es8396_capture_r_mixer_controls[0],
1365*4882a593Smuzhiyun 				     ARRAY_SIZE
1366*4882a593Smuzhiyun 				     (es8396_capture_r_mixer_controls)),
1367*4882a593Smuzhiyun 
1368*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("LPGA P", ES8396_ADC_ANALOG_CTRL_REG5E, 4, 1, NULL, 0),
1369*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("RPGA P", ES8396_ADC_ANALOG_CTRL_REG5E, 5, 1, NULL, 0),
1370*4882a593Smuzhiyun 
1371*4882a593Smuzhiyun 	SND_SOC_DAPM_ADC("ADC Left", NULL, ES8396_ADC_ANALOG_CTRL_REG5E, 2, 1),
1372*4882a593Smuzhiyun 	SND_SOC_DAPM_ADC("ADC Right", NULL, ES8396_ADC_ANALOG_CTRL_REG5E, 3, 1),
1373*4882a593Smuzhiyun 	SND_SOC_DAPM_SWITCH_E("ADC_1", SND_SOC_NOPM, 0, 0,
1374*4882a593Smuzhiyun 			      &es8396_adc_controls, adc_event,
1375*4882a593Smuzhiyun 			      SND_SOC_DAPM_PRE_PMD),
1376*4882a593Smuzhiyun 
1377*4882a593Smuzhiyun 	/*
1378*4882a593Smuzhiyun 	 * Analog MIC Muxes
1379*4882a593Smuzhiyun 	 */
1380*4882a593Smuzhiyun 	SND_SOC_DAPM_SWITCH("AMIC Mux", ES8396_SYS_MIC_IBIAS_EN_REG75, 0, 1,
1381*4882a593Smuzhiyun 			    &es8396_micin_mux_controls),
1382*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("MIC BOOST", SND_SOC_NOPM, 0, 0, NULL, 0),
1383*4882a593Smuzhiyun 
1384*4882a593Smuzhiyun 	/* LN,AX Muxes */
1385*4882a593Smuzhiyun 	/*
1386*4882a593Smuzhiyun 	 * LN MUX
1387*4882a593Smuzhiyun 	 */
1388*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("LLN Mux", SND_SOC_NOPM, 0, 0,
1389*4882a593Smuzhiyun 			 &es8396_left_lnmux_controls),
1390*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("RLN Mux", SND_SOC_NOPM, 0, 0,
1391*4882a593Smuzhiyun 			 &es8396_right_lnmux_controls),
1392*4882a593Smuzhiyun 	/*
1393*4882a593Smuzhiyun 	 * AX MUX
1394*4882a593Smuzhiyun 	 */
1395*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("LAX Mux", SND_SOC_NOPM, 0, 0,
1396*4882a593Smuzhiyun 			 &es8396_left_axmux_controls),
1397*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("RAX Mux", SND_SOC_NOPM, 0, 0,
1398*4882a593Smuzhiyun 			 &es8396_right_axmux_controls),
1399*4882a593Smuzhiyun 	/*
1400*4882a593Smuzhiyun 	 * AIF IN
1401*4882a593Smuzhiyun 	 */
1402*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("VOICESDPIL", "SDP1 Playback", 0,
1403*4882a593Smuzhiyun 			    ES8396_SDP1_IN_FMT_REG1F, 6, 1),
1404*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("VOICESDPIR", "SDP1 Playback", 0,
1405*4882a593Smuzhiyun 			    ES8396_SDP1_IN_FMT_REG1F, 6, 1),
1406*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("MASTERSDPIL", "SDP2 Playback", 0,
1407*4882a593Smuzhiyun 			    SND_SOC_NOPM, 6, 1),
1408*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("MASTERSDPIR", "SDP2 Playback", 0,
1409*4882a593Smuzhiyun 			    SND_SOC_NOPM, 6, 1),
1410*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("AUXSDPIL", "SDP3 Playback", 0,
1411*4882a593Smuzhiyun 			    ES8396_SDP3_IN_FMT_REG24, 6, 1),
1412*4882a593Smuzhiyun 	SND_SOC_DAPM_AIF_IN("AUXSDPIR", "SDP3 Playback", 0,
1413*4882a593Smuzhiyun 			    ES8396_SDP3_IN_FMT_REG24, 6, 1),
1414*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("VOICEIN AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1415*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("MASTERIN AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1416*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("AUXIN AIF Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1417*4882a593Smuzhiyun 	/*
1418*4882a593Smuzhiyun 	 * Digital mixer1,2
1419*4882a593Smuzhiyun 	 */
1420*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("LDMIX1 Mux", SND_SOC_NOPM, 0, 0,
1421*4882a593Smuzhiyun 			 &es8396_left_digital_mixer_controls),
1422*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("RDMIX1 Mux", SND_SOC_NOPM, 0, 0,
1423*4882a593Smuzhiyun 			 &es8396_right_digital_mixer_controls),
1424*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("LDMIX2 Mux", SND_SOC_NOPM, 0, 0,
1425*4882a593Smuzhiyun 			 &es8396_left_digital2_mixer_controls),
1426*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("RDMIX2 Mux", SND_SOC_NOPM, 0, 0,
1427*4882a593Smuzhiyun 			 &es8396_right_digital2_mixer_controls),
1428*4882a593Smuzhiyun 
1429*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("Digital Left Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1430*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("Digital Right Mixer", SND_SOC_NOPM, 0, 0, NULL, 0),
1431*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("Equalizer", SND_SOC_NOPM, 0, 0, NULL, 0),
1432*4882a593Smuzhiyun 
1433*4882a593Smuzhiyun 	SND_SOC_DAPM_MUX("DACSRC Mux", SND_SOC_NOPM, 0, 0,
1434*4882a593Smuzhiyun 			 &es8396_dac_src_mux_controls),
1435*4882a593Smuzhiyun 	/*
1436*4882a593Smuzhiyun 	 * DAC
1437*4882a593Smuzhiyun 	 */
1438*4882a593Smuzhiyun 	SND_SOC_DAPM_SWITCH("DAC_1", SND_SOC_NOPM, 0, 0,
1439*4882a593Smuzhiyun 			    &es8396_dac_controls),
1440*4882a593Smuzhiyun 
1441*4882a593Smuzhiyun 	SND_SOC_DAPM_DAC("Left DAC", NULL, SND_SOC_NOPM, 0, 0),
1442*4882a593Smuzhiyun 	SND_SOC_DAPM_DAC("Right DAC", NULL, SND_SOC_NOPM, 0, 0),
1443*4882a593Smuzhiyun 
1444*4882a593Smuzhiyun 	/*
1445*4882a593Smuzhiyun 	 * mixerMono
1446*4882a593Smuzhiyun 	 */
1447*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("LMONIN Mix", ES8396_MN_MIXER_BOOST_REG37, 4, 1,
1448*4882a593Smuzhiyun 			   &es8396_mnmix_l_mixer_controls[0],
1449*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_mnmix_l_mixer_controls)),
1450*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("LMONINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1451*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("RMONIN Mix", ES8396_MN_MIXER_BOOST_REG37, 0, 1,
1452*4882a593Smuzhiyun 			   &es8396_mnmix_r_mixer_controls[0],
1453*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_mnmix_r_mixer_controls)),
1454*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("RMONINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1455*4882a593Smuzhiyun 	/*
1456*4882a593Smuzhiyun 	 * mixerLN
1457*4882a593Smuzhiyun 	 */
1458*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("LLNIN Mix", ES8396_LN_MIXER_BOOST_REG33, 4, 1,
1459*4882a593Smuzhiyun 			   &es8396_lnmix_l_mixer_controls[0],
1460*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_lnmix_l_mixer_controls)),
1461*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("LLNINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1462*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("RLNIN Mix", ES8396_LN_MIXER_BOOST_REG33, 0, 1,
1463*4882a593Smuzhiyun 			   &es8396_lnmix_r_mixer_controls[0],
1464*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_lnmix_r_mixer_controls)),
1465*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("RLNINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1466*4882a593Smuzhiyun 	/*
1467*4882a593Smuzhiyun 	 * mixerAX
1468*4882a593Smuzhiyun 	 */
1469*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("LAXIN Mix", ES8396_AX_MIXER_BOOST_REG2F, 4, 1,
1470*4882a593Smuzhiyun 			   &es8396_axmix_l_mixer_controls[0],
1471*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_axmix_l_mixer_controls)),
1472*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("LAXINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1473*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("RAXIN Mix", ES8396_AX_MIXER_BOOST_REG2F, 0, 1,
1474*4882a593Smuzhiyun 			   &es8396_axmix_r_mixer_controls[0],
1475*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_axmix_r_mixer_controls)),
1476*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("RAXINMIX PGA", SND_SOC_NOPM, 0, 0, NULL, 0),
1477*4882a593Smuzhiyun 	/*
1478*4882a593Smuzhiyun 	 * mixerLNOUT
1479*4882a593Smuzhiyun 	 */
1480*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("LOUT1 Mix", SND_SOC_NOPM, 0, 0,
1481*4882a593Smuzhiyun 			   &es8396_lout1_mixer_controls[0],
1482*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_lout1_mixer_controls)),
1483*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("LNOUTMIX1 PGA", SND_SOC_NOPM, 6, 0,
1484*4882a593Smuzhiyun 			 NULL, 0),
1485*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("ROUT1 Mix", SND_SOC_NOPM, 0, 0,
1486*4882a593Smuzhiyun 			   &es8396_rout1_mixer_controls[0],
1487*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_rout1_mixer_controls)),
1488*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("RNOUTMIX1 PGA", SND_SOC_NOPM, 6, 0,
1489*4882a593Smuzhiyun 			 NULL, 0),
1490*4882a593Smuzhiyun 
1491*4882a593Smuzhiyun 	/*
1492*4882a593Smuzhiyun 	 * mixerMNOUT
1493*4882a593Smuzhiyun 	 */
1494*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("MNOUTP Mix", SND_SOC_NOPM, 0, 0,
1495*4882a593Smuzhiyun 			   &es8396_mono_p_mixer_controls[0],
1496*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_mono_p_mixer_controls)),
1497*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("MNOUTP PGA", ES8396_MONOHP_P_BOOST_MUTE_REG48, 7, 0,
1498*4882a593Smuzhiyun 			 NULL, 0),
1499*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("MNOUTN Mix", SND_SOC_NOPM, 0, 0,
1500*4882a593Smuzhiyun 			   &es8396_mono_n_mixer_controls[0],
1501*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_mono_n_mixer_controls)),
1502*4882a593Smuzhiyun 	SND_SOC_DAPM_PGA("MNOUTN PGA", ES8396_MONOHP_N_BOOST_MUTE_REG49, 7, 0,
1503*4882a593Smuzhiyun 			 NULL, 0),
1504*4882a593Smuzhiyun 
1505*4882a593Smuzhiyun 	/*
1506*4882a593Smuzhiyun 	 * mixerHP
1507*4882a593Smuzhiyun 	 */
1508*4882a593Smuzhiyun 	/*
1509*4882a593Smuzhiyun 	 * SND_SOC_DAPM_MIXER("HPL Mix", ES8396_HP_MIXER_BOOST_REG2B, 4, 1,
1510*4882a593Smuzhiyun 	 */
1511*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("HPL Mix", SND_SOC_NOPM, 6, 0,
1512*4882a593Smuzhiyun 			   &es8396_hpl_mixer_controls[0],
1513*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_hpl_mixer_controls)),
1514*4882a593Smuzhiyun 	/*
1515*4882a593Smuzhiyun 	 * SND_SOC_DAPM_MIXER("HPR Mix", ES8396_HP_MIXER_BOOST_REG2B, 0, 1,
1516*4882a593Smuzhiyun 	 */
1517*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("HPR Mix", SND_SOC_NOPM, 2, 0,
1518*4882a593Smuzhiyun 			   &es8396_hpr_mixer_controls[0],
1519*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_hpr_mixer_controls)),
1520*4882a593Smuzhiyun 	SND_SOC_DAPM_SWITCH_E("HP Amp", SND_SOC_NOPM, 0, 0,
1521*4882a593Smuzhiyun 			      &hp_amp_ctl, hpamp_event,
1522*4882a593Smuzhiyun 			      SND_SOC_DAPM_PRE_PMU),
1523*4882a593Smuzhiyun 	/*
1524*4882a593Smuzhiyun 	 * mixerSPK
1525*4882a593Smuzhiyun 	 */
1526*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("SPKL Mix", SND_SOC_NOPM, 0, 0,
1527*4882a593Smuzhiyun 			   &es8396_speaker_lmixer_controls[0],
1528*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_speaker_lmixer_controls)),
1529*4882a593Smuzhiyun 	SND_SOC_DAPM_MIXER("SPKR Mix", SND_SOC_NOPM, 0, 0,
1530*4882a593Smuzhiyun 			   &es8396_speaker_rmixer_controls[0],
1531*4882a593Smuzhiyun 			   ARRAY_SIZE(es8396_speaker_rmixer_controls)),
1532*4882a593Smuzhiyun 	SND_SOC_DAPM_SWITCH_E("SPK Amp", SND_SOC_NOPM, 0, 0,
1533*4882a593Smuzhiyun 			      &es8396_spkldo_pwrswitch_controls, classd_event,
1534*4882a593Smuzhiyun 			      SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_PRE_PMD),
1535*4882a593Smuzhiyun 
1536*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("MONOOUTP"),
1537*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("MONOOUTN"),
1538*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("HPL"),
1539*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("HPR"),
1540*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("SPKOUTL"),
1541*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("SPKOUTR"),
1542*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("LOUTP"),
1543*4882a593Smuzhiyun 	SND_SOC_DAPM_OUTPUT("ROUTN"),
1544*4882a593Smuzhiyun };
1545*4882a593Smuzhiyun 
1546*4882a593Smuzhiyun static const struct snd_soc_dapm_route es8396_dapm_routes[] = {
1547*4882a593Smuzhiyun 	/* lln mux */
1548*4882a593Smuzhiyun 	{"LLN Mux", "RPGAP", "RPGA P"},
1549*4882a593Smuzhiyun 	{"LLN Mux", "LPGAP", "LPGA P"},
1550*4882a593Smuzhiyun 	{"LLN Mux", "MONOP", "MONOINP"},
1551*4882a593Smuzhiyun 	{"LLN Mux", "AINL", "AINL"},
1552*4882a593Smuzhiyun 
1553*4882a593Smuzhiyun 	/* rln mux */
1554*4882a593Smuzhiyun 	{"RLN Mux", "RPGAP", "RPGA P"},
1555*4882a593Smuzhiyun 	{"RLN Mux", "LPGAP", "LPGA P"},
1556*4882a593Smuzhiyun 	{"RLN Mux", "MONON", "MONOINN"},
1557*4882a593Smuzhiyun 	{"RLN Mux", "AINR", "AINR"},
1558*4882a593Smuzhiyun 
1559*4882a593Smuzhiyun 	/* lax mux */
1560*4882a593Smuzhiyun 	{"LAX Mux", "RPGAP", "RPGA P"},
1561*4882a593Smuzhiyun 	{"LAX Mux", "LPGAP", "LPGA P"},
1562*4882a593Smuzhiyun 	{"LAX Mux", "MONOP", "MONOINP"},
1563*4882a593Smuzhiyun 	{"LAX Mux", "AINL", "AINL"},
1564*4882a593Smuzhiyun 
1565*4882a593Smuzhiyun 	/* rax mux */
1566*4882a593Smuzhiyun 	{"RAX Mux", "RPGAP", "RPGA P"},
1567*4882a593Smuzhiyun 	{"RAX Mux", "LPGAP", "LPGA P"},
1568*4882a593Smuzhiyun 	{"RAX Mux", "MONON", "MONOINN"},
1569*4882a593Smuzhiyun 	{"RAX Mux", "AINR", "AINR"},
1570*4882a593Smuzhiyun 
1571*4882a593Smuzhiyun 	/* Left, right PGA */
1572*4882a593Smuzhiyun 	{"LPGA P", NULL, "PGA Left Mix"},
1573*4882a593Smuzhiyun 	{"RPGA P", NULL, "PGA Right Mix"},
1574*4882a593Smuzhiyun 
1575*4882a593Smuzhiyun 	{"PGA Left Mix", "RLNMIX2LPGA Switch", "RLNINMIX PGA"},
1576*4882a593Smuzhiyun 	{"PGA Left Mix", "RAXMIX2LPGA Switch", "RAXINMIX PGA"},
1577*4882a593Smuzhiyun 	{"PGA Left Mix", "RMNMIX2LPGA Switch", "RMONINMIX PGA"},
1578*4882a593Smuzhiyun 	{"PGA Left Mix", "LMNMIX2LPGA Switch", "LMONINMIX PGA"},
1579*4882a593Smuzhiyun 	{"PGA Left Mix", "LLNMIX2LPGA Switch", "LLNINMIX PGA"},
1580*4882a593Smuzhiyun 
1581*4882a593Smuzhiyun 	{"PGA Right Mix", "RLNMIX2RPGA Switch", "RLNINMIX PGA"},
1582*4882a593Smuzhiyun 	{"PGA Right Mix", "RAXMIX2RPGA Switch", "RAXINMIX PGA"},
1583*4882a593Smuzhiyun 	{"PGA Right Mix", "RMNMIX2RPGA Switch", "RMONINMIX PGA"},
1584*4882a593Smuzhiyun 	{"PGA Right Mix", "LMNMIX2RPGA Switch", "LMONINMIX PGA"},
1585*4882a593Smuzhiyun 	{"PGA Right Mix", "LAXMIX2RPGA Switch", "LAXINMIX PGA"},
1586*4882a593Smuzhiyun 
1587*4882a593Smuzhiyun 	/* lnmix */
1588*4882a593Smuzhiyun 	{"RLNINMIX PGA", NULL, "RLNIN Mix"},
1589*4882a593Smuzhiyun 	{"LLNINMIX PGA", NULL, "LLNIN Mix"},
1590*4882a593Smuzhiyun 
1591*4882a593Smuzhiyun 	{"LLNIN Mix", "AINL2LLNMIX Switch", "AINL"},
1592*4882a593Smuzhiyun 	{"LLNIN Mix", "LLNMUX2LLNMIX Switch", "LLN Mux"},
1593*4882a593Smuzhiyun 	{"LLNIN Mix", "MIC1P2LLNMIX Switch", "MIC"},
1594*4882a593Smuzhiyun 	{"LLNIN Mix", "PMICDSE2LLNMIX Switch", "MIC BOOST"},
1595*4882a593Smuzhiyun 
1596*4882a593Smuzhiyun 	{"RLNIN Mix", "AINR2RLNMIX Switch", "AINR"},
1597*4882a593Smuzhiyun 	{"RLNIN Mix", "RLNMUX2RLNMIX Switch", "RLN Mux"},
1598*4882a593Smuzhiyun 	{"RLNIN Mix", "MIC1N2LLNMIX Switch", "MIC"},
1599*4882a593Smuzhiyun 	{"RLNIN Mix", "NMICDSE2RLNMIX Switch", "MIC BOOST"},
1600*4882a593Smuzhiyun 
1601*4882a593Smuzhiyun 	/* AXmix */
1602*4882a593Smuzhiyun 	{"RAXINMIX PGA", NULL, "RAXIN Mix"},
1603*4882a593Smuzhiyun 	{"LAXINMIX PGA", NULL, "LAXIN Mix"},
1604*4882a593Smuzhiyun 
1605*4882a593Smuzhiyun 	{"LAXIN Mix", "LAXMUX2LAXMIX Switch", "LAX Mux"},
1606*4882a593Smuzhiyun 	{"LAXIN Mix", "MONOP2LAXMIX Switch", "MONOINP"},
1607*4882a593Smuzhiyun 	{"LAXIN Mix", "MIC2P2LAXMIX Switch", "MIC"},
1608*4882a593Smuzhiyun 	{"LAXIN Mix", "PMICDSE2LAXMIX Switch", "MIC BOOST"},
1609*4882a593Smuzhiyun 
1610*4882a593Smuzhiyun 	{"RAXIN Mix", "RAXMUX2RAXMIX Switch", "RAX Mux"},
1611*4882a593Smuzhiyun 	{"RAXIN Mix", "MONON2RAXMIX Switch", "MONOINN"},
1612*4882a593Smuzhiyun 	{"RAXIN Mix", "MIC2N2RAXMIX Switch", "MIC"},
1613*4882a593Smuzhiyun 	{"RAXIN Mix", "NMICDSE2RAXMIX Switch", "MIC BOOST"},
1614*4882a593Smuzhiyun 
1615*4882a593Smuzhiyun 	/* MNmix */
1616*4882a593Smuzhiyun 	{"RMONINMIX PGA", NULL, "RMONIN Mix"},
1617*4882a593Smuzhiyun 	{"LMONINMIX PGA", NULL, "LMONIN Mix"},
1618*4882a593Smuzhiyun 
1619*4882a593Smuzhiyun 	{"LMONIN Mix", "LDAC2LMNMIX Switch", "Left DAC"},
1620*4882a593Smuzhiyun 	{"LMONIN Mix", "MONOP2LMNMIX Switch", "MONOINP"},
1621*4882a593Smuzhiyun 	{"LMONIN Mix", "AINL2LMNMIX Switch", "AINL"},
1622*4882a593Smuzhiyun 
1623*4882a593Smuzhiyun 	{"RMONIN Mix", "RDAC2RMNMIX Switch", "Right DAC"},
1624*4882a593Smuzhiyun 	{"RMONIN Mix", "MONON2RMNMIX Switch", "MONOINN"},
1625*4882a593Smuzhiyun 	{"RMONIN Mix", "AINR2RMNMIX Switch", "AINR"},
1626*4882a593Smuzhiyun 
1627*4882a593Smuzhiyun 	/* Analog mic mux */
1628*4882a593Smuzhiyun 	{"MIC BOOST", NULL, "AMIC Mux"},
1629*4882a593Smuzhiyun 
1630*4882a593Smuzhiyun 	{"AMIC Mux", "Switch", "MIC"},
1631*4882a593Smuzhiyun 	{"MIC", NULL, "MIC Bias"},
1632*4882a593Smuzhiyun 	/* capature */
1633*4882a593Smuzhiyun 	{"ADC Left", NULL, "LPGA P"},
1634*4882a593Smuzhiyun 	{"ADC Right", NULL, "RPGA P"},
1635*4882a593Smuzhiyun 
1636*4882a593Smuzhiyun 	{"ADC_1", "Switch", "ADC Left"},
1637*4882a593Smuzhiyun 	{"ADC_1", "Switch", "ADC Right"},
1638*4882a593Smuzhiyun 
1639*4882a593Smuzhiyun 	/* digital mixer */
1640*4882a593Smuzhiyun 	{"Equalizer", NULL, "Digital Left Mixer"},
1641*4882a593Smuzhiyun 	{"Equalizer", NULL, "Digital Right Mixer"},
1642*4882a593Smuzhiyun 
1643*4882a593Smuzhiyun 	{"Digital Left Mixer", NULL, "LDMIX1 Mux"},
1644*4882a593Smuzhiyun 	{"Digital Left Mixer", NULL, "LDMIX2 Mux"},
1645*4882a593Smuzhiyun 
1646*4882a593Smuzhiyun 	{"Digital Right Mixer", NULL, "RDMIX1 Mux"},
1647*4882a593Smuzhiyun 	{"Digital Right Mixer", NULL, "RDMIX2 Mux"},
1648*4882a593Smuzhiyun 
1649*4882a593Smuzhiyun 	{"LDMIX1 Mux", "left SDP1 in", "VOICESDPIL"},
1650*4882a593Smuzhiyun 	{"LDMIX1 Mux", "left SDP2 in", "MASTERSDPIL"},
1651*4882a593Smuzhiyun 	{"LDMIX1 Mux", "left SDP3 in", "AUXSDPIL"},
1652*4882a593Smuzhiyun 	{"LDMIX1 Mux", "left ADC out", "ADC_1"},
1653*4882a593Smuzhiyun 	{"LDMIX1 Mux", "right SDP1 in", "VOICESDPIR"},
1654*4882a593Smuzhiyun 	{"LDMIX1 Mux", "right SDP2 in", "MASTERSDPIR"},
1655*4882a593Smuzhiyun 	{"LDMIX1 Mux", "right SDP3 in", "AUXSDPIR"},
1656*4882a593Smuzhiyun 	{"LDMIX1 Mux", "right ADC out", "ADC_1"},
1657*4882a593Smuzhiyun 
1658*4882a593Smuzhiyun 	{"RDMIX1 Mux", "left SDP1 in", "VOICESDPIL"},
1659*4882a593Smuzhiyun 	{"RDMIX1 Mux", "left SDP2 in", "MASTERSDPIL"},
1660*4882a593Smuzhiyun 	{"RDMIX1 Mux", "left SDP3 in", "AUXSDPIL"},
1661*4882a593Smuzhiyun 	{"RDMIX1 Mux", "left ADC out", "ADC_1"},
1662*4882a593Smuzhiyun 	{"RDMIX1 Mux", "right SDP1 in", "VOICESDPIR"},
1663*4882a593Smuzhiyun 	{"RDMIX1 Mux", "right SDP2 in", "MASTERSDPIR"},
1664*4882a593Smuzhiyun 	{"RDMIX1 Mux", "right SDP3 in", "AUXSDPIR"},
1665*4882a593Smuzhiyun 	{"RDMIX1 Mux", "right ADC out", "ADC_1"},
1666*4882a593Smuzhiyun 
1667*4882a593Smuzhiyun 	{"LDMIX2 Mux", "left SDP1 in", "VOICESDPIL"},
1668*4882a593Smuzhiyun 	{"LDMIX2 Mux", "left SDP2 in", "MASTERSDPIL"},
1669*4882a593Smuzhiyun 	{"LDMIX2 Mux", "left SDP3 in", "AUXSDPIL"},
1670*4882a593Smuzhiyun 	{"LDMIX2 Mux", "left ADC out", "ADC_1"},
1671*4882a593Smuzhiyun 	{"LDMIX2 Mux", "right SDP1 in", "VOICESDPIR"},
1672*4882a593Smuzhiyun 	{"LDMIX2 Mux", "right SDP2 in", "MASTERSDPIR"},
1673*4882a593Smuzhiyun 	{"LDMIX2 Mux", "right SDP3 in", "AUXSDPIR"},
1674*4882a593Smuzhiyun 	{"LDMIX2 Mux", "right ADC out", "ADC_1"},
1675*4882a593Smuzhiyun 
1676*4882a593Smuzhiyun 	{"RDMIX2 Mux", "left SDP1 in", "VOICESDPIL"},
1677*4882a593Smuzhiyun 	{"RDMIX2 Mux", "left SDP2 in", "MASTERSDPIL"},
1678*4882a593Smuzhiyun 	{"RDMIX2 Mux", "left SDP3 in", "AUXSDPIL"},
1679*4882a593Smuzhiyun 	{"RDMIX2 Mux", "left ADC out", "ADC_1"},
1680*4882a593Smuzhiyun 	{"RDMIX2 Mux", "right SDP1 in", "VOICESDPIR"},
1681*4882a593Smuzhiyun 	{"RDMIX2 Mux", "right SDP2 in", "MASTERSDPIR"},
1682*4882a593Smuzhiyun 	{"RDMIX2 Mux", "right SDP3 in", "AUXSDPIR"},
1683*4882a593Smuzhiyun 	{"RDMIX2 Mux", "right ADC out", "ADC_1"},
1684*4882a593Smuzhiyun 
1685*4882a593Smuzhiyun 	/* VOICE/SDP1 AIF IN mixer */
1686*4882a593Smuzhiyun 	{"VOICEIN AIF Mixer", NULL, "VOICESDPIL"},
1687*4882a593Smuzhiyun 	{"VOICEIN AIF Mixer", NULL, "VOICESDPIR"},
1688*4882a593Smuzhiyun 	/* master/SDP2 AIF IN mixer */
1689*4882a593Smuzhiyun 	{"MASTERIN AIF Mixer", NULL, "MASTERSDPIL"},
1690*4882a593Smuzhiyun 	{"MASTERIN AIF Mixer", NULL, "MASTERSDPIR"},
1691*4882a593Smuzhiyun 	/* aux/SDP3 AIF IN mixer */
1692*4882a593Smuzhiyun 	{"AUXIN AIF Mixer", NULL, "AUXSDPIL"},
1693*4882a593Smuzhiyun 	{"AUXIN AIF Mixer", NULL, "AUXSDPIR"},
1694*4882a593Smuzhiyun 	/* VOICE/SDP1 AIF OUT */
1695*4882a593Smuzhiyun 	{"VOICESDPOL", NULL, "VOICESDPO Mux"},
1696*4882a593Smuzhiyun 	{"VOICESDPOR", NULL, "VOICESDPO Mux"},
1697*4882a593Smuzhiyun 
1698*4882a593Smuzhiyun 	{"VOICESDPO Mux", "ADC out", "ADC_1"},
1699*4882a593Smuzhiyun 	{"VOICESDPO Mux", "SDP1 in", "VOICEIN AIF Mixer"},
1700*4882a593Smuzhiyun 	{"VOICESDPO Mux", "SDP2 in", "MASTERIN AIF Mixer"},
1701*4882a593Smuzhiyun 	{"VOICESDPO Mux", "SDP3 in", "AUXIN AIF Mixer"},
1702*4882a593Smuzhiyun 	{"VOICESDPO Mux", "EQ stereo", "Equalizer"},
1703*4882a593Smuzhiyun 	{"VOICESDPO Mux", "EQ left", "Digital Left Mixer"},
1704*4882a593Smuzhiyun 	{"VOICESDPO Mux", "EQ right", "Digital Right Mixer"},
1705*4882a593Smuzhiyun 
1706*4882a593Smuzhiyun 	/* master/SDP2 AIF OUT */
1707*4882a593Smuzhiyun 	{"MASTERSDPOL", NULL, "MASTERSDPO Mux"},
1708*4882a593Smuzhiyun 	{"MASTERSDPOR", NULL, "MASTERSDPO Mux"},
1709*4882a593Smuzhiyun 
1710*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "ADC out", "ADC_1"},
1711*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "SDP1 in", "VOICEIN AIF Mixer"},
1712*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "SDP2 in", "MASTERIN AIF Mixer"},
1713*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "SDP3 in", "AUXIN AIF Mixer"},
1714*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "EQ stereo", "Equalizer"},
1715*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "EQ left", "Digital Left Mixer"},
1716*4882a593Smuzhiyun 	{"MASTERSDPO Mux", "EQ right", "Digital Right Mixer"},
1717*4882a593Smuzhiyun 
1718*4882a593Smuzhiyun 	/* AUX/SDP3 AIF OUT */
1719*4882a593Smuzhiyun 	{"AUXSDPOL", NULL, "AUXSDPO Mux"},
1720*4882a593Smuzhiyun 	{"AUXSDPOR", NULL, "AUXSDPO Mux"},
1721*4882a593Smuzhiyun 
1722*4882a593Smuzhiyun 	{"AUXSDPO Mux", "ADC out", "ADC_1"},
1723*4882a593Smuzhiyun 	{"AUXSDPO Mux", "SDP1 in", "VOICEIN AIF Mixer"},
1724*4882a593Smuzhiyun 	{"AUXSDPO Mux", "SDP2 in", "MASTERIN AIF Mixer"},
1725*4882a593Smuzhiyun 	{"AUXSDPO Mux", "SDP3 in", "AUXIN AIF Mixer"},
1726*4882a593Smuzhiyun 	{"AUXSDPO Mux", "EQ stereo", "Equalizer"},
1727*4882a593Smuzhiyun 	{"AUXSDPO Mux", "EQ left", "Digital Left Mixer"},
1728*4882a593Smuzhiyun 	{"AUXSDPO Mux", "EQ right", "Digital Right Mixer"},
1729*4882a593Smuzhiyun 
1730*4882a593Smuzhiyun 	/* DAC */
1731*4882a593Smuzhiyun 	{"Left DAC", NULL, "DAC_1"},
1732*4882a593Smuzhiyun 	{"Right DAC", NULL, "DAC_1"},
1733*4882a593Smuzhiyun 
1734*4882a593Smuzhiyun 	{"DAC_1", "Switch", "DACSRC Mux"},
1735*4882a593Smuzhiyun 
1736*4882a593Smuzhiyun 	{"DACSRC Mux", "SDP1 in", "VOICEIN AIF Mixer"},
1737*4882a593Smuzhiyun 	{"DACSRC Mux", "SDP2 in", "MASTERIN AIF Mixer"},
1738*4882a593Smuzhiyun 	{"DACSRC Mux", "SDP3 in", "AUXIN AIF Mixer"},
1739*4882a593Smuzhiyun 	{"DACSRC Mux", "ADC out", "ADC_1"},
1740*4882a593Smuzhiyun 	{"DACSRC Mux", "EQ stereo", "Equalizer"},
1741*4882a593Smuzhiyun 	{"DACSRC Mux", "EQ left", "Digital Left Mixer"},
1742*4882a593Smuzhiyun 	{"DACSRC Mux", "EQ right", "Digital Right Mixer"},
1743*4882a593Smuzhiyun 
1744*4882a593Smuzhiyun 	/* SPEAKER Paths */
1745*4882a593Smuzhiyun 	{"SPKOUTL", NULL, "SPK Amp"},
1746*4882a593Smuzhiyun 	{"SPKOUTR", NULL, "SPK Amp"},
1747*4882a593Smuzhiyun 
1748*4882a593Smuzhiyun 	{"SPK Amp", "Switch", "SPKL Mix"},
1749*4882a593Smuzhiyun 	{"SPK Amp", "Switch", "SPKR Mix"},
1750*4882a593Smuzhiyun 	/*
1751*4882a593Smuzhiyun 	 * {"SPK Amp", "Switch", "SPKL Mux"},
1752*4882a593Smuzhiyun 	 * {"SPK Amp", "Switch", "SPKR Mux"},
1753*4882a593Smuzhiyun 	 *
1754*4882a593Smuzhiyun 	 * {"SPKL Mux", "SPKR Route", "SPKR Mix"},
1755*4882a593Smuzhiyun 	 * {"SPKL Mux", "SPKL Route", "SPKL Mix"},
1756*4882a593Smuzhiyun 	 *
1757*4882a593Smuzhiyun 	 * {"SPKR Mux", "SPKR Route", "SPKR Mix"},
1758*4882a593Smuzhiyun 	 * {"SPKR Mux", "SPKL Route", "SPKL Mix"},
1759*4882a593Smuzhiyun 	 */
1760*4882a593Smuzhiyun 	{"SPKL Mix", "LLNMUX2SPKMIX Switch", "LLN Mux"},
1761*4882a593Smuzhiyun 	{"SPKL Mix", "LAXMUX2SPKMIX Switch", "LAX Mux"},
1762*4882a593Smuzhiyun 	{"SPKL Mix", "LDAC2SPKMIX Switch", "Left DAC"},
1763*4882a593Smuzhiyun 
1764*4882a593Smuzhiyun 	{"SPKR Mix", "RLNMUX2SPKMIX Switch", "RLN Mux"},
1765*4882a593Smuzhiyun 	{"SPKR Mix", "RAXMUX2SPKMIX Switch", "RAX Mux"},
1766*4882a593Smuzhiyun 	{"SPKR Mix", "RDAC2SPKMIX Switch", "Right DAC"},
1767*4882a593Smuzhiyun 
1768*4882a593Smuzhiyun 	/* HEADPHONE Paths */
1769*4882a593Smuzhiyun 	{"HPL", NULL, "HP Amp"},
1770*4882a593Smuzhiyun 	{"HPR", NULL, "HP Amp"},
1771*4882a593Smuzhiyun 
1772*4882a593Smuzhiyun 	{"HP Amp", "Switch", "HPL Mix"},
1773*4882a593Smuzhiyun 	{"HP Amp", "Switch", "HPR Mix"},
1774*4882a593Smuzhiyun 
1775*4882a593Smuzhiyun 	{"HPL Mix", "LNMUX2HPMIX_L Switch", "LLN Mux"},
1776*4882a593Smuzhiyun 	{"HPL Mix", "AXMUX2HPMIX_L Switch", "LAX Mux"},
1777*4882a593Smuzhiyun 	{"HPL Mix", "DACL2HPMIX Switch", "Left DAC"},
1778*4882a593Smuzhiyun 
1779*4882a593Smuzhiyun 	{"HPR Mix", "LNMUX2HPMIX_R Switch", "RLN Mux"},
1780*4882a593Smuzhiyun 	{"HPR Mix", "AXMUX2HPMIX_R Switch", "RAX Mux"},
1781*4882a593Smuzhiyun 	{"HPR Mix", "DACR2HPMIX Switch", "Right DAC"},
1782*4882a593Smuzhiyun 
1783*4882a593Smuzhiyun 	/* EARPIECE Paths */
1784*4882a593Smuzhiyun 	{"MONOOUTP", NULL, "MNOUTP PGA"},
1785*4882a593Smuzhiyun 	{"MONOOUTN", NULL, "MNOUTN PGA"},
1786*4882a593Smuzhiyun 
1787*4882a593Smuzhiyun 	{"MNOUTP PGA", NULL, "MNOUTP Mix"},
1788*4882a593Smuzhiyun 	{"MNOUTN PGA", NULL, "MNOUTN Mix"},
1789*4882a593Smuzhiyun 
1790*4882a593Smuzhiyun 	{"MNOUTP Mix", "LHPMIX2MNMIXP Switch", "HPL Mix"},
1791*4882a593Smuzhiyun 	{"MNOUTP Mix", "RHPMIX2MNOMIXP Switch", "HPR Mix"},
1792*4882a593Smuzhiyun 	{"MNOUTP Mix", "RMNMIX2MNOMIXP Switch", "RMONINMIX PGA"},
1793*4882a593Smuzhiyun 	{"MNOUTP Mix", "RAXMIX2MNOMIXP Switch", "RAXINMIX PGA"},
1794*4882a593Smuzhiyun 	{"MNOUTP Mix", "LLNMIX2MNOMIXP Switch", "LLNINMIX PGA"},
1795*4882a593Smuzhiyun 
1796*4882a593Smuzhiyun 	{"MNOUTN Mix", "LMNMIX2MNMIXN Switch", "LMONINMIX PGA"},
1797*4882a593Smuzhiyun 	{"MNOUTN Mix", "RHPMIX2MNOMIXN Switch", "HPR Mix"},
1798*4882a593Smuzhiyun 	{"MNOUTN Mix", "MOPINV2MNOMIXN Switch", "MNOUTP Mix"},
1799*4882a593Smuzhiyun 	{"MNOUTN Mix", "LLNMIX2MNOMIXN Switch", "LLNINMIX PGA"},
1800*4882a593Smuzhiyun 	{"MNOUTN Mix", "LAXMIX2MNOMIXN Switch", "LAXINMIX PGA"},
1801*4882a593Smuzhiyun 
1802*4882a593Smuzhiyun 	/* LNOUT Paths */
1803*4882a593Smuzhiyun 	{"LOUTP", NULL, "LNOUTMIX1 PGA"},
1804*4882a593Smuzhiyun 	{"ROUTN", NULL, "RNOUTMIX1 PGA"},
1805*4882a593Smuzhiyun 
1806*4882a593Smuzhiyun 	{"LNOUTMIX1 PGA", NULL, "LOUT1 Mix"},
1807*4882a593Smuzhiyun 	{"RNOUTMIX1 PGA", NULL, "ROUT1 Mix"},
1808*4882a593Smuzhiyun 
1809*4882a593Smuzhiyun 	{"LOUT1 Mix", "LDAC2LO1MIXP Switch", "Left DAC"},
1810*4882a593Smuzhiyun 	{"LOUT1 Mix", "LAXMIX2LO1MIXP Switch", "LAXINMIX PGA"},
1811*4882a593Smuzhiyun 	{"LOUT1 Mix", "LLNMIX2LO1MIXP Switch", "LLNINMIX PGA"},
1812*4882a593Smuzhiyun 	{"LOUT1 Mix", "LMNMIX2LO1MIXP Switch", "LMONINMIX PGA"},
1813*4882a593Smuzhiyun 	{"LOUT1 Mix", "RO1INV2LO1MIXP Switch", "ROUT1 Mix"},
1814*4882a593Smuzhiyun 
1815*4882a593Smuzhiyun 	{"ROUT1 Mix", "RDAC2RO1MIXN Switch", "Right DAC"},
1816*4882a593Smuzhiyun 	{"ROUT1 Mix", "RAXMIX2RO1MIXN Switch", "RAXINMIX PGA"},
1817*4882a593Smuzhiyun 	{"ROUT1 Mix", "RLNMIX2RO1MIXN Switch", "RLNINMIX PGA"},
1818*4882a593Smuzhiyun 	{"ROUT1 Mix", "RMNMIX2RO1MIXN Switch", "RMONINMIX PGA"},
1819*4882a593Smuzhiyun 	{"ROUT1 Mix", "LO1INV2RO1MIXN Switch", "LOUT1 Mix"},
1820*4882a593Smuzhiyun };
1821*4882a593Smuzhiyun 
1822*4882a593Smuzhiyun struct _pll_div {
1823*4882a593Smuzhiyun 	u32 pll_in;
1824*4882a593Smuzhiyun 	u32 pll_out;
1825*4882a593Smuzhiyun 	u8 mclkdiv;
1826*4882a593Smuzhiyun 	u8 plldiv;
1827*4882a593Smuzhiyun 	u8 n;
1828*4882a593Smuzhiyun 	u8 k1;
1829*4882a593Smuzhiyun 	u8 k2;
1830*4882a593Smuzhiyun 	u8 k3;
1831*4882a593Smuzhiyun };
1832*4882a593Smuzhiyun 
1833*4882a593Smuzhiyun static const struct _pll_div codec_pll_div[] = {
1834*4882a593Smuzhiyun 	{7500000, 11289600, 1, 8, 12, 0x01, 0xc6, 0xee},
1835*4882a593Smuzhiyun 	{7500000, 12288000, 1, 8, 13, 0x04, 0x82, 0x90},
1836*4882a593Smuzhiyun 
1837*4882a593Smuzhiyun 	{7600000, 11289600, 1, 8, 11, 0x25, 0x2e, 0x93},
1838*4882a593Smuzhiyun 	{7600000, 12288000, 1, 8, 12, 0x27, 0x53, 0x49},
1839*4882a593Smuzhiyun 
1840*4882a593Smuzhiyun 	{8192000, 11289600, 1, 8, 11, 0x01, 0x0d, 0x41},
1841*4882a593Smuzhiyun 	{8192000, 12288000, 1, 8, 12, 0x00, 0x00, 0x01},
1842*4882a593Smuzhiyun 
1843*4882a593Smuzhiyun 	{8380000, 11289600, 1, 8, 10, 0x20, 0xb7, 0x8d},
1844*4882a593Smuzhiyun 	{8380000, 12288000, 1, 8, 11, 0x1e, 0xbe, 0xb7},
1845*4882a593Smuzhiyun 
1846*4882a593Smuzhiyun 	{9000000, 11289600, 1, 8, 10, 0x01, 0x7b, 0x1c},
1847*4882a593Smuzhiyun 	{9000000, 12288000, 1, 8, 10, 0x26, 0xd1, 0x4a},
1848*4882a593Smuzhiyun 
1849*4882a593Smuzhiyun 	{9600000, 11289600, 1, 8, 9, 0x11, 0x2a, 0x3c},
1850*4882a593Smuzhiyun 	{9600000, 12288000, 1, 8, 10, 0x0a, 0x18, 0xd8},
1851*4882a593Smuzhiyun 
1852*4882a593Smuzhiyun 	{9800000, 11289600, 1, 8, 9, 0x09, 0x16, 0x5c},
1853*4882a593Smuzhiyun 	{9800000, 12288000, 1, 8, 10, 0x01, 0x4e, 0x18},
1854*4882a593Smuzhiyun 
1855*4882a593Smuzhiyun 	{10000000, 11289600, 1, 8, 9, 0x01, 0x55, 0x33},
1856*4882a593Smuzhiyun 	{10000000, 12288000, 1, 8, 9, 0x22, 0xef, 0x8f},
1857*4882a593Smuzhiyun 
1858*4882a593Smuzhiyun 	{11059200, 11289600, 1, 8, 8, 0x07, 0x03, 0x07},
1859*4882a593Smuzhiyun 	{11059200, 12288000, 1, 8, 8, 0x25, 0x65, 0x7f},
1860*4882a593Smuzhiyun 
1861*4882a593Smuzhiyun 	{11289600, 11289600, 1, 8, 8, 0x00, 0x00, 0x01},
1862*4882a593Smuzhiyun 	{11289600, 12288000, 1, 8, 8, 0x1d, 0xc3, 0xb8},
1863*4882a593Smuzhiyun 
1864*4882a593Smuzhiyun 	{11500000, 11289600, 1, 8, 7, 0x23, 0xe9, 0xcd},
1865*4882a593Smuzhiyun 	{11500000, 12288000, 1, 8, 8, 0x17, 0x0f, 0xee},
1866*4882a593Smuzhiyun 
1867*4882a593Smuzhiyun 	{12000000, 11289600, 1, 8, 7, 0x16, 0x25, 0x6c},
1868*4882a593Smuzhiyun 	{12000000, 12288000, 1, 8, 8, 0x08, 0x13, 0xe0},
1869*4882a593Smuzhiyun 
1870*4882a593Smuzhiyun 	{12288000, 11289600, 1, 8, 7, 0x0e, 0xb9, 0x90},
1871*4882a593Smuzhiyun 	{12288000, 12288000, 1, 8, 8, 0x00, 0x00, 0x01},
1872*4882a593Smuzhiyun 
1873*4882a593Smuzhiyun 	{12500000, 11289600, 1, 8, 7, 0x09, 0x7a, 0xff},
1874*4882a593Smuzhiyun 	{12500000, 12288000, 1, 8, 7, 0x24, 0x5c, 0xe2},
1875*4882a593Smuzhiyun 
1876*4882a593Smuzhiyun 	{12800000, 11289600, 1, 8, 7, 0x02, 0x5b, 0x21},
1877*4882a593Smuzhiyun 	{12800000, 12288000, 1, 8, 7, 0x1c, 0x9b, 0xb9},
1878*4882a593Smuzhiyun 
1879*4882a593Smuzhiyun 	{13000000, 11289600, 1, 8, 6, 0x27, 0xdc, 0x2b},
1880*4882a593Smuzhiyun 	{13000000, 12288000, 1, 8, 7, 0x17, 0xa3, 0x2f},
1881*4882a593Smuzhiyun 
1882*4882a593Smuzhiyun 	{13500000, 11289600, 1, 8, 6, 0x1d, 0x08, 0xdc},
1883*4882a593Smuzhiyun 	{13500000, 12288000, 1, 8, 7, 0x0b, 0xda, 0xcc},
1884*4882a593Smuzhiyun 
1885*4882a593Smuzhiyun 	{13560000, 11289600, 1, 8, 6, 0x1b, 0xca, 0x0a},
1886*4882a593Smuzhiyun 	{13560000, 12288000, 1, 8, 7, 0x0a, 0x7f, 0xc7},
1887*4882a593Smuzhiyun 
1888*4882a593Smuzhiyun 	{14000000, 11289600, 1, 8, 6, 0x12, 0xfb, 0x81},
1889*4882a593Smuzhiyun 	{14000000, 12288000, 1, 8, 7, 0x00, 0xe9, 0xdd},
1890*4882a593Smuzhiyun 
1891*4882a593Smuzhiyun 	{15000000, 11289600, 1, 8, 6, 0x00, 0xe3, 0x77},
1892*4882a593Smuzhiyun 	{15000000, 12288000, 1, 8, 6, 0x17, 0x4a, 0x5f},
1893*4882a593Smuzhiyun 
1894*4882a593Smuzhiyun 	{15360000, 11289600, 1, 8, 5, 0x25, 0x05, 0xc2},
1895*4882a593Smuzhiyun 	{15360000, 12288000, 1, 8, 6, 0x10, 0xd4, 0x12},
1896*4882a593Smuzhiyun 
1897*4882a593Smuzhiyun 	{16000000, 11289600, 1, 8, 5, 0x1b, 0x20, 0x9d},
1898*4882a593Smuzhiyun 	{16000000, 12288000, 1, 8, 6, 0x06, 0x0e, 0xe8},
1899*4882a593Smuzhiyun 
1900*4882a593Smuzhiyun 	{16384000, 11289600, 1, 8, 5, 0x15, 0x8f, 0xb8},
1901*4882a593Smuzhiyun 	{16384000, 12288000, 1, 8, 6, 0x00, 0x00, 0x01},
1902*4882a593Smuzhiyun 
1903*4882a593Smuzhiyun 	{16800000, 11289600, 1, 8, 5, 0x0f, 0xd1, 0x96},
1904*4882a593Smuzhiyun 	{16800000, 12288000, 1, 8, 5, 0x23, 0xd2, 0x0a},
1905*4882a593Smuzhiyun 
1906*4882a593Smuzhiyun 	{18432000, 11289600, 2, 8, 9, 0x21, 0xa8, 0x25},
1907*4882a593Smuzhiyun 	{18432000, 12288000, 2, 8, 10, 0x1c, 0x0c, 0x1f},
1908*4882a593Smuzhiyun 
1909*4882a593Smuzhiyun 	{19200000, 11289600, 2, 8, 9, 0x11, 0x2a, 0x3c},
1910*4882a593Smuzhiyun 	{19200000, 12288000, 2, 8, 10, 0x0a, 0x18, 0xd8},
1911*4882a593Smuzhiyun 
1912*4882a593Smuzhiyun 	{19800000, 11289600, 2, 8, 9, 0x05, 0x2b, 0xc0},
1913*4882a593Smuzhiyun 	{19800000, 12288000, 2, 8, 9, 0x27, 0x1d, 0x01},
1914*4882a593Smuzhiyun 
1915*4882a593Smuzhiyun 	{20000000, 11289600, 2, 8, 9, 0x01, 0x55, 0x33},
1916*4882a593Smuzhiyun 	{20000000, 12288000, 2, 8, 9, 0x22, 0xef, 0x8f},
1917*4882a593Smuzhiyun 
1918*4882a593Smuzhiyun 	{22118400, 11289600, 2, 8, 8, 0x07, 0x03, 0x07},
1919*4882a593Smuzhiyun 	{22118400, 12288000, 2, 8, 8, 0x25, 0x65, 0x7f},
1920*4882a593Smuzhiyun 
1921*4882a593Smuzhiyun 	{22579200, 11289600, 2, 8, 8, 0x00, 0x00, 0x01},
1922*4882a593Smuzhiyun 	{22579200, 12288000, 2, 8, 8, 0x1d, 0xc3, 0xb8},
1923*4882a593Smuzhiyun 
1924*4882a593Smuzhiyun 	{24000000, 11289600, 2, 8, 7, 0x16, 0x25, 0x6c},
1925*4882a593Smuzhiyun 	{24000000, 12288000, 2, 8, 8, 0x08, 0x13, 0xe0},
1926*4882a593Smuzhiyun 
1927*4882a593Smuzhiyun 	{24576000, 11289600, 2, 8, 7, 0x0e, 0xb9, 0x90},
1928*4882a593Smuzhiyun 	{24576000, 12288000, 2, 8, 8, 0x00, 0x00, 0x01},
1929*4882a593Smuzhiyun 
1930*4882a593Smuzhiyun 	{25000000, 11289600, 2, 8, 7, 0x09, 0x7a, 0xff},
1931*4882a593Smuzhiyun 	{25000000, 12288000, 2, 8, 7, 0x24, 0x5c, 0xe2},
1932*4882a593Smuzhiyun 
1933*4882a593Smuzhiyun 	{26000000, 11289600, 2, 8, 6, 0x27, 0xdc, 0x2b},
1934*4882a593Smuzhiyun 	{26000000, 12288000, 2, 8, 7, 0x17, 0xa3, 0x2f},
1935*4882a593Smuzhiyun 
1936*4882a593Smuzhiyun 	{27000000, 11289600, 2, 8, 6, 0x1d, 0x08, 0xdc},
1937*4882a593Smuzhiyun 	{27000000, 12288000, 2, 8, 7, 0x0b, 0xda, 0xcc},
1938*4882a593Smuzhiyun 
1939*4882a593Smuzhiyun 	{30000000, 11289600, 2, 8, 6, 0x00, 0xe3, 0x77},
1940*4882a593Smuzhiyun 	{30000000, 12288000, 2, 8, 6, 0x17, 0x4a, 0x5f},
1941*4882a593Smuzhiyun };
1942*4882a593Smuzhiyun 
es8396_set_pll(struct snd_soc_dai * dai,int pll_id,int source,unsigned int freq_in,unsigned int freq_out)1943*4882a593Smuzhiyun static int es8396_set_pll(struct snd_soc_dai *dai, int pll_id,
1944*4882a593Smuzhiyun 			  int source, unsigned int freq_in,
1945*4882a593Smuzhiyun 			  unsigned int freq_out)
1946*4882a593Smuzhiyun {
1947*4882a593Smuzhiyun 	int i;
1948*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
1949*4882a593Smuzhiyun 	struct es8396_private *priv = snd_soc_component_get_drvdata(component);
1950*4882a593Smuzhiyun 	u16 reg;
1951*4882a593Smuzhiyun 	u8 N, K1, K2, K3, mclk_div, pll_div, tmp;
1952*4882a593Smuzhiyun 
1953*4882a593Smuzhiyun 	switch (pll_id) {
1954*4882a593Smuzhiyun 	case ES8396_PLL:
1955*4882a593Smuzhiyun 		break;
1956*4882a593Smuzhiyun 	default:
1957*4882a593Smuzhiyun 		return -EINVAL;
1958*4882a593Smuzhiyun 	}
1959*4882a593Smuzhiyun 	/* Disable PLL, power down and hold in reset state */
1960*4882a593Smuzhiyun 	snd_soc_component_write(component, ES8396_PLL_CTRL_1_REG02, 0x81);
1961*4882a593Smuzhiyun 
1962*4882a593Smuzhiyun 	if (!freq_in || !freq_out)
1963*4882a593Smuzhiyun 		return 0;
1964*4882a593Smuzhiyun 
1965*4882a593Smuzhiyun 	switch (source) {
1966*4882a593Smuzhiyun 	case ES8396_PLL_NO_SRC_0:
1967*4882a593Smuzhiyun 		/* Allow no source specification when stopping */
1968*4882a593Smuzhiyun 		if (freq_out)
1969*4882a593Smuzhiyun 			return -EINVAL;
1970*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_SRC_SEL_REG01);
1971*4882a593Smuzhiyun 		reg &= 0xF0;
1972*4882a593Smuzhiyun 		if (source == 0)
1973*4882a593Smuzhiyun 			reg |= 0x01;	/* clksrc2= 0, clksrc1 = 1 */
1974*4882a593Smuzhiyun 		else
1975*4882a593Smuzhiyun 			reg |= 0x09;	/* clksrc2= 1, clksrc1 = 1 */
1976*4882a593Smuzhiyun 
1977*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, reg);
1978*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
1979*4882a593Smuzhiyun 		reg |= 0x0F;
1980*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, reg);
1981*4882a593Smuzhiyun 		pr_debug("ES8396 PLL No Clock source\n");
1982*4882a593Smuzhiyun 		break;
1983*4882a593Smuzhiyun 	case ES8396_PLL_SRC_FRM_MCLK:
1984*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_SRC_SEL_REG01);
1985*4882a593Smuzhiyun 		reg &= 0xF3;
1986*4882a593Smuzhiyun 		reg |= 0x04;	/* clksrc2= mclk */
1987*4882a593Smuzhiyun 		/* use clk2 for pll clk source */
1988*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, reg);
1989*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
1990*4882a593Smuzhiyun 		reg |= 0x0F;
1991*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, reg);
1992*4882a593Smuzhiyun 		pr_debug("ES8396 PLL Clock Source from MCLK pin\n");
1993*4882a593Smuzhiyun 		break;
1994*4882a593Smuzhiyun 	case ES8396_PLL_SRC_FRM_BCLK:
1995*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_SRC_SEL_REG01);
1996*4882a593Smuzhiyun 		reg &= 0xF3;
1997*4882a593Smuzhiyun 		reg |= 0x0c;	/* clksrc2= bclk, */
1998*4882a593Smuzhiyun 		/* use clk2 for pll clk source */
1999*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, reg);
2000*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
2001*4882a593Smuzhiyun 		reg |= 0x0F;
2002*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, reg);
2003*4882a593Smuzhiyun 		pr_debug("ES8396 PLL Clock Source from BCLK signal\n");
2004*4882a593Smuzhiyun 		break;
2005*4882a593Smuzhiyun 	default:
2006*4882a593Smuzhiyun 		return -EINVAL;
2007*4882a593Smuzhiyun 	}
2008*4882a593Smuzhiyun 	/* get N & K */
2009*4882a593Smuzhiyun 	tmp = 0;
2010*4882a593Smuzhiyun 	if (source == ES8396_PLL_SRC_FRM_MCLK ||
2011*4882a593Smuzhiyun 	    source == ES8396_PLL_SRC_FRM_BCLK) {
2012*4882a593Smuzhiyun 		for (i = 0; i < ARRAY_SIZE(codec_pll_div); i++) {
2013*4882a593Smuzhiyun 			if (codec_pll_div[i].pll_in == freq_in &&
2014*4882a593Smuzhiyun 			    codec_pll_div[i].pll_out == freq_out) {
2015*4882a593Smuzhiyun 				/* PLL source from MCLK */
2016*4882a593Smuzhiyun 				mclk_div = codec_pll_div[i].mclkdiv;
2017*4882a593Smuzhiyun 				pll_div = codec_pll_div[i].plldiv;
2018*4882a593Smuzhiyun 				N = codec_pll_div[i].n;
2019*4882a593Smuzhiyun 				K3 = codec_pll_div[i].k1;
2020*4882a593Smuzhiyun 				K2 = codec_pll_div[i].k2;
2021*4882a593Smuzhiyun 				K1 = codec_pll_div[i].k3;
2022*4882a593Smuzhiyun 				tmp = 1;
2023*4882a593Smuzhiyun 				break;
2024*4882a593Smuzhiyun 			}
2025*4882a593Smuzhiyun 		}
2026*4882a593Smuzhiyun 
2027*4882a593Smuzhiyun 		if (tmp == 1) {
2028*4882a593Smuzhiyun 			pr_debug("MCLK DIV=%d PLL DIV=%d PLL CLOCK SOURCE=%dHz\n",
2029*4882a593Smuzhiyun 				 mclk_div, pll_div, freq_in);
2030*4882a593Smuzhiyun 			pr_debug("N=%d, K3=%d, K2=%d, K1=%d\n", N, K3, K2, K1);
2031*4882a593Smuzhiyun 
2032*4882a593Smuzhiyun 			/* set N & K */
2033*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_N_REG04, N);
2034*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K2_REG05, K3);
2035*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K1_REG06, K2);
2036*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K0_REG07, K1);
2037*4882a593Smuzhiyun 			if (mclk_div == 1)
2038*4882a593Smuzhiyun 				/* mclk div2 = 0 */
2039*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2040*4882a593Smuzhiyun 							      ES8396_CLK_SRC_SEL_REG01,
2041*4882a593Smuzhiyun 						    0x10, 0x00);
2042*4882a593Smuzhiyun 			else
2043*4882a593Smuzhiyun 				/* mclk div2 = 1 */
2044*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2045*4882a593Smuzhiyun 							      ES8396_CLK_SRC_SEL_REG01,
2046*4882a593Smuzhiyun 						    0x10, 0x10);
2047*4882a593Smuzhiyun 
2048*4882a593Smuzhiyun 			/* pll div 8 */
2049*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_PLL_CTRL_1_REG02,
2050*4882a593Smuzhiyun 						      0x3, 0x01);
2051*4882a593Smuzhiyun 
2052*4882a593Smuzhiyun 			/* configure the pll power voltage  */
2053*4882a593Smuzhiyun 			switch (priv->dvdd_pwr_vol) {
2054*4882a593Smuzhiyun 			case 0x18:
2055*4882a593Smuzhiyun 				/* dvdd=1.8v */
2056*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2057*4882a593Smuzhiyun 							      ES8396_PLL_CTRL_2_REG03,
2058*4882a593Smuzhiyun 						    0x0c, 0x00);
2059*4882a593Smuzhiyun 				break;
2060*4882a593Smuzhiyun 			case 0x25:
2061*4882a593Smuzhiyun 				/* dvdd=2.5v */
2062*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2063*4882a593Smuzhiyun 							      ES8396_PLL_CTRL_2_REG03,
2064*4882a593Smuzhiyun 						    0x0c, 0x04);
2065*4882a593Smuzhiyun 				break;
2066*4882a593Smuzhiyun 			case 0x33:
2067*4882a593Smuzhiyun 				/* dvdd=3.3v */
2068*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2069*4882a593Smuzhiyun 							      ES8396_PLL_CTRL_2_REG03,
2070*4882a593Smuzhiyun 						    0x0c, 0x08);
2071*4882a593Smuzhiyun 				break;
2072*4882a593Smuzhiyun 			default:
2073*4882a593Smuzhiyun 				/* dvdd=1.8v */
2074*4882a593Smuzhiyun 				snd_soc_component_update_bits(component,
2075*4882a593Smuzhiyun 							      ES8396_PLL_CTRL_2_REG03,
2076*4882a593Smuzhiyun 						    0x0c, 0x00);
2077*4882a593Smuzhiyun 				break;
2078*4882a593Smuzhiyun 			}
2079*4882a593Smuzhiyun 			/* enable PLL analog power up  */
2080*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_PLL_CTRL_1_REG02,
2081*4882a593Smuzhiyun 						      0x80, 0x00);
2082*4882a593Smuzhiyun 			/* pll digital on */
2083*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_PLL_CTRL_1_REG02,
2084*4882a593Smuzhiyun 						      0x40, 0x40);
2085*4882a593Smuzhiyun 			priv->mclk[dai->id - 1] = freq_out;
2086*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_N_REG04, 0x08);
2087*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K2_REG05, 0X1D);
2088*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K1_REG06, 0XC3);
2089*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_PLL_K0_REG07, 0XB8);
2090*4882a593Smuzhiyun 		} else {
2091*4882a593Smuzhiyun 			pr_debug("Can not find the correct clock frequency!!!!!\n");
2092*4882a593Smuzhiyun 		}
2093*4882a593Smuzhiyun 	}
2094*4882a593Smuzhiyun 	return 0;
2095*4882a593Smuzhiyun }
2096*4882a593Smuzhiyun 
2097*4882a593Smuzhiyun /*
2098*4882a593Smuzhiyun  * if PLL not be used, use internal clk1 for mclk,
2099*4882a593Smuzhiyun  * otherwise, use internal clk2 for PLL source.
2100*4882a593Smuzhiyun  */
es8396_set_dai_sysclk(struct snd_soc_dai * dai,int clk_id,unsigned int freq,int dir)2101*4882a593Smuzhiyun static int es8396_set_dai_sysclk(struct snd_soc_dai *dai,
2102*4882a593Smuzhiyun 				 int clk_id, unsigned int freq, int dir)
2103*4882a593Smuzhiyun {
2104*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2105*4882a593Smuzhiyun 	struct es8396_private *priv = snd_soc_component_get_drvdata(component);
2106*4882a593Smuzhiyun 	u8 reg;
2107*4882a593Smuzhiyun 
2108*4882a593Smuzhiyun 	switch (dai->id) {
2109*4882a593Smuzhiyun 	case ES8396_SDP1:
2110*4882a593Smuzhiyun 	case ES8396_SDP2:
2111*4882a593Smuzhiyun 	case ES8396_SDP3:
2112*4882a593Smuzhiyun 		break;
2113*4882a593Smuzhiyun 	default:
2114*4882a593Smuzhiyun 		return -EINVAL;
2115*4882a593Smuzhiyun 	}
2116*4882a593Smuzhiyun 	switch (clk_id) {
2117*4882a593Smuzhiyun 	/* the clock source form MCLK pin, don't use PLL */
2118*4882a593Smuzhiyun 	case ES8396_CLKID_MCLK:
2119*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_SRC_SEL_REG01);
2120*4882a593Smuzhiyun 		reg &= 0xFC;
2121*4882a593Smuzhiyun 		reg |= 0x00;	/* clksrc1= mclk */
2122*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, reg);
2123*4882a593Smuzhiyun 
2124*4882a593Smuzhiyun 		/* always use clk1 */
2125*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
2126*4882a593Smuzhiyun 		reg &= 0xf0;
2127*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, reg);
2128*4882a593Smuzhiyun 
2129*4882a593Smuzhiyun 		priv->sysclk[dai->id] = clk_id;
2130*4882a593Smuzhiyun 		priv->mclk[dai->id] = freq;
2131*4882a593Smuzhiyun 		if (freq > 19600000) {
2132*4882a593Smuzhiyun 			/* mclk div2 */
2133*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_CLK_SRC_SEL_REG01,
2134*4882a593Smuzhiyun 						      0x10, 0x10);
2135*4882a593Smuzhiyun 		}
2136*4882a593Smuzhiyun 		switch (dai->id) {
2137*4882a593Smuzhiyun 		case ES8396_SDP1:
2138*4882a593Smuzhiyun 			/* bclkdiv m1 use clk1 */
2139*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M1_REG0E,
2140*4882a593Smuzhiyun 						      0x20, 0x00);
2141*4882a593Smuzhiyun 			/* lrckdiv m3 use clk1 */
2142*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M3_REG10,
2143*4882a593Smuzhiyun 						      0x20, 0x00);
2144*4882a593Smuzhiyun 			break;
2145*4882a593Smuzhiyun 		case ES8396_SDP2:
2146*4882a593Smuzhiyun 		case ES8396_SDP3:
2147*4882a593Smuzhiyun 			/* bclkdiv m1 use clk1 */
2148*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M2_REG0F,
2149*4882a593Smuzhiyun 						      0x20, 0x00);
2150*4882a593Smuzhiyun 			/* lrckdiv m4 use clk1 */
2151*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M4_REG11,
2152*4882a593Smuzhiyun 						      0x20, 0x00);
2153*4882a593Smuzhiyun 			break;
2154*4882a593Smuzhiyun 		default:
2155*4882a593Smuzhiyun 			break;
2156*4882a593Smuzhiyun 		}
2157*4882a593Smuzhiyun 		pr_debug("ES8396 using MCLK as SYSCLK at %uHz\n", freq);
2158*4882a593Smuzhiyun 		break;
2159*4882a593Smuzhiyun 	/* the clock source form internal BCLK signal, don't use PLL */
2160*4882a593Smuzhiyun 	case ES8396_CLKID_BCLK:
2161*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_SRC_SEL_REG01);
2162*4882a593Smuzhiyun 		reg &= 0xFC;
2163*4882a593Smuzhiyun 		reg |= 0x03;	/* clksrc1= bclk */
2164*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, reg);
2165*4882a593Smuzhiyun 		/* always use clk1 */
2166*4882a593Smuzhiyun 		reg = snd_soc_component_read(component, ES8396_CLK_CTRL_REG08);
2167*4882a593Smuzhiyun 		reg &= 0xf0;
2168*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, reg);
2169*4882a593Smuzhiyun 
2170*4882a593Smuzhiyun 		priv->sysclk[dai->id] = clk_id;
2171*4882a593Smuzhiyun 		priv->mclk[dai->id] = freq;
2172*4882a593Smuzhiyun 		if (freq > 19600000) {
2173*4882a593Smuzhiyun 			/* mclk div2 */
2174*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_CLK_SRC_SEL_REG01,
2175*4882a593Smuzhiyun 						      0x10, 0x10);
2176*4882a593Smuzhiyun 		}
2177*4882a593Smuzhiyun 		switch (dai->id) {
2178*4882a593Smuzhiyun 		case ES8396_SDP1:
2179*4882a593Smuzhiyun 			/* bclkdiv m1 use clk1 */
2180*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M1_REG0E,
2181*4882a593Smuzhiyun 						      0x20, 0x00);
2182*4882a593Smuzhiyun 			/* lrckdiv m3 use clk1 */
2183*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M3_REG10,
2184*4882a593Smuzhiyun 						      0x20, 0x00);
2185*4882a593Smuzhiyun 			break;
2186*4882a593Smuzhiyun 		case ES8396_SDP2:
2187*4882a593Smuzhiyun 		case ES8396_SDP3:
2188*4882a593Smuzhiyun 			/* bclkdiv m1 use clk1 */
2189*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M2_REG0F,
2190*4882a593Smuzhiyun 						      0x20, 0x00);
2191*4882a593Smuzhiyun 			/* lrckdiv m4 use clk1 */
2192*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M4_REG11,
2193*4882a593Smuzhiyun 						      0x20, 0x00);
2194*4882a593Smuzhiyun 			break;
2195*4882a593Smuzhiyun 		default:
2196*4882a593Smuzhiyun 			break;
2197*4882a593Smuzhiyun 		}
2198*4882a593Smuzhiyun 		pr_debug("ES8396 using BCLK as SYSCLK at %uHz\n", freq);
2199*4882a593Smuzhiyun 		break;
2200*4882a593Smuzhiyun 	case ES8396_CLKID_PLLO:
2201*4882a593Smuzhiyun 		priv->sysclk[dai->id] = ES8396_CLKID_PLLO;
2202*4882a593Smuzhiyun 		switch (dai->id) {
2203*4882a593Smuzhiyun 		case ES8396_SDP1:
2204*4882a593Smuzhiyun 			/* bclkdiv m1 use clk1 */
2205*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M1_REG0E,
2206*4882a593Smuzhiyun 						      0x20, 0x00);
2207*4882a593Smuzhiyun 			/* lrckdiv m3 use clk1 */
2208*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M3_REG10,
2209*4882a593Smuzhiyun 						      0x20, 0x00);
2210*4882a593Smuzhiyun 			break;
2211*4882a593Smuzhiyun 		case ES8396_SDP2:
2212*4882a593Smuzhiyun 			/* bclkdiv m1 use clk2 */
2213*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M1_REG0E,
2214*4882a593Smuzhiyun 						      0x20, 0x20);
2215*4882a593Smuzhiyun 			/* lrckdiv m3 use clk2 */
2216*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M3_REG10,
2217*4882a593Smuzhiyun 						      0x20, 0x20);
2218*4882a593Smuzhiyun 			break;
2219*4882a593Smuzhiyun 		case ES8396_SDP3:
2220*4882a593Smuzhiyun 			/* bclkdiv m1 use clk2 */
2221*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_BCLK_DIV_M2_REG0F,
2222*4882a593Smuzhiyun 						      0x20, 0x20);
2223*4882a593Smuzhiyun 			/* lrckdiv m4 use clk2 */
2224*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_LRCK_DIV_M4_REG11,
2225*4882a593Smuzhiyun 						      0x20, 0x20);
2226*4882a593Smuzhiyun 			break;
2227*4882a593Smuzhiyun 		default:
2228*4882a593Smuzhiyun 			break;
2229*4882a593Smuzhiyun 		}
2230*4882a593Smuzhiyun 		pr_debug("ES8396 using PLL Output as SYSCLK\n");
2231*4882a593Smuzhiyun 		break;
2232*4882a593Smuzhiyun 	default:
2233*4882a593Smuzhiyun 		pr_err("ES8396 System clock error\n");
2234*4882a593Smuzhiyun 		return -EINVAL;
2235*4882a593Smuzhiyun 	}
2236*4882a593Smuzhiyun 	return 0;
2237*4882a593Smuzhiyun }
2238*4882a593Smuzhiyun 
2239*4882a593Smuzhiyun struct es8396_mclk_div {
2240*4882a593Smuzhiyun 	u32 mclk;
2241*4882a593Smuzhiyun 	u32 srate;
2242*4882a593Smuzhiyun 	u8 lrcdiv;
2243*4882a593Smuzhiyun 	u8 bclkdiv;
2244*4882a593Smuzhiyun };
2245*4882a593Smuzhiyun 
2246*4882a593Smuzhiyun static struct es8396_mclk_div es8396_mclk_coeffs[] = {
2247*4882a593Smuzhiyun 	/* MCLK, Sample Rate, lrckdiv, bclkdiv */
2248*4882a593Smuzhiyun 	{5644800, 11025, 0x04, 0x08},
2249*4882a593Smuzhiyun 	{5644800, 22050, 0x02, 0x04},
2250*4882a593Smuzhiyun 	{5644800, 44100, 0x00, 0x02},
2251*4882a593Smuzhiyun 
2252*4882a593Smuzhiyun 	{6000000, 8000, 0x17, 0x0f},
2253*4882a593Smuzhiyun 	{6000000, 11025, 0x16, 0x08},
2254*4882a593Smuzhiyun 	{6000000, 12000, 0x15, 0x0a},
2255*4882a593Smuzhiyun 	{6000000, 16000, 0x14, 0x05},
2256*4882a593Smuzhiyun 	{6000000, 22050, 0x13, 0x04},
2257*4882a593Smuzhiyun 	{6000000, 24000, 0x12, 0x05},
2258*4882a593Smuzhiyun 	{6000000, 44100, 0x11, 0x02},
2259*4882a593Smuzhiyun 	{6000000, 48000, 0x10, 0x01},
2260*4882a593Smuzhiyun 
2261*4882a593Smuzhiyun 	{6144000, 8000, 0x06, 0x0c},
2262*4882a593Smuzhiyun 	{6144000, 12000, 0x04, 0x08},
2263*4882a593Smuzhiyun 	{6144000, 16000, 0x03, 0x06},
2264*4882a593Smuzhiyun 	{6144000, 24000, 0x02, 0x04},
2265*4882a593Smuzhiyun 	{6144000, 32000, 0x01, 0x03},
2266*4882a593Smuzhiyun 	{6144000, 48000, 0x00, 0x02},
2267*4882a593Smuzhiyun 
2268*4882a593Smuzhiyun 	{8192000, 8000, 0x07, 0x10},
2269*4882a593Smuzhiyun 	{8192000, 16000, 0x04, 0x08},
2270*4882a593Smuzhiyun 	{8192000, 32000, 0x02, 0x04},
2271*4882a593Smuzhiyun 
2272*4882a593Smuzhiyun 	{11289600, 11025, 0x07, 0x10},
2273*4882a593Smuzhiyun 	{11289600, 22050, 0x04, 0x08},
2274*4882a593Smuzhiyun 	{11289600, 44100, 0x02, 0x04},
2275*4882a593Smuzhiyun 
2276*4882a593Smuzhiyun 	{12000000, 8000, 0x1b, 0x17},
2277*4882a593Smuzhiyun 	{12000000, 11025, 0x19, 0x11},
2278*4882a593Smuzhiyun 	{12000000, 12000, 0x18, 0x13},
2279*4882a593Smuzhiyun 	{12000000, 16000, 0x17, 0x0f},
2280*4882a593Smuzhiyun 	{12000000, 22050, 0x16, 0x08},
2281*4882a593Smuzhiyun 	{12000000, 24000, 0x15, 0x0a},
2282*4882a593Smuzhiyun 	{12000000, 32000, 0x14, 0x05},
2283*4882a593Smuzhiyun 	{12000000, 44100, 0x13, 0x04},
2284*4882a593Smuzhiyun 	{12000000, 48000, 0x12, 0x05},
2285*4882a593Smuzhiyun 
2286*4882a593Smuzhiyun 	{12288000, 8000, 0x0a, 0x15},
2287*4882a593Smuzhiyun 	{12288000, 12000, 0x07, 0x10},
2288*4882a593Smuzhiyun 	{12288000, 16000, 0x06, 0x0c},
2289*4882a593Smuzhiyun 	{12288000, 24000, 0x04, 0x08},
2290*4882a593Smuzhiyun 	{12288000, 32000, 0x03, 0x06},
2291*4882a593Smuzhiyun 	{12288000, 48000, 0x02, 0x04},
2292*4882a593Smuzhiyun };
2293*4882a593Smuzhiyun 
es8396_set_dai_fmt(struct snd_soc_dai * codec_dai,unsigned int fmt)2294*4882a593Smuzhiyun static int es8396_set_dai_fmt(struct snd_soc_dai *codec_dai, unsigned int fmt)
2295*4882a593Smuzhiyun {
2296*4882a593Smuzhiyun 	struct snd_soc_component *component = codec_dai->component;
2297*4882a593Smuzhiyun 	struct es8396_private *priv = snd_soc_component_get_drvdata(component);
2298*4882a593Smuzhiyun 	u8 id = codec_dai->id;
2299*4882a593Smuzhiyun 	unsigned int inv, format;
2300*4882a593Smuzhiyun 	u8 spc, mmcc;
2301*4882a593Smuzhiyun 
2302*4882a593Smuzhiyun 	switch (id) {
2303*4882a593Smuzhiyun 	case ES8396_SDP1:
2304*4882a593Smuzhiyun 		spc = snd_soc_component_read(component, ES8396_SDP1_IN_FMT_REG1F) & 0x3f;
2305*4882a593Smuzhiyun 		mmcc = snd_soc_component_read(component, ES8396_SDP_1_MS_REG12);
2306*4882a593Smuzhiyun 		break;
2307*4882a593Smuzhiyun 	case ES8396_SDP2:
2308*4882a593Smuzhiyun 		spc = snd_soc_component_read(component, ES8396_SDP2_IN_FMT_REG22) & 0x3f;
2309*4882a593Smuzhiyun 		mmcc = snd_soc_component_read(component, ES8396_SDP_2_MS_REG13);
2310*4882a593Smuzhiyun 		break;
2311*4882a593Smuzhiyun 	case ES8396_SDP3:
2312*4882a593Smuzhiyun 		spc = snd_soc_component_read(component, ES8396_SDP3_IN_FMT_REG24) & 0x3f;
2313*4882a593Smuzhiyun 		mmcc = snd_soc_component_read(component, ES8396_SDP_3_MS_REG14);
2314*4882a593Smuzhiyun 		break;
2315*4882a593Smuzhiyun 	default:
2316*4882a593Smuzhiyun 		return -EINVAL;
2317*4882a593Smuzhiyun 	}
2318*4882a593Smuzhiyun 
2319*4882a593Smuzhiyun 	switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
2320*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_CBM_CFM:
2321*4882a593Smuzhiyun 		mmcc &= ~MS_MASTER;
2322*4882a593Smuzhiyun 		mmcc |= 0x24;
2323*4882a593Smuzhiyun 		if (id == ES8396_SDP1) {
2324*4882a593Smuzhiyun 			mmcc &= 0xe4;	/* select bclkm1,lrckm3 */
2325*4882a593Smuzhiyun 		} else {
2326*4882a593Smuzhiyun 			mmcc &= 0xe4;	/* select bclkm2,lrckm4 */
2327*4882a593Smuzhiyun 			mmcc |= 0x09;
2328*4882a593Smuzhiyun 		}
2329*4882a593Smuzhiyun 		break;
2330*4882a593Smuzhiyun 
2331*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_CBS_CFS:
2332*4882a593Smuzhiyun 		mmcc &= ~MS_MASTER;
2333*4882a593Smuzhiyun 		break;
2334*4882a593Smuzhiyun 
2335*4882a593Smuzhiyun 	default:
2336*4882a593Smuzhiyun 		return -EINVAL;
2337*4882a593Smuzhiyun 	}
2338*4882a593Smuzhiyun 
2339*4882a593Smuzhiyun 	format = (fmt & SND_SOC_DAIFMT_FORMAT_MASK);
2340*4882a593Smuzhiyun 	inv = (fmt & SND_SOC_DAIFMT_INV_MASK);
2341*4882a593Smuzhiyun 
2342*4882a593Smuzhiyun 	switch (format) {
2343*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_I2S:
2344*4882a593Smuzhiyun 		spc &= 0xC7;
2345*4882a593Smuzhiyun 		/* lrck polarity normal, TO CHECK THE L&R Inverted for i-net */
2346*4882a593Smuzhiyun 		spc |= 0x00;
2347*4882a593Smuzhiyun 		break;
2348*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_LEFT_J:
2349*4882a593Smuzhiyun 		spc &= 0xC7;
2350*4882a593Smuzhiyun 		spc |= 0x18;	/* lrck polarity normal */
2351*4882a593Smuzhiyun 		break;
2352*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_RIGHT_J:
2353*4882a593Smuzhiyun 		if (id == ES8396_SDP1) {
2354*4882a593Smuzhiyun 			spc &= 0xC7;
2355*4882a593Smuzhiyun 			spc |= 0x28;	/* lrck polarity normal */
2356*4882a593Smuzhiyun 		} else {
2357*4882a593Smuzhiyun 			pr_err("ES8396 SDP2&SDP3 don't Support Right Justified\n");
2358*4882a593Smuzhiyun 			return -EINVAL;
2359*4882a593Smuzhiyun 		}
2360*4882a593Smuzhiyun 		break;
2361*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_DSP_A:
2362*4882a593Smuzhiyun 	case SND_SOC_DAIFMT_DSP_B:
2363*4882a593Smuzhiyun 		spc &= 0xC7;
2364*4882a593Smuzhiyun 
2365*4882a593Smuzhiyun 		if (format == SND_SOC_DAIFMT_DSP_A)
2366*4882a593Smuzhiyun 			spc |= 0x30;
2367*4882a593Smuzhiyun 		else
2368*4882a593Smuzhiyun 			spc |= 0x38;
2369*4882a593Smuzhiyun 		break;
2370*4882a593Smuzhiyun 	default:
2371*4882a593Smuzhiyun 		return -EINVAL;
2372*4882a593Smuzhiyun 	}
2373*4882a593Smuzhiyun 
2374*4882a593Smuzhiyun 	snd_soc_component_write(component, ES8396_SDP1_IN_FMT_REG1F, 00);
2375*4882a593Smuzhiyun 	pr_debug("es8396_set_dai_fmt-->\n");
2376*4882a593Smuzhiyun 
2377*4882a593Smuzhiyun 	priv->config[id].spc = spc;
2378*4882a593Smuzhiyun 	priv->config[id].mmcc = mmcc;
2379*4882a593Smuzhiyun 
2380*4882a593Smuzhiyun 	return 0;
2381*4882a593Smuzhiyun }
2382*4882a593Smuzhiyun 
es8396_pcm_hw_params(struct snd_pcm_substream * substream,struct snd_pcm_hw_params * params,struct snd_soc_dai * dai)2383*4882a593Smuzhiyun static int es8396_pcm_hw_params(struct snd_pcm_substream *substream,
2384*4882a593Smuzhiyun 				struct snd_pcm_hw_params *params,
2385*4882a593Smuzhiyun 				struct snd_soc_dai *dai)
2386*4882a593Smuzhiyun {
2387*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2388*4882a593Smuzhiyun 	struct es8396_private *priv = snd_soc_component_get_drvdata(component);
2389*4882a593Smuzhiyun 	int id = dai->id;
2390*4882a593Smuzhiyun 	int mclk_coeff = 0;
2391*4882a593Smuzhiyun 	int srate = params_rate(params);
2392*4882a593Smuzhiyun 	u8 bdiv, lrdiv;
2393*4882a593Smuzhiyun 
2394*4882a593Smuzhiyun 	pr_debug("DAI[%d]: MCLK= %u, srate= %u, lrckdiv= %x, bclkdiv= %x\n",
2395*4882a593Smuzhiyun 		 id, priv->mclk[0], srate,
2396*4882a593Smuzhiyun 		 es8396_mclk_coeffs[mclk_coeff].lrcdiv,
2397*4882a593Smuzhiyun 		 es8396_mclk_coeffs[mclk_coeff].bclkdiv);
2398*4882a593Smuzhiyun 
2399*4882a593Smuzhiyun 	switch (id) {
2400*4882a593Smuzhiyun 	case ES8396_SDP1:
2401*4882a593Smuzhiyun 		bdiv = snd_soc_component_read(component, ES8396_BCLK_DIV_M2_REG0F);
2402*4882a593Smuzhiyun 		bdiv &= 0xe0;
2403*4882a593Smuzhiyun 		bdiv |= es8396_mclk_coeffs[mclk_coeff].bclkdiv;
2404*4882a593Smuzhiyun 		lrdiv = snd_soc_component_read(component, ES8396_LRCK_DIV_M4_REG11);
2405*4882a593Smuzhiyun 		lrdiv &= 0xe0;
2406*4882a593Smuzhiyun 		lrdiv |= 0x22;	/* es8396_mclk_coeffs[mclk_coeff].lrcdiv; */
2407*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_BCLK_DIV_M2_REG0F, bdiv);
2408*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_LRCK_DIV_M4_REG11, lrdiv);
2409*4882a593Smuzhiyun 		priv->config[id].srate = srate;
2410*4882a593Smuzhiyun 		priv->config[id].lrcdiv = lrdiv;
2411*4882a593Smuzhiyun 		priv->config[id].sclkdiv = bdiv;
2412*4882a593Smuzhiyun 		break;
2413*4882a593Smuzhiyun 	case ES8396_SDP2:
2414*4882a593Smuzhiyun 	case ES8396_SDP3:
2415*4882a593Smuzhiyun 		bdiv = snd_soc_component_read(component, ES8396_BCLK_DIV_M1_REG0E);
2416*4882a593Smuzhiyun 		bdiv &= 0xe0;
2417*4882a593Smuzhiyun 		bdiv |= es8396_mclk_coeffs[mclk_coeff].bclkdiv;
2418*4882a593Smuzhiyun 		lrdiv = snd_soc_component_read(component, ES8396_LRCK_DIV_M3_REG10);
2419*4882a593Smuzhiyun 		lrdiv &= 0xe0;
2420*4882a593Smuzhiyun 		lrdiv |= es8396_mclk_coeffs[mclk_coeff].lrcdiv;
2421*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_BCLK_DIV_M1_REG0E, bdiv);
2422*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_LRCK_DIV_M3_REG10, lrdiv);
2423*4882a593Smuzhiyun 		priv->config[id].srate = srate;
2424*4882a593Smuzhiyun 		priv->config[id].lrcdiv = lrdiv;
2425*4882a593Smuzhiyun 		priv->config[id].sclkdiv = bdiv;
2426*4882a593Smuzhiyun 		break;
2427*4882a593Smuzhiyun 	default:
2428*4882a593Smuzhiyun 		return -EINVAL;
2429*4882a593Smuzhiyun 	}
2430*4882a593Smuzhiyun 
2431*4882a593Smuzhiyun 	return 0;
2432*4882a593Smuzhiyun }
2433*4882a593Smuzhiyun 
es8396_set_bias_level(struct snd_soc_component * component,enum snd_soc_bias_level level)2434*4882a593Smuzhiyun static int es8396_set_bias_level(struct snd_soc_component *component,
2435*4882a593Smuzhiyun 				 enum snd_soc_bias_level level)
2436*4882a593Smuzhiyun {
2437*4882a593Smuzhiyun 	u8 value;
2438*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2439*4882a593Smuzhiyun 
2440*4882a593Smuzhiyun 	switch (level) {
2441*4882a593Smuzhiyun 	case SND_SOC_BIAS_ON:
2442*4882a593Smuzhiyun 		/*
2443*4882a593Smuzhiyun 		 * dac csm startup, dac digital still on
2444*4882a593Smuzhiyun 		 * snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0xFF, 0x00);
2445*4882a593Smuzhiyun 		 * dac analog power on
2446*4882a593Smuzhiyun 		 * snd_soc_component_update_bits(component, ES8396_DAC_REF_PWR_CTRL_REG6E,
2447*4882a593Smuzhiyun 		 * 0xff, 0x00);
2448*4882a593Smuzhiyun 		 */
2449*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x4E, 0x80);
2450*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x4F, 0x81);
2451*4882a593Smuzhiyun 		break;
2452*4882a593Smuzhiyun 
2453*4882a593Smuzhiyun 	case SND_SOC_BIAS_PREPARE:
2454*4882a593Smuzhiyun 		break;
2455*4882a593Smuzhiyun 
2456*4882a593Smuzhiyun 	case SND_SOC_BIAS_STANDBY:
2457*4882a593Smuzhiyun 		if (es8396->aif1_select == 0 && es8396->aif2_select == 0) {
2458*4882a593Smuzhiyun 			if (snd_soc_component_get_bias_level(component) == SND_SOC_BIAS_OFF) {
2459*4882a593Smuzhiyun 				snd_soc_component_write(component, ES8396_SYS_VMID_REF_REG71,
2460*4882a593Smuzhiyun 							0xFF);
2461*4882a593Smuzhiyun 				if (es8396_valid_analdo(es8396->ana_ldo_lvl)) {
2462*4882a593Smuzhiyun 					value = es8396->ana_ldo_lvl;
2463*4882a593Smuzhiyun 					value &= 0x07;
2464*4882a593Smuzhiyun 					snd_soc_component_write(component, 0x70, value);
2465*4882a593Smuzhiyun 				}
2466*4882a593Smuzhiyun 			}
2467*4882a593Smuzhiyun 		}
2468*4882a593Smuzhiyun 		/*
2469*4882a593Smuzhiyun 		 * dac csm startup, dac digital still stop
2470*4882a593Smuzhiyun 		 * snd_soc_component_update_bits(component, ES8396_DAC_CSM_REG66, 0xFF, 0x04);
2471*4882a593Smuzhiyun 		 * adc csm startup, adc digital still stop
2472*4882a593Smuzhiyun 		 * snd_soc_component_update_bits(component, ES8396_ADC_CSM_REG53, 0xFF, 0x00);
2473*4882a593Smuzhiyun 		 */
2474*4882a593Smuzhiyun 		break;
2475*4882a593Smuzhiyun 
2476*4882a593Smuzhiyun 	case SND_SOC_BIAS_OFF:
2477*4882a593Smuzhiyun 		break;
2478*4882a593Smuzhiyun 	}
2479*4882a593Smuzhiyun 
2480*4882a593Smuzhiyun 	return 0;
2481*4882a593Smuzhiyun }
2482*4882a593Smuzhiyun 
es8396_set_tristate(struct snd_soc_dai * dai,int tristate)2483*4882a593Smuzhiyun static int es8396_set_tristate(struct snd_soc_dai *dai, int tristate)
2484*4882a593Smuzhiyun {
2485*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2486*4882a593Smuzhiyun 	int id = dai->id;
2487*4882a593Smuzhiyun 
2488*4882a593Smuzhiyun 	pr_debug("es8396_set_tristate\n");
2489*4882a593Smuzhiyun 	pr_debug("ES8396 SDP NUM = %d\n", id);
2490*4882a593Smuzhiyun 	switch (id) {
2491*4882a593Smuzhiyun 	case ES8396_SDP1:
2492*4882a593Smuzhiyun 		return snd_soc_component_update_bits(component, ES8396_SDP1_DGAIN_TDM_REG21,
2493*4882a593Smuzhiyun 						     0x0a, 0x0a);
2494*4882a593Smuzhiyun 	case ES8396_SDP2:
2495*4882a593Smuzhiyun 	case ES8396_SDP3:
2496*4882a593Smuzhiyun 		pr_err("SDP NUM = %d, Can not support tristate\n", id);
2497*4882a593Smuzhiyun 		return -EINVAL;
2498*4882a593Smuzhiyun 	default:
2499*4882a593Smuzhiyun 		return -EINVAL;
2500*4882a593Smuzhiyun 	}
2501*4882a593Smuzhiyun }
2502*4882a593Smuzhiyun 
es8396_pcm_startup(struct snd_pcm_substream * substream,struct snd_soc_dai * dai)2503*4882a593Smuzhiyun static int es8396_pcm_startup(struct snd_pcm_substream *substream,
2504*4882a593Smuzhiyun 			      struct snd_soc_dai *dai)
2505*4882a593Smuzhiyun {
2506*4882a593Smuzhiyun 	bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
2507*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2508*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2509*4882a593Smuzhiyun 	int ret;
2510*4882a593Smuzhiyun 	int regv;
2511*4882a593Smuzhiyun 	int i;
2512*4882a593Smuzhiyun 
2513*4882a593Smuzhiyun 	pr_debug(">>>>>>>>es8396_pcm_startup\n");
2514*4882a593Smuzhiyun 	ret = snd_soc_component_read(component, ES8396_ADC_CSM_REG53);
2515*4882a593Smuzhiyun 	pr_debug("ES8396_ADC_CSM_REG53===0x%x\n", ret);
2516*4882a593Smuzhiyun 	/*
2517*4882a593Smuzhiyun 	 * set the clock source to MCLK pin
2518*4882a593Smuzhiyun 	 * set divider for music playback
2519*4882a593Smuzhiyun 	 * set DAC source from SDP1 in
2520*4882a593Smuzhiyun 	 */
2521*4882a593Smuzhiyun 	if ((es8396->aif2_select & 0x01) == 0) {
2522*4882a593Smuzhiyun 		pr_debug(">>>>>>>>es8396_pcm_startup, only power on sdp1 for music\n");
2523*4882a593Smuzhiyun 		/* if don't have voice requirement */
2524*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x1A, 0x00);
2525*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x8, 0x10);
2526*4882a593Smuzhiyun 		snd_soc_component_write(component, 0xd, 0x00);
2527*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x9, 0x04);
2528*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x69, 0x00);
2529*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x67, 0x00);
2530*4882a593Smuzhiyun 	} else {
2531*4882a593Smuzhiyun 		pr_debug(">>>>>>>>es8396_pcm_startup, already power on sdp2 for voice\n");
2532*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x18, 0x00);	/* set eq source */
2533*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x19, 0x51);	/* set eq source */
2534*4882a593Smuzhiyun 		/* if have voice requirement */
2535*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x1A, 0x40);
2536*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x8, 0x10);
2537*4882a593Smuzhiyun 		snd_soc_component_write(component, 0xd, 0x00);
2538*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x9, 0x04);
2539*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x67, 0x0c);
2540*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x69, 0x04);
2541*4882a593Smuzhiyun 	}
2542*4882a593Smuzhiyun 
2543*4882a593Smuzhiyun 	if (playback) {
2544*4882a593Smuzhiyun 		pr_debug(">>>>>>>>>>>es8396_pcm_startup playback\n");
2545*4882a593Smuzhiyun 		es8396->aif1_select |= 0x01;
2546*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x66, 0x01);
2547*4882a593Smuzhiyun 		for (i = 0; i < 120; i = i + 2) {
2548*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x6A, i + 1);
2549*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x6B, i + 1);
2550*4882a593Smuzhiyun 			usleep_range(100, 200);
2551*4882a593Smuzhiyun 		}
2552*4882a593Smuzhiyun 		if (es8396->calibrate == 0) {
2553*4882a593Smuzhiyun 			pr_debug("Enter into %s  %d\n", __func__, __LINE__);
2554*4882a593Smuzhiyun 			es8396->calibrate = true;
2555*4882a593Smuzhiyun 		}
2556*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->pcm_pop_work,
2557*4882a593Smuzhiyun 				      msecs_to_jiffies(10));
2558*4882a593Smuzhiyun 
2559*4882a593Smuzhiyun 	} else {
2560*4882a593Smuzhiyun 		pr_debug(">>>>>>>>>>>es8396_pcm_startup capture\n");
2561*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP1_OUT_FMT_REG20, 0x40,
2562*4882a593Smuzhiyun 					      0x40);
2563*4882a593Smuzhiyun 		/* set adc alc */
2564*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_1_REG58, 0xC6);
2565*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_2_REG59, 0x12);
2566*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_4_REG5B, 0x04);
2567*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_5_REG5C, 0xC8);
2568*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_6_REG5D, 0x11);
2569*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x0);
2570*4882a593Smuzhiyun 		/* Enable MIC BOOST */
2571*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_MIC_IBIAS_EN_REG75, 0x02);
2572*4882a593Smuzhiyun 
2573*4882a593Smuzhiyun 		/* axMixer Gain boost */
2574*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_AX_MIXER_BOOST_REG2F);
2575*4882a593Smuzhiyun 		regv |= 0x88;
2576*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_BOOST_REG2F, regv);
2577*4882a593Smuzhiyun 		/* axmixer vol = +12db */
2578*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_VOL_REG30, 0xaa);
2579*4882a593Smuzhiyun 		/* axmixer high driver capacility */
2580*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_REF_LP_REG31, 0x02);
2581*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x33, 0);
2582*4882a593Smuzhiyun 		/* MNMixer Gain boost */
2583*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_MN_MIXER_BOOST_REG37);
2584*4882a593Smuzhiyun 		regv |= 0x88;
2585*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_BOOST_REG37, regv);
2586*4882a593Smuzhiyun 		/* mnmixer vol = +12db */
2587*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_VOL_REG38, 0x44);
2588*4882a593Smuzhiyun 		/* mnmixer high driver capacility */
2589*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_REF_LP_REG39, 0x02);
2590*4882a593Smuzhiyun 
2591*4882a593Smuzhiyun 		/* ADC STM and Digital Startup, ADC DS Mode */
2592*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x00);
2593*4882a593Smuzhiyun 		/* force adc stm to normal */
2594*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x40);
2595*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x0);
2596*4882a593Smuzhiyun 		/* ADC Volume =0db */
2597*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_LADC_VOL_REG56, 0x0);
2598*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_RADC_VOL_REG57, 0x0);
2599*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CLK_DIV_REG09, 0x04);
2600*4882a593Smuzhiyun 		es8396->aif1_select |= 0x02;
2601*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->adc_depop_work,
2602*4882a593Smuzhiyun 				      msecs_to_jiffies(150));
2603*4882a593Smuzhiyun 	}
2604*4882a593Smuzhiyun 	return 0;
2605*4882a593Smuzhiyun }
2606*4882a593Smuzhiyun 
es8396_pcm_shutdown(struct snd_pcm_substream * substream,struct snd_soc_dai * dai)2607*4882a593Smuzhiyun static void es8396_pcm_shutdown(struct snd_pcm_substream *substream,
2608*4882a593Smuzhiyun 				struct snd_soc_dai *dai)
2609*4882a593Smuzhiyun {
2610*4882a593Smuzhiyun 	bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
2611*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2612*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2613*4882a593Smuzhiyun 
2614*4882a593Smuzhiyun 	pr_debug(">>>>>>>>es8396_pcm_shutdown\n");
2615*4882a593Smuzhiyun 
2616*4882a593Smuzhiyun 	/*
2617*4882a593Smuzhiyun 	 * mute SDP1 in and mute SDP1 out
2618*4882a593Smuzhiyun 	 */
2619*4882a593Smuzhiyun 	if (playback) {
2620*4882a593Smuzhiyun 		pr_debug(">>>>>>>>es8396_pcm_shutdown, playback\n");
2621*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->pcm_shutdown_depop_work,
2622*4882a593Smuzhiyun 				      msecs_to_jiffies(20));
2623*4882a593Smuzhiyun 	} else {
2624*4882a593Smuzhiyun 		pr_debug(">>>>>>>>es8396_pcm_shutdown, capture\n");
2625*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP1_OUT_FMT_REG20, 0x40,
2626*4882a593Smuzhiyun 					      0x40);
2627*4882a593Smuzhiyun 		es8396->aif1_select &= 0xfd;
2628*4882a593Smuzhiyun 	}
2629*4882a593Smuzhiyun }
2630*4882a593Smuzhiyun 
es8396_voice_startup(struct snd_pcm_substream * substream,struct snd_soc_dai * dai)2631*4882a593Smuzhiyun static int es8396_voice_startup(struct snd_pcm_substream *substream,
2632*4882a593Smuzhiyun 				struct snd_soc_dai *dai)
2633*4882a593Smuzhiyun {
2634*4882a593Smuzhiyun 	unsigned int index;
2635*4882a593Smuzhiyun 	bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
2636*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2637*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2638*4882a593Smuzhiyun 	int regv;
2639*4882a593Smuzhiyun 	int i;
2640*4882a593Smuzhiyun 
2641*4882a593Smuzhiyun 	pr_debug("****************es8396_voice_startup\n");
2642*4882a593Smuzhiyun 
2643*4882a593Smuzhiyun 	if (playback) {
2644*4882a593Smuzhiyun 		pr_debug("****************es8396_voice_startup, playback\n");
2645*4882a593Smuzhiyun 		es8396->aif2_select |= 0x01;
2646*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x4e, 0x84);
2647*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x4f, 0x85);
2648*4882a593Smuzhiyun 
2649*4882a593Smuzhiyun 		for (i = 0; i < 120; i = i + 2) {
2650*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x6A, i + 1);
2651*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x6B, i + 1);
2652*4882a593Smuzhiyun 			usleep_range(100, 200);
2653*4882a593Smuzhiyun 		}
2654*4882a593Smuzhiyun 
2655*4882a593Smuzhiyun 		/* mute dac */
2656*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x66, 0x01);
2657*4882a593Smuzhiyun 		/* DSP-B, 1st SCLK after LRCK edge, I2S2 SDPIN */
2658*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP2_IN_FMT_REG22,
2659*4882a593Smuzhiyun 					      0x7F, 0x13);
2660*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x18, 0x51);	/* set eq source */
2661*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x19, 0x51);	/* set eq source */
2662*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x8, 0x10);
2663*4882a593Smuzhiyun 		snd_soc_component_write(component, 0xd, 0x00);
2664*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x9, 0x04);
2665*4882a593Smuzhiyun 		if ((es8396->aif1_select & 0x01) == 0) {
2666*4882a593Smuzhiyun 			/* if only voice */
2667*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x67, 0x0c);
2668*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x69, 0x04);
2669*4882a593Smuzhiyun 		} else {
2670*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x67, 0x0c);
2671*4882a593Smuzhiyun 			snd_soc_component_write(component, 0x69, 0x04);
2672*4882a593Smuzhiyun 		}
2673*4882a593Smuzhiyun 		/* clk2 used as EQ clk, OSR = 6xFs for 8k resampling to 48k */
2674*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_EQ_CLK_OSR_SEL_REG1C, 0x35);
2675*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SHARED_ADDR_REG1D, 0x00);
2676*4882a593Smuzhiyun 
2677*4882a593Smuzhiyun 		for (index = 0; index < 59; index++) {
2678*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_SHARED_DATA_REG1E,
2679*4882a593Smuzhiyun 						es8396_equalizer_lpf_bt_incall[index]);
2680*4882a593Smuzhiyun 		}
2681*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SHARED_ADDR_REG1D, 0xbb);
2682*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SHARED_DATA_REG1E,
2683*4882a593Smuzhiyun 					es8396_equalizer_lpf_bt_incall[59]);
2684*4882a593Smuzhiyun 
2685*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->voice_pop_work,
2686*4882a593Smuzhiyun 				      msecs_to_jiffies(50));
2687*4882a593Smuzhiyun 	} else {
2688*4882a593Smuzhiyun 		pr_debug("****************es8396_voice_startup, capture\n");
2689*4882a593Smuzhiyun 		es8396->aif2_select |= 0x02;
2690*4882a593Smuzhiyun 		/* set adc alc */
2691*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_1_REG58, 0xC6);
2692*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_2_REG59, 0x12);
2693*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_4_REG5B, 0x04);
2694*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_5_REG5C, 0xC8);
2695*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ALC_CTRL_6_REG5D, 0x11);
2696*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x0);
2697*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_MIC_IBIAS_EN_REG75, 0x02);
2698*4882a593Smuzhiyun 
2699*4882a593Smuzhiyun 		/* axMixer Gain boost */
2700*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_AX_MIXER_BOOST_REG2F);
2701*4882a593Smuzhiyun 		regv |= 0x88;
2702*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_BOOST_REG2F, regv);
2703*4882a593Smuzhiyun 		/* axmixer vol = +12db */
2704*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_VOL_REG30, 0xaa);
2705*4882a593Smuzhiyun 		/* axmixer high driver capacility */
2706*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_AX_MIXER_REF_LP_REG31, 0x02);
2707*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x33, 0);
2708*4882a593Smuzhiyun 		/* MNMixer Gain boost */
2709*4882a593Smuzhiyun 		regv = snd_soc_component_read(component, ES8396_MN_MIXER_BOOST_REG37);
2710*4882a593Smuzhiyun 		regv |= 0x88;
2711*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_BOOST_REG37, regv);
2712*4882a593Smuzhiyun 		/* mnmixer vol = +12db */
2713*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_VOL_REG38, 0x44);
2714*4882a593Smuzhiyun 		/* mnmixer high driver capacility */
2715*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_MN_MIXER_REF_LP_REG39, 0x02);
2716*4882a593Smuzhiyun 
2717*4882a593Smuzhiyun 		/* ADC STM and Digital Startup, ADC DS Mode */
2718*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x00);
2719*4882a593Smuzhiyun 		/* force adc stm to normal */
2720*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x40);
2721*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x0);
2722*4882a593Smuzhiyun 		/* ADC Volume =0db */
2723*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_LADC_VOL_REG56, 0x0);
2724*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_RADC_VOL_REG57, 0x0);
2725*4882a593Smuzhiyun 
2726*4882a593Smuzhiyun 		/* clk2 used as EQ clk, OSR = 6xFs for 8k resampling to 48k */
2727*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP2_OUT_FMT_REG23,
2728*4882a593Smuzhiyun 					      0x7F, 0x33);
2729*4882a593Smuzhiyun 	}
2730*4882a593Smuzhiyun 	return 0;
2731*4882a593Smuzhiyun }
2732*4882a593Smuzhiyun 
es8396_voice_shutdown(struct snd_pcm_substream * substream,struct snd_soc_dai * dai)2733*4882a593Smuzhiyun static void es8396_voice_shutdown(struct snd_pcm_substream *substream,
2734*4882a593Smuzhiyun 				  struct snd_soc_dai *dai)
2735*4882a593Smuzhiyun {
2736*4882a593Smuzhiyun 	struct snd_soc_component *component = dai->component;
2737*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2738*4882a593Smuzhiyun 	bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
2739*4882a593Smuzhiyun 
2740*4882a593Smuzhiyun 	pr_debug("****************es8396_voice_shutdown\n");
2741*4882a593Smuzhiyun 
2742*4882a593Smuzhiyun 	/* DSP-B, 1st SCLK after LRCK edge, I2S2 SDPIN */
2743*4882a593Smuzhiyun 	if (playback) {
2744*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x66, 0x01);
2745*4882a593Smuzhiyun 		pr_debug("****************es8396_voice_shutdown, playback\n");
2746*4882a593Smuzhiyun 		schedule_delayed_work(&es8396->voice_shutdown_depop_work,
2747*4882a593Smuzhiyun 				      msecs_to_jiffies(10));
2748*4882a593Smuzhiyun 	} else {
2749*4882a593Smuzhiyun 		pr_debug("****************es8396_voice_shutdown, captuer\n");
2750*4882a593Smuzhiyun 		/* //DSP-B, 1st SCLK after LRCK edge, I2S2 SDPO */
2751*4882a593Smuzhiyun 		snd_soc_component_update_bits(component, ES8396_SDP2_OUT_FMT_REG23,
2752*4882a593Smuzhiyun 					      0x7F, 0x73);
2753*4882a593Smuzhiyun 		es8396->aif2_select &= 0xfd;
2754*4882a593Smuzhiyun 	}
2755*4882a593Smuzhiyun }
2756*4882a593Smuzhiyun 
2757*4882a593Smuzhiyun /*
2758*4882a593Smuzhiyun  * Only mute SDP IN(for dac)
2759*4882a593Smuzhiyun  */
es8396_aif1_mute(struct snd_soc_dai * codec_dai,int mute,int stream)2760*4882a593Smuzhiyun static int es8396_aif1_mute(struct snd_soc_dai *codec_dai, int mute, int stream)
2761*4882a593Smuzhiyun {
2762*4882a593Smuzhiyun 	struct snd_soc_component *component = codec_dai->component;
2763*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2764*4882a593Smuzhiyun 
2765*4882a593Smuzhiyun 	pr_debug("es8396_aif1_mute id = %d, mute = %d", codec_dai->id, mute);
2766*4882a593Smuzhiyun 	if (mute) {
2767*4882a593Smuzhiyun 		if (es8396->spk_ctl_gpio && es8396->aif2_select == 0)
2768*4882a593Smuzhiyun 			gpiod_set_value(es8396->spk_ctl_gpio, 0);
2769*4882a593Smuzhiyun 		if (es8396->lineout_ctl_gpio && es8396->aif2_select == 0)
2770*4882a593Smuzhiyun 			gpiod_set_value(es8396->lineout_ctl_gpio, 0);
2771*4882a593Smuzhiyun 		msleep(100);
2772*4882a593Smuzhiyun 	} else {
2773*4882a593Smuzhiyun 		if (es8396->spk_ctl_gpio)
2774*4882a593Smuzhiyun 			gpiod_set_value(es8396->spk_ctl_gpio, 1);
2775*4882a593Smuzhiyun 		if (es8396->lineout_ctl_gpio)
2776*4882a593Smuzhiyun 			gpiod_set_value(es8396->lineout_ctl_gpio, 1);
2777*4882a593Smuzhiyun 	}
2778*4882a593Smuzhiyun 
2779*4882a593Smuzhiyun 	return 0;
2780*4882a593Smuzhiyun }
2781*4882a593Smuzhiyun 
es8396_aif2_mute(struct snd_soc_dai * codec_dai,int mute,int stream)2782*4882a593Smuzhiyun static int es8396_aif2_mute(struct snd_soc_dai *codec_dai, int mute, int stream)
2783*4882a593Smuzhiyun {
2784*4882a593Smuzhiyun 	struct snd_soc_component *component = codec_dai->component;
2785*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2786*4882a593Smuzhiyun 
2787*4882a593Smuzhiyun 	pr_debug("es8396_aif2_mute id = %d, mute = %d", codec_dai->id, mute);
2788*4882a593Smuzhiyun 
2789*4882a593Smuzhiyun 	if (mute) {
2790*4882a593Smuzhiyun 		if (es8396->spk_ctl_gpio && es8396->aif1_select == 0)
2791*4882a593Smuzhiyun 			gpiod_set_value(es8396->spk_ctl_gpio, 0);
2792*4882a593Smuzhiyun 		if (es8396->lineout_ctl_gpio && es8396->aif1_select == 0)
2793*4882a593Smuzhiyun 			gpiod_set_value(es8396->lineout_ctl_gpio, 0);
2794*4882a593Smuzhiyun 		msleep(100);
2795*4882a593Smuzhiyun 	} else {
2796*4882a593Smuzhiyun 		if (es8396->spk_ctl_gpio)
2797*4882a593Smuzhiyun 			gpiod_set_value(es8396->spk_ctl_gpio, 1);
2798*4882a593Smuzhiyun 		if (es8396->lineout_ctl_gpio)
2799*4882a593Smuzhiyun 			gpiod_set_value(es8396->lineout_ctl_gpio, 1);
2800*4882a593Smuzhiyun 	}
2801*4882a593Smuzhiyun 	return 0;
2802*4882a593Smuzhiyun }
2803*4882a593Smuzhiyun 
2804*4882a593Smuzhiyun /* SNDRV_PCM_RATE_KNOT -> 12000, 24000 Hz, limit with constraint list */
2805*4882a593Smuzhiyun #define ES8396_RATES (SNDRV_PCM_RATE_8000_48000 | SNDRV_PCM_RATE_KNOT)
2806*4882a593Smuzhiyun #define ES8396_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE |\
2807*4882a593Smuzhiyun 			SNDRV_PCM_FMTBIT_S24_LE)
2808*4882a593Smuzhiyun 
2809*4882a593Smuzhiyun static const struct snd_soc_dai_ops es8396_aif1_dai_ops = {
2810*4882a593Smuzhiyun 	.startup = es8396_pcm_startup,
2811*4882a593Smuzhiyun 	.shutdown = es8396_pcm_shutdown,
2812*4882a593Smuzhiyun 	.set_sysclk = es8396_set_dai_sysclk,
2813*4882a593Smuzhiyun 	.set_fmt = es8396_set_dai_fmt,
2814*4882a593Smuzhiyun 	.hw_params = es8396_pcm_hw_params,
2815*4882a593Smuzhiyun 	.mute_stream = es8396_aif1_mute,
2816*4882a593Smuzhiyun 	.set_pll = es8396_set_pll,
2817*4882a593Smuzhiyun 	.set_tristate = es8396_set_tristate,
2818*4882a593Smuzhiyun 	.no_capture_mute = 1,
2819*4882a593Smuzhiyun };
2820*4882a593Smuzhiyun 
2821*4882a593Smuzhiyun static const struct snd_soc_dai_ops es8396_aif2_dai_ops = {
2822*4882a593Smuzhiyun 	.startup = es8396_voice_startup,
2823*4882a593Smuzhiyun 	.shutdown = es8396_voice_shutdown,
2824*4882a593Smuzhiyun 	.set_sysclk = es8396_set_dai_sysclk,
2825*4882a593Smuzhiyun 	.set_fmt = es8396_set_dai_fmt,
2826*4882a593Smuzhiyun 	.hw_params = es8396_pcm_hw_params,
2827*4882a593Smuzhiyun 	.mute_stream = es8396_aif2_mute,
2828*4882a593Smuzhiyun 	.set_pll = es8396_set_pll,
2829*4882a593Smuzhiyun 	.no_capture_mute = 1,
2830*4882a593Smuzhiyun };
2831*4882a593Smuzhiyun 
2832*4882a593Smuzhiyun static struct snd_soc_dai_driver es8396_dai[] = {
2833*4882a593Smuzhiyun 	{
2834*4882a593Smuzhiyun 		.name = "es8396-aif1",
2835*4882a593Smuzhiyun 		.playback = {
2836*4882a593Smuzhiyun 			.stream_name = "SDP1 Playback",
2837*4882a593Smuzhiyun 			.channels_min = 1,
2838*4882a593Smuzhiyun 			.channels_max = 2,
2839*4882a593Smuzhiyun 			.rates = ES8396_RATES,
2840*4882a593Smuzhiyun 			.formats = ES8396_FORMATS,
2841*4882a593Smuzhiyun 		},
2842*4882a593Smuzhiyun 		.capture = {
2843*4882a593Smuzhiyun 			.stream_name = "SDP1 Capture",
2844*4882a593Smuzhiyun 			.channels_min = 1,
2845*4882a593Smuzhiyun 			.channels_max = 2,
2846*4882a593Smuzhiyun 			.rates = ES8396_RATES,
2847*4882a593Smuzhiyun 			.formats = ES8396_FORMATS,
2848*4882a593Smuzhiyun 		},
2849*4882a593Smuzhiyun 		.ops = &es8396_aif1_dai_ops,
2850*4882a593Smuzhiyun 	},
2851*4882a593Smuzhiyun };
2852*4882a593Smuzhiyun 
es8396_suspend(struct device * dev)2853*4882a593Smuzhiyun static int es8396_suspend(struct device *dev)
2854*4882a593Smuzhiyun {
2855*4882a593Smuzhiyun 	struct es8396_private *es8396 = dev_get_drvdata(dev);
2856*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
2857*4882a593Smuzhiyun 
2858*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4e, 0x84);
2859*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4f, 0x85);
2860*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x66, 0x01);
2861*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x6e, 0x00);
2862*4882a593Smuzhiyun 
2863*4882a593Smuzhiyun 	return 0;
2864*4882a593Smuzhiyun }
2865*4882a593Smuzhiyun 
es8396_resume(struct device * dev)2866*4882a593Smuzhiyun static int es8396_resume(struct device *dev)
2867*4882a593Smuzhiyun {
2868*4882a593Smuzhiyun 	struct es8396_private *es8396 = dev_get_drvdata(dev);
2869*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
2870*4882a593Smuzhiyun 
2871*4882a593Smuzhiyun 	usleep_range(20000, 21000);
2872*4882a593Smuzhiyun 
2873*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x6e, 0x00);
2874*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x66, 0x00);
2875*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4e, 0x80);
2876*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4f, 0x81);
2877*4882a593Smuzhiyun 	return 0;
2878*4882a593Smuzhiyun }
2879*4882a593Smuzhiyun 
es8396_probe(struct snd_soc_component * component)2880*4882a593Smuzhiyun static int es8396_probe(struct snd_soc_component *component)
2881*4882a593Smuzhiyun {
2882*4882a593Smuzhiyun 	struct es8396_private *es8396 = snd_soc_component_get_drvdata(component);
2883*4882a593Smuzhiyun 	int ret = 0, regv;
2884*4882a593Smuzhiyun 	u8 value;
2885*4882a593Smuzhiyun 
2886*4882a593Smuzhiyun 	es8396->component = component;
2887*4882a593Smuzhiyun 	es8396->mclk_clock = devm_clk_get(component->dev, "mclk");
2888*4882a593Smuzhiyun 	if (PTR_ERR(es8396->mclk_clock) == -EPROBE_DEFER)
2889*4882a593Smuzhiyun 		return -EPROBE_DEFER;
2890*4882a593Smuzhiyun 
2891*4882a593Smuzhiyun 	ret = clk_prepare_enable(es8396->mclk_clock);
2892*4882a593Smuzhiyun 	if (ret)
2893*4882a593Smuzhiyun 		return ret;
2894*4882a593Smuzhiyun 	regv = snd_soc_component_read(component, ES8396_PLL_K2_REG05);
2895*4882a593Smuzhiyun 
2896*4882a593Smuzhiyun 	if (regv == 0x00) {
2897*4882a593Smuzhiyun 		/*
2898*4882a593Smuzhiyun 		 * setup system analog control
2899*4882a593Smuzhiyun 		 */
2900*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DLL_CTRL_REG0D, 0x20);
2901*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_SRC_SEL_REG01, 0x04);
2902*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_CTRL_1_REG02, 0xc1);
2903*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_CTRL_2_REG03, 0x00);
2904*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_N_REG04, 0x08);
2905*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_K2_REG05, 0X1d);
2906*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_K1_REG06, 0Xc3);
2907*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_K0_REG07, 0Xb8);
2908*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_PLL_CTRL_1_REG02, 0x41);
2909*4882a593Smuzhiyun 
2910*4882a593Smuzhiyun 		/* adc,dac,cphp,class d clk enable,from clk2 */
2911*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_CLK_CTRL_REG08, 0x00);
2912*4882a593Smuzhiyun 		/* adc clk ratio=1 */
2913*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CLK_DIV_REG09, 0x04);
2914*4882a593Smuzhiyun 		/* dac clk ratio=1 */
2915*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_CLK_DIV_REG0A, 0x01);
2916*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_BCLK_DIV_M2_REG0F, 0x24);
2917*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_LRCK_DIV_M4_REG11, 0x22);
2918*4882a593Smuzhiyun 
2919*4882a593Smuzhiyun 		msleep(50);
2920*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_VMID_REF_REG71, 0xFC);
2921*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x72, 0xFF);
2922*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x73, 0xFF);
2923*4882a593Smuzhiyun 		if (es8396_valid_analdo(es8396->ana_ldo_lvl) == false) {
2924*4882a593Smuzhiyun 			pr_err("Analog LDO Level error.\n");
2925*4882a593Smuzhiyun 			return -EINVAL;
2926*4882a593Smuzhiyun 		}
2927*4882a593Smuzhiyun 		value = es8396->ana_ldo_lvl;
2928*4882a593Smuzhiyun 		value &= 0x07;
2929*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_CHIP_ANA_CTL_REG70, value);
2930*4882a593Smuzhiyun 		/* mic enable, mic d2se enable */
2931*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_MIC_IBIAS_EN_REG75, 0x01);
2932*4882a593Smuzhiyun 		msleep(50);
2933*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_TEST_MODE_REG76, 0xA0);
2934*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_NGTH_REG7A, 0x20);
2935*4882a593Smuzhiyun 		msleep(50);
2936*4882a593Smuzhiyun 
2937*4882a593Smuzhiyun 		/* power up adc and dac analog */
2938*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x00);
2939*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_REF_PWR_CTRL_REG6E, 0x00);
2940*4882a593Smuzhiyun 		/* set L,R DAC volume */
2941*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_LDAC_VOL_REG6A, 0x01);
2942*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_RDAC_VOL_REG6B, 0x01);
2943*4882a593Smuzhiyun 		/* setup charge current for calibrate */
2944*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_LADC_VOL_REG56, 0x84);
2945*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_RADC_VOL_REG57, 0xdc);
2946*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_OFFSET_CALI_REG6F, 0x06);
2947*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_RAMP_RATE_REG67, 0x00);
2948*4882a593Smuzhiyun 		/* enable adc and dac stm for calibrate */
2949*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_CSM_REG66, 0x00);
2950*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x00);
2951*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x40);
2952*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_FORCE_REG77, 0x00);
2953*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DLL_CTRL_REG0D, 0x00);
2954*4882a593Smuzhiyun 		msleep(100);
2955*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_CSM_REG66, 0x00);
2956*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_ANALOG_CTRL_REG5E, 0x00);
2957*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x5f, 0xf2);
2958*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x1f, 0x00);
2959*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x20, 0x40);
2960*4882a593Smuzhiyun 		/* FM */
2961*4882a593Smuzhiyun 		msleep(100);
2962*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x65, 0x88);
2963*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x2E, 0x88);
2964*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x2F, 0x00);
2965*4882a593Smuzhiyun 		snd_soc_component_write(component, 0x30, 0xBB);
2966*4882a593Smuzhiyun 
2967*4882a593Smuzhiyun 		if (es8396_valid_micbias(es8396->mic_bias_lvl) == false) {
2968*4882a593Smuzhiyun 			pr_err("MIC BIAS Level error.\n");
2969*4882a593Smuzhiyun 			return -EINVAL;
2970*4882a593Smuzhiyun 		}
2971*4882a593Smuzhiyun 		value = es8396->mic_bias_lvl;
2972*4882a593Smuzhiyun 		value &= 0x07;
2973*4882a593Smuzhiyun 		value = (value << 4) | 0x08;
2974*4882a593Smuzhiyun 		/* enable micbias1 */
2975*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SYS_MICBIAS_CTRL_REG74, value);
2976*4882a593Smuzhiyun 
2977*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_CSM_REG53, 0x20);
2978*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_PGA_GAIN_REG61, 0x33);
2979*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_MICBOOST_REG60, 0x22);
2980*4882a593Smuzhiyun 		if (es8396->dmic_amic == MIC_AMIC)
2981*4882a593Smuzhiyun 			/*use analog mic */
2982*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_ADC_DMIC_RAMPRATE_REG54,
2983*4882a593Smuzhiyun 						0x00);
2984*4882a593Smuzhiyun 		else
2985*4882a593Smuzhiyun 			/*use digital mic */
2986*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_ADC_DMIC_RAMPRATE_REG54,
2987*4882a593Smuzhiyun 						0xf0);
2988*4882a593Smuzhiyun 
2989*4882a593Smuzhiyun 		/*Enable HPF, LDATA= LADC, RDATA = LADC */
2990*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ADC_HPF_COMP_DASEL_REG55, 0x31);
2991*4882a593Smuzhiyun 
2992*4882a593Smuzhiyun 		/*
2993*4882a593Smuzhiyun 		 * setup hp detection
2994*4882a593Smuzhiyun 		 */
2995*4882a593Smuzhiyun 
2996*4882a593Smuzhiyun 		/* gpio 2 for irq, AINL as irq src, gpio1 for dmic clk */
2997*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_ALRCK_GPIO_SEL_REG15, 0xfa);
2998*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_JACK_DET_COMP_REG69, 0x00);
2999*4882a593Smuzhiyun 		if (es8396->jackdet_enable == 1) {
3000*4882a593Smuzhiyun 			/* jack detection from AINL pin, AINL=0, HP Insert */
3001*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_DAC_JACK_DET_COMP_REG69,
3002*4882a593Smuzhiyun 						0x04);
3003*4882a593Smuzhiyun 			if (es8396->gpio_int_pol == 0)
3004*4882a593Smuzhiyun 				/* if HP insert, GPIO2=Low */
3005*4882a593Smuzhiyun 				snd_soc_component_write(component, ES8396_GPIO_IRQ_REG16,
3006*4882a593Smuzhiyun 							0x80);
3007*4882a593Smuzhiyun 			else
3008*4882a593Smuzhiyun 				/* if HP insert, GPIO2=High */
3009*4882a593Smuzhiyun 				snd_soc_component_write(component, ES8396_GPIO_IRQ_REG16,
3010*4882a593Smuzhiyun 							0xc0);
3011*4882a593Smuzhiyun 		} else {
3012*4882a593Smuzhiyun 			snd_soc_component_write(component, ES8396_GPIO_IRQ_REG16, 0x00);
3013*4882a593Smuzhiyun 		}
3014*4882a593Smuzhiyun 
3015*4882a593Smuzhiyun 		/*
3016*4882a593Smuzhiyun 		 * setup mono in in differential mode or stereo mode
3017*4882a593Smuzhiyun 		 */
3018*4882a593Smuzhiyun 
3019*4882a593Smuzhiyun 		/* monoin in differential mode */
3020*4882a593Smuzhiyun 		if (es8396->monoin_differential == 1)
3021*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_MN_MIXER_REF_LP_REG39,
3022*4882a593Smuzhiyun 						      0x08, 0x08);
3023*4882a593Smuzhiyun 		else
3024*4882a593Smuzhiyun 			snd_soc_component_update_bits(component, ES8396_MN_MIXER_REF_LP_REG39,
3025*4882a593Smuzhiyun 						      0x08, 0x00);
3026*4882a593Smuzhiyun 
3027*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_DAC_JACK_DET_COMP_REG69, 0x00);
3028*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_BCLK_DIV_M1_REG0E, 0x24);
3029*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_LRCK_DIV_M3_REG10, 0x22);
3030*4882a593Smuzhiyun 		snd_soc_component_write(component, ES8396_SDP_2_MS_REG13, 0x00);
3031*4882a593Smuzhiyun 		//codec->dapm.bias_level = SND_SOC_BIAS_STANDBY;
3032*4882a593Smuzhiyun 	}
3033*4882a593Smuzhiyun 
3034*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->adc_depop_work, adc_depop_work_events);
3035*4882a593Smuzhiyun 	mutex_init(&es8396->adc_depop_mlock);
3036*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->pcm_pop_work, pcm_pop_work_events);
3037*4882a593Smuzhiyun 	mutex_init(&es8396->pcm_depop_mlock);
3038*4882a593Smuzhiyun 
3039*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->voice_pop_work, voice_pop_work_events);
3040*4882a593Smuzhiyun 	mutex_init(&es8396->voice_depop_mlock);
3041*4882a593Smuzhiyun 
3042*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->init_cali_work, init_cali_work_events);
3043*4882a593Smuzhiyun 	mutex_init(&es8396->init_cali_mlock);
3044*4882a593Smuzhiyun 
3045*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->pcm_shutdown_depop_work,
3046*4882a593Smuzhiyun 			  pcm_shutdown_depop_events);
3047*4882a593Smuzhiyun 	mutex_init(&es8396->pcm_shutdown_depop_mlock);
3048*4882a593Smuzhiyun 
3049*4882a593Smuzhiyun 	INIT_DELAYED_WORK(&es8396->voice_shutdown_depop_work,
3050*4882a593Smuzhiyun 			  voice_shutdown_depop_events);
3051*4882a593Smuzhiyun 	mutex_init(&es8396->voice_shutdown_depop_mlock);
3052*4882a593Smuzhiyun 
3053*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x6f, 0x83);
3054*4882a593Smuzhiyun 	snd_soc_component_write(component, ES8396_SYS_VMID_REF_REG71, 0xFC);
3055*4882a593Smuzhiyun 	msleep(100);
3056*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4E, 0x84);
3057*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4F, 0x85);
3058*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4A, 0x60);
3059*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x4B, 0x60);
3060*4882a593Smuzhiyun 	/*
3061*4882a593Smuzhiyun 	 * TODO: pop noise occur when HS calibration during probe
3062*4882a593Smuzhiyun 	 * increase the delay of a period of time if necessary
3063*4882a593Smuzhiyun 	 * msleep(50);
3064*4882a593Smuzhiyun 	 */
3065*4882a593Smuzhiyun 	return ret;
3066*4882a593Smuzhiyun }
3067*4882a593Smuzhiyun 
es8396_remove(struct snd_soc_component * component)3068*4882a593Smuzhiyun static void es8396_remove(struct snd_soc_component *component)
3069*4882a593Smuzhiyun {
3070*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4E, 0x84);
3071*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4F, 0x85);
3072*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4A, 0x80);
3073*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4B, 0x80);
3074*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x70, 0xd4);
3075*4882a593Smuzhiyun }
3076*4882a593Smuzhiyun 
3077*4882a593Smuzhiyun const struct regmap_config es8396_regmap_config = {
3078*4882a593Smuzhiyun 	.reg_bits       = 8,
3079*4882a593Smuzhiyun 	.val_bits       = 8,
3080*4882a593Smuzhiyun 	.max_register   = ES8396_MAX_REGISTER,
3081*4882a593Smuzhiyun 	.cache_type     = REGCACHE_RBTREE,
3082*4882a593Smuzhiyun 	.reg_defaults = es8396_reg_defaults,
3083*4882a593Smuzhiyun 	.num_reg_defaults = ARRAY_SIZE(es8396_reg_defaults),
3084*4882a593Smuzhiyun };
3085*4882a593Smuzhiyun 
3086*4882a593Smuzhiyun static const struct snd_soc_component_driver soc_codec_dev_es8396 = {
3087*4882a593Smuzhiyun 	.probe = es8396_probe,
3088*4882a593Smuzhiyun 	.remove = es8396_remove,
3089*4882a593Smuzhiyun 	.set_bias_level = es8396_set_bias_level,
3090*4882a593Smuzhiyun 
3091*4882a593Smuzhiyun 	.dapm_widgets = es8396_dapm_widgets,
3092*4882a593Smuzhiyun 	.num_dapm_widgets = ARRAY_SIZE(es8396_dapm_widgets),
3093*4882a593Smuzhiyun 	.dapm_routes = es8396_dapm_routes,
3094*4882a593Smuzhiyun 	.num_dapm_routes = ARRAY_SIZE(es8396_dapm_routes),
3095*4882a593Smuzhiyun 
3096*4882a593Smuzhiyun 	.controls = es8396_snd_controls,
3097*4882a593Smuzhiyun 	.num_controls = ARRAY_SIZE(es8396_snd_controls),
3098*4882a593Smuzhiyun };
3099*4882a593Smuzhiyun 
init_es8396_prv(struct es8396_private * es8396)3100*4882a593Smuzhiyun static int init_es8396_prv(struct es8396_private *es8396)
3101*4882a593Smuzhiyun {
3102*4882a593Smuzhiyun 	if (!es8396)
3103*4882a593Smuzhiyun 		return -EINVAL;
3104*4882a593Smuzhiyun 
3105*4882a593Smuzhiyun 	es8396->dvdd_pwr_vol = 0x18;
3106*4882a593Smuzhiyun 	es8396->spkmono = false;
3107*4882a593Smuzhiyun 	es8396->earpiece = true;
3108*4882a593Smuzhiyun 	es8396->monoin_differential = true;
3109*4882a593Smuzhiyun 	es8396->lno_differential = 0;
3110*4882a593Smuzhiyun 	es8396->ana_ldo_lvl = ANA_LDO_2_1V;
3111*4882a593Smuzhiyun 	es8396->spk_ldo_lvl = SPK_LDO_3V;
3112*4882a593Smuzhiyun 	es8396->mic_bias_lvl = MICBIAS_3V;
3113*4882a593Smuzhiyun 	es8396->jackdet_enable = true;
3114*4882a593Smuzhiyun 	es8396->gpio_int_pol = 0;
3115*4882a593Smuzhiyun 	es8396->dmic_amic = MIC_AMIC;
3116*4882a593Smuzhiyun 	es8396->calibrate = false;
3117*4882a593Smuzhiyun 	es8396->pcm_pop_work_retry = 1;
3118*4882a593Smuzhiyun 	es8396->output_device_selected = 0;
3119*4882a593Smuzhiyun 	es8396->aif1_select = 0;
3120*4882a593Smuzhiyun 	es8396->aif2_select = 0;
3121*4882a593Smuzhiyun 	return 0;
3122*4882a593Smuzhiyun }
3123*4882a593Smuzhiyun 
es8396_i2c_probe(struct i2c_client * i2c_client,const struct i2c_device_id * id)3124*4882a593Smuzhiyun static int es8396_i2c_probe(struct i2c_client *i2c_client,
3125*4882a593Smuzhiyun 			    const struct i2c_device_id *id)
3126*4882a593Smuzhiyun {
3127*4882a593Smuzhiyun 	struct es8396_private *es8396;
3128*4882a593Smuzhiyun 	int ret;
3129*4882a593Smuzhiyun 
3130*4882a593Smuzhiyun 	es8396 = devm_kzalloc(&i2c_client->dev, sizeof(struct es8396_private),
3131*4882a593Smuzhiyun 			      GFP_KERNEL);
3132*4882a593Smuzhiyun 	if (!es8396)
3133*4882a593Smuzhiyun 		return -ENOMEM;
3134*4882a593Smuzhiyun 
3135*4882a593Smuzhiyun 	ret = init_es8396_prv(es8396);
3136*4882a593Smuzhiyun 	if (ret < 0)
3137*4882a593Smuzhiyun 		return -EINVAL;
3138*4882a593Smuzhiyun 
3139*4882a593Smuzhiyun 	es8396->regmap = devm_regmap_init_i2c(i2c_client, &es8396_regmap_config);
3140*4882a593Smuzhiyun 	if (IS_ERR(es8396->regmap))
3141*4882a593Smuzhiyun 		return PTR_ERR(es8396->regmap);
3142*4882a593Smuzhiyun 
3143*4882a593Smuzhiyun 	/* initialize codec */
3144*4882a593Smuzhiyun 	i2c_set_clientdata(i2c_client, es8396);
3145*4882a593Smuzhiyun 
3146*4882a593Smuzhiyun 	/* external speaker amp controller */
3147*4882a593Smuzhiyun 	es8396->spk_ctl_gpio = devm_gpiod_get_optional(&i2c_client->dev,
3148*4882a593Smuzhiyun 						       "spk-con-gpio",
3149*4882a593Smuzhiyun 						       GPIOD_OUT_LOW);
3150*4882a593Smuzhiyun 	if (IS_ERR(es8396->spk_ctl_gpio))
3151*4882a593Smuzhiyun 		return PTR_ERR(es8396->spk_ctl_gpio);
3152*4882a593Smuzhiyun 
3153*4882a593Smuzhiyun 	/* lineout output  controller*/
3154*4882a593Smuzhiyun 	es8396->lineout_ctl_gpio = devm_gpiod_get_optional(&i2c_client->dev,
3155*4882a593Smuzhiyun 							   "lineout-con-gpio",
3156*4882a593Smuzhiyun 							   GPIOD_OUT_LOW);
3157*4882a593Smuzhiyun 	if (IS_ERR(es8396->lineout_ctl_gpio))
3158*4882a593Smuzhiyun 		return PTR_ERR(es8396->lineout_ctl_gpio);
3159*4882a593Smuzhiyun 
3160*4882a593Smuzhiyun 	return devm_snd_soc_register_component(&i2c_client->dev,
3161*4882a593Smuzhiyun 					       &soc_codec_dev_es8396, es8396_dai,
3162*4882a593Smuzhiyun 					       ARRAY_SIZE(es8396_dai));
3163*4882a593Smuzhiyun }
3164*4882a593Smuzhiyun 
es8396_i2c_shutdown(struct i2c_client * client)3165*4882a593Smuzhiyun static void es8396_i2c_shutdown(struct i2c_client *client)
3166*4882a593Smuzhiyun {
3167*4882a593Smuzhiyun 	struct es8396_private *es8396 = i2c_get_clientdata(client);
3168*4882a593Smuzhiyun 	struct snd_soc_component *component = es8396->component;
3169*4882a593Smuzhiyun 
3170*4882a593Smuzhiyun 	if (es8396->spk_ctl_gpio)
3171*4882a593Smuzhiyun 		gpiod_set_value(es8396->spk_ctl_gpio, 0);
3172*4882a593Smuzhiyun 
3173*4882a593Smuzhiyun 	usleep_range(20000, 21000);
3174*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4E, 0x84);
3175*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4F, 0x85);
3176*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4a, 0x80);
3177*4882a593Smuzhiyun 	snd_soc_component_write(component, 0X4b, 0x80);
3178*4882a593Smuzhiyun 	snd_soc_component_write(component, 0x70, 0xd4);
3179*4882a593Smuzhiyun 	msleep(300);
3180*4882a593Smuzhiyun }
3181*4882a593Smuzhiyun 
3182*4882a593Smuzhiyun static const struct i2c_device_id es8396_id[] = {
3183*4882a593Smuzhiyun 	{"es8396", 0},
3184*4882a593Smuzhiyun 	{}
3185*4882a593Smuzhiyun };
3186*4882a593Smuzhiyun 
3187*4882a593Smuzhiyun MODULE_DEVICE_TABLE(i2c, es8396_id);
3188*4882a593Smuzhiyun static const struct dev_pm_ops es8396_pm_ops = {
3189*4882a593Smuzhiyun 	.suspend = es8396_suspend,
3190*4882a593Smuzhiyun 	.resume = es8396_resume,
3191*4882a593Smuzhiyun };
3192*4882a593Smuzhiyun 
3193*4882a593Smuzhiyun static struct i2c_driver es8396_i2c_driver = {
3194*4882a593Smuzhiyun 	.driver = {
3195*4882a593Smuzhiyun 		   .name = "es8396",
3196*4882a593Smuzhiyun 		   .pm = &es8396_pm_ops,
3197*4882a593Smuzhiyun 		   },
3198*4882a593Smuzhiyun 	.id_table = es8396_id,
3199*4882a593Smuzhiyun 	.probe = es8396_i2c_probe,
3200*4882a593Smuzhiyun 	.shutdown = es8396_i2c_shutdown,
3201*4882a593Smuzhiyun };
3202*4882a593Smuzhiyun 
3203*4882a593Smuzhiyun module_i2c_driver(es8396_i2c_driver);
3204*4882a593Smuzhiyun 
3205*4882a593Smuzhiyun MODULE_DESCRIPTION("ASoC ES8396 driver");
3206*4882a593Smuzhiyun MODULE_AUTHOR("DavidYang, Everest Semiconductor Co., Ltd, <yangxiaohua@everest-semi.com>");
3207*4882a593Smuzhiyun MODULE_LICENSE("GPL");
3208