blob: 6b700a68a57aefee21db68b6f54078cae98232a6 [file] [log] [blame]
Meng Wang43bbb872018-12-10 12:32:05 +08001// SPDX-License-Identifier: GPL-2.0-only
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302/* Copyright (c) 2018, The Linux Foundation. All rights reserved.
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303 */
4
5#include <linux/module.h>
6#include <linux/init.h>
7#include <linux/io.h>
8#include <linux/platform_device.h>
9#include <linux/clk.h>
10#include <sound/soc.h>
11#include <sound/pcm.h>
12#include <sound/pcm_params.h>
13#include <sound/soc-dapm.h>
14#include <sound/tlv.h>
15#include <soc/swr-wcd.h>
16
Meng Wang11a25cf2018-10-31 14:11:26 +080017#include <asoc/msm-cdc-pinctrl.h>
Laxminath Kasama7ecc582018-06-15 16:55:02 +053018#include "bolero-cdc.h"
19#include "bolero-cdc-registers.h"
Laxminath Kasama7ecc582018-06-15 16:55:02 +053020
21#define RX_MACRO_RATES (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000 |\
22 SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_48000 |\
23 SNDRV_PCM_RATE_96000 | SNDRV_PCM_RATE_192000 |\
24 SNDRV_PCM_RATE_384000)
25/* Fractional Rates */
26#define RX_MACRO_FRAC_RATES (SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_88200 |\
27 SNDRV_PCM_RATE_176400 | SNDRV_PCM_RATE_352800)
28
29#define RX_MACRO_FORMATS (SNDRV_PCM_FMTBIT_S16_LE |\
30 SNDRV_PCM_FMTBIT_S24_LE |\
31 SNDRV_PCM_FMTBIT_S24_3LE | SNDRV_PCM_FMTBIT_S32_LE)
32
33#define RX_MACRO_ECHO_RATES (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000 |\
34 SNDRV_PCM_RATE_48000)
35#define RX_MACRO_ECHO_FORMATS (SNDRV_PCM_FMTBIT_S16_LE |\
36 SNDRV_PCM_FMTBIT_S24_LE |\
37 SNDRV_PCM_FMTBIT_S24_3LE)
38
Laxminath Kasamac396d52018-09-06 12:53:26 +053039#define SAMPLING_RATE_44P1KHZ 44100
40#define SAMPLING_RATE_88P2KHZ 88200
41#define SAMPLING_RATE_176P4KHZ 176400
42#define SAMPLING_RATE_352P8KHZ 352800
43
Laxminath Kasama7ecc582018-06-15 16:55:02 +053044#define RX_MACRO_MAX_OFFSET 0x1000
45
46#define RX_MACRO_MAX_DMA_CH_PER_PORT 2
47#define RX_SWR_STRING_LEN 80
48#define RX_MACRO_CHILD_DEVICES_MAX 3
49
50#define RX_MACRO_INTERP_MUX_NUM_INPUTS 3
51#define RX_MACRO_SIDETONE_IIR_COEFF_MAX 5
52
53#define STRING(name) #name
54#define RX_MACRO_DAPM_ENUM(name, reg, offset, text) \
55static SOC_ENUM_SINGLE_DECL(name##_enum, reg, offset, text); \
56static const struct snd_kcontrol_new name##_mux = \
57 SOC_DAPM_ENUM(STRING(name), name##_enum)
58
59#define RX_MACRO_DAPM_ENUM_EXT(name, reg, offset, text, getname, putname) \
60static SOC_ENUM_SINGLE_DECL(name##_enum, reg, offset, text); \
61static const struct snd_kcontrol_new name##_mux = \
62 SOC_DAPM_ENUM_EXT(STRING(name), name##_enum, getname, putname)
63
64#define RX_MACRO_DAPM_MUX(name, shift, kctl) \
65 SND_SOC_DAPM_MUX(name, SND_SOC_NOPM, shift, 0, &kctl##_mux)
66
67#define RX_MACRO_RX_PATH_OFFSET 0x80
68#define RX_MACRO_COMP_OFFSET 0x40
69
Laxminath Kasam497a6512018-09-17 16:11:52 +053070#define MAX_IMPED_PARAMS 6
71
72struct wcd_imped_val {
73 u32 imped_val;
74 u8 index;
75};
76
77static const struct wcd_imped_val imped_index[] = {
78 {4, 0},
79 {5, 1},
80 {6, 2},
81 {7, 3},
82 {8, 4},
83 {9, 5},
84 {10, 6},
85 {11, 7},
86 {12, 8},
87 {13, 9},
88};
89
90struct rx_macro_reg_mask_val {
91 u16 reg;
92 u8 mask;
93 u8 val;
94};
95
96static const struct rx_macro_reg_mask_val imped_table[][MAX_IMPED_PARAMS] = {
97 {
98 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xf2},
99 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xf2},
100 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
101 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xf2},
102 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xf2},
103 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
104 },
105 {
106 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xf4},
107 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xf4},
108 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
109 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xf4},
110 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xf4},
111 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
112 },
113 {
114 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xf7},
115 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xf7},
116 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x01},
117 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xf7},
118 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xf7},
119 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x01},
120 },
121 {
122 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xf9},
123 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xf9},
124 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
125 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xf9},
126 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xf9},
127 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
128 },
129 {
130 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xfa},
131 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xfa},
132 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
133 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xfa},
134 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xfa},
135 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
136 },
137 {
138 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xfb},
139 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xfb},
140 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
141 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xfb},
142 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xfb},
143 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
144 },
145 {
146 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xfc},
147 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xfc},
148 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
149 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xfc},
150 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xfc},
151 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
152 },
153 {
154 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xfd},
155 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xfd},
156 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x00},
157 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xfd},
158 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xfd},
159 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x00},
160 },
161 {
162 {BOLERO_CDC_RX_RX0_RX_VOL_CTL, 0xff, 0xfd},
163 {BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0xff, 0xfd},
164 {BOLERO_CDC_RX_RX0_RX_PATH_SEC1, 0x01, 0x01},
165 {BOLERO_CDC_RX_RX1_RX_VOL_CTL, 0xff, 0xfd},
166 {BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0xff, 0xfd},
167 {BOLERO_CDC_RX_RX1_RX_PATH_SEC1, 0x01, 0x01},
168 },
169};
170
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530171enum {
172 INTERP_HPHL,
173 INTERP_HPHR,
174 INTERP_AUX,
175 INTERP_MAX
176};
177
178enum {
179 RX_MACRO_RX0,
180 RX_MACRO_RX1,
181 RX_MACRO_RX2,
182 RX_MACRO_RX3,
183 RX_MACRO_RX4,
184 RX_MACRO_RX5,
185 RX_MACRO_PORTS_MAX
186};
187
188enum {
189 RX_MACRO_COMP1, /* HPH_L */
190 RX_MACRO_COMP2, /* HPH_R */
191 RX_MACRO_COMP_MAX
192};
193
194enum {
195 INTn_1_INP_SEL_ZERO = 0,
196 INTn_1_INP_SEL_DEC0,
197 INTn_1_INP_SEL_DEC1,
198 INTn_1_INP_SEL_IIR0,
199 INTn_1_INP_SEL_IIR1,
200 INTn_1_INP_SEL_RX0,
201 INTn_1_INP_SEL_RX1,
202 INTn_1_INP_SEL_RX2,
203 INTn_1_INP_SEL_RX3,
204 INTn_1_INP_SEL_RX4,
205 INTn_1_INP_SEL_RX5,
206};
207
208enum {
209 INTn_2_INP_SEL_ZERO = 0,
210 INTn_2_INP_SEL_RX0,
211 INTn_2_INP_SEL_RX1,
212 INTn_2_INP_SEL_RX2,
213 INTn_2_INP_SEL_RX3,
214 INTn_2_INP_SEL_RX4,
215 INTn_2_INP_SEL_RX5,
216};
217
218enum {
219 INTERP_MAIN_PATH,
220 INTERP_MIX_PATH,
221};
222
223/* Codec supports 2 IIR filters */
224enum {
225 IIR0 = 0,
226 IIR1,
227 IIR_MAX,
228};
229
230/* Each IIR has 5 Filter Stages */
231enum {
232 BAND1 = 0,
233 BAND2,
234 BAND3,
235 BAND4,
236 BAND5,
237 BAND_MAX,
238};
239
240struct rx_macro_idle_detect_config {
241 u8 hph_idle_thr;
242 u8 hph_idle_detect_en;
243};
244
245struct interp_sample_rate {
246 int sample_rate;
247 int rate_val;
248};
249
250static struct interp_sample_rate sr_val_tbl[] = {
251 {8000, 0x0}, {16000, 0x1}, {32000, 0x3}, {48000, 0x4}, {96000, 0x5},
252 {192000, 0x6}, {384000, 0x7}, {44100, 0x9}, {88200, 0xA},
253 {176400, 0xB}, {352800, 0xC},
254};
255
Aditya Bavanari4f3d5642018-09-18 22:19:10 +0530256struct rx_macro_bcl_pmic_params {
257 u8 id;
258 u8 sid;
259 u8 ppid;
260};
261
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530262static int rx_macro_hw_params(struct snd_pcm_substream *substream,
263 struct snd_pcm_hw_params *params,
264 struct snd_soc_dai *dai);
265static int rx_macro_get_channel_map(struct snd_soc_dai *dai,
266 unsigned int *tx_num, unsigned int *tx_slot,
267 unsigned int *rx_num, unsigned int *rx_slot);
268static int rx_macro_int_dem_inp_mux_put(struct snd_kcontrol *kcontrol,
269 struct snd_ctl_elem_value *ucontrol);
270static int rx_macro_mux_get(struct snd_kcontrol *kcontrol,
271 struct snd_ctl_elem_value *ucontrol);
272static int rx_macro_mux_put(struct snd_kcontrol *kcontrol,
273 struct snd_ctl_elem_value *ucontrol);
Meng Wang15c825d2018-09-06 10:49:18 +0800274static int rx_macro_enable_interp_clk(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530275 int event, int interp_idx);
276
277/* Hold instance to soundwire platform device */
278struct rx_swr_ctrl_data {
279 struct platform_device *rx_swr_pdev;
280};
281
282struct rx_swr_ctrl_platform_data {
283 void *handle; /* holds codec private data */
284 int (*read)(void *handle, int reg);
285 int (*write)(void *handle, int reg, int val);
286 int (*bulk_write)(void *handle, u32 *reg, u32 *val, size_t len);
287 int (*clk)(void *handle, bool enable);
288 int (*handle_irq)(void *handle,
289 irqreturn_t (*swrm_irq_handler)(int irq,
290 void *data),
291 void *swrm_handle,
292 int action);
293};
294
295enum {
Laxminath Kasam59c7a1d2018-08-09 16:11:17 +0530296 RX_MACRO_AIF_INVALID = 0,
297 RX_MACRO_AIF1_PB,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530298 RX_MACRO_AIF2_PB,
299 RX_MACRO_AIF3_PB,
300 RX_MACRO_AIF4_PB,
301 RX_MACRO_MAX_DAIS,
302};
303
304enum {
305 RX_MACRO_AIF1_CAP = 0,
306 RX_MACRO_AIF2_CAP,
307 RX_MACRO_AIF3_CAP,
308 RX_MACRO_MAX_AIF_CAP_DAIS
309};
310/*
311 * @dev: rx macro device pointer
312 * @comp_enabled: compander enable mixer value set
313 * @prim_int_users: Users of interpolator
314 * @rx_mclk_users: RX MCLK users count
315 * @vi_feed_value: VI sense mask
316 * @swr_clk_lock: to lock swr master clock operations
317 * @swr_ctrl_data: SoundWire data structure
318 * @swr_plat_data: Soundwire platform data
319 * @rx_macro_add_child_devices_work: work for adding child devices
320 * @rx_swr_gpio_p: used by pinctrl API
321 * @rx_core_clk: MCLK for rx macro
322 * @rx_npl_clk: NPL clock for RX soundwire
Meng Wang15c825d2018-09-06 10:49:18 +0800323 * @component: codec handle
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530324 */
325struct rx_macro_priv {
326 struct device *dev;
327 int comp_enabled[RX_MACRO_COMP_MAX];
328 /* Main path clock users count */
329 int main_clk_users[INTERP_MAX];
330 int rx_port_value[RX_MACRO_PORTS_MAX];
331 u16 prim_int_users[INTERP_MAX];
332 int rx_mclk_users;
333 int swr_clk_users;
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +0530334 int clsh_users;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530335 int rx_mclk_cnt;
Laxminath Kasambee08192018-07-01 14:38:55 +0530336 bool is_native_on;
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +0530337 bool is_ear_mode_on;
Laxminath Kasam701e3582018-10-15 20:06:09 +0530338 bool dev_up;
Laxminath Kasamde09dfb2018-11-09 13:00:30 +0530339 bool hph_pwr_mode;
Laxminath Kasamd3ffb332018-11-14 19:59:21 +0530340 bool hph_hd2_mode;
Laxminath Kasambee08192018-07-01 14:38:55 +0530341 u16 mclk_mux;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530342 struct mutex mclk_lock;
343 struct mutex swr_clk_lock;
344 struct rx_swr_ctrl_data *swr_ctrl_data;
345 struct rx_swr_ctrl_platform_data swr_plat_data;
346 struct work_struct rx_macro_add_child_devices_work;
347 struct device_node *rx_swr_gpio_p;
348 struct clk *rx_core_clk;
349 struct clk *rx_npl_clk;
Meng Wang15c825d2018-09-06 10:49:18 +0800350 struct snd_soc_component *component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530351 unsigned long active_ch_mask[RX_MACRO_MAX_DAIS];
352 unsigned long active_ch_cnt[RX_MACRO_MAX_DAIS];
353 u16 bit_width[RX_MACRO_MAX_DAIS];
354 char __iomem *rx_io_base;
355 char __iomem *rx_mclk_mode_muxsel;
356 struct rx_macro_idle_detect_config idle_det_cfg;
357 u8 sidetone_coeff_array[IIR_MAX][BAND_MAX]
358 [RX_MACRO_SIDETONE_IIR_COEFF_MAX * 4];
359
360 struct platform_device *pdev_child_devices
361 [RX_MACRO_CHILD_DEVICES_MAX];
362 int child_count;
Aditya Bavanari4f3d5642018-09-18 22:19:10 +0530363 int is_softclip_on;
364 int softclip_clk_users;
365 struct rx_macro_bcl_pmic_params bcl_pmic_params;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530366};
367
368static struct snd_soc_dai_driver rx_macro_dai[];
369static const DECLARE_TLV_DB_SCALE(digital_gain, 0, 1, 0);
370
371static const char * const rx_int_mix_mux_text[] = {
372 "ZERO", "RX0", "RX1", "RX2", "RX3", "RX4", "RX5"
373};
374
375static const char * const rx_prim_mix_text[] = {
376 "ZERO", "DEC0", "DEC1", "IIR0", "IIR1", "RX0", "RX1", "RX2",
377 "RX3", "RX4", "RX5"
378};
379
380static const char * const rx_sidetone_mix_text[] = {
381 "ZERO", "SRC0", "SRC1", "SRC_SUM"
382};
383
384static const char * const rx_echo_mux_text[] = {
385 "ZERO", "RX_MIX0", "RX_MIX1", "RX_MIX2"
386};
387
388static const char * const iir_inp_mux_text[] = {
389 "ZERO", "DEC0", "DEC1", "DEC2", "DEC3",
390 "RX0", "RX1", "RX2", "RX3", "RX4", "RX5"
391};
392
393static const char * const rx_int_dem_inp_mux_text[] = {
394 "NORMAL_DSM_OUT", "CLSH_DSM_OUT",
395};
396
397static const char * const rx_int0_1_interp_mux_text[] = {
398 "ZERO", "RX INT0_1 MIX1",
399};
400
401static const char * const rx_int1_1_interp_mux_text[] = {
402 "ZERO", "RX INT1_1 MIX1",
403};
404
405static const char * const rx_int2_1_interp_mux_text[] = {
406 "ZERO", "RX INT2_1 MIX1",
407};
408
409static const char * const rx_int0_2_interp_mux_text[] = {
410 "ZERO", "RX INT0_2 MUX",
411};
412
413static const char * const rx_int1_2_interp_mux_text[] = {
414 "ZERO", "RX INT1_2 MUX",
415};
416
417static const char * const rx_int2_2_interp_mux_text[] = {
418 "ZERO", "RX INT2_2 MUX",
419};
420
421static const char *const rx_macro_mux_text[] = {
422 "ZERO", "AIF1_PB", "AIF2_PB", "AIF3_PB", "AIF4_PB"
423};
424
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +0530425static const char *const rx_macro_ear_mode_text[] = {"OFF", "ON"};
426static const struct soc_enum rx_macro_ear_mode_enum =
427 SOC_ENUM_SINGLE_EXT(2, rx_macro_ear_mode_text);
428
Laxminath Kasamd3ffb332018-11-14 19:59:21 +0530429static const char *const rx_macro_hph_hd2_mode_text[] = {"OFF", "ON"};
430static const struct soc_enum rx_macro_hph_hd2_mode_enum =
431 SOC_ENUM_SINGLE_EXT(2, rx_macro_hph_hd2_mode_text);
432
Laxminath Kasamc21e98a2018-12-04 11:21:01 +0530433static const char *const rx_macro_hph_pwr_mode_text[] = {"ULP", "LOHIFI"};
Laxminath Kasamde09dfb2018-11-09 13:00:30 +0530434static const struct soc_enum rx_macro_hph_pwr_mode_enum =
435 SOC_ENUM_SINGLE_EXT(2, rx_macro_hph_pwr_mode_text);
436
Aditya Bavanari4f3d5642018-09-18 22:19:10 +0530437static const char * const rx_macro_vbat_bcl_gsm_mode_text[] = {"OFF", "ON"};
438static const struct soc_enum rx_macro_vbat_bcl_gsm_mode_enum =
439 SOC_ENUM_SINGLE_EXT(2, rx_macro_vbat_bcl_gsm_mode_text);
440
441static const struct snd_kcontrol_new rx_int2_1_vbat_mix_switch[] = {
442 SOC_DAPM_SINGLE("RX AUX VBAT Enable", SND_SOC_NOPM, 0, 1, 0)
443};
444
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530445RX_MACRO_DAPM_ENUM(rx_int0_2, BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG1, 0,
446 rx_int_mix_mux_text);
447RX_MACRO_DAPM_ENUM(rx_int1_2, BOLERO_CDC_RX_INP_MUX_RX_INT1_CFG1, 0,
448 rx_int_mix_mux_text);
449RX_MACRO_DAPM_ENUM(rx_int2_2, BOLERO_CDC_RX_INP_MUX_RX_INT2_CFG1, 0,
450 rx_int_mix_mux_text);
451
452
453RX_MACRO_DAPM_ENUM(rx_int0_1_mix_inp0, BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG0, 0,
454 rx_prim_mix_text);
455RX_MACRO_DAPM_ENUM(rx_int0_1_mix_inp1, BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG0, 4,
456 rx_prim_mix_text);
457RX_MACRO_DAPM_ENUM(rx_int0_1_mix_inp2, BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG1, 4,
458 rx_prim_mix_text);
459RX_MACRO_DAPM_ENUM(rx_int1_1_mix_inp0, BOLERO_CDC_RX_INP_MUX_RX_INT1_CFG0, 0,
460 rx_prim_mix_text);
461RX_MACRO_DAPM_ENUM(rx_int1_1_mix_inp1, BOLERO_CDC_RX_INP_MUX_RX_INT1_CFG0, 4,
462 rx_prim_mix_text);
463RX_MACRO_DAPM_ENUM(rx_int1_1_mix_inp2, BOLERO_CDC_RX_INP_MUX_RX_INT1_CFG1, 4,
464 rx_prim_mix_text);
465RX_MACRO_DAPM_ENUM(rx_int2_1_mix_inp0, BOLERO_CDC_RX_INP_MUX_RX_INT2_CFG0, 0,
466 rx_prim_mix_text);
467RX_MACRO_DAPM_ENUM(rx_int2_1_mix_inp1, BOLERO_CDC_RX_INP_MUX_RX_INT2_CFG0, 4,
468 rx_prim_mix_text);
469RX_MACRO_DAPM_ENUM(rx_int2_1_mix_inp2, BOLERO_CDC_RX_INP_MUX_RX_INT2_CFG1, 4,
470 rx_prim_mix_text);
471
472RX_MACRO_DAPM_ENUM(rx_int0_mix2_inp, BOLERO_CDC_RX_INP_MUX_SIDETONE_SRC_CFG0, 2,
473 rx_sidetone_mix_text);
474RX_MACRO_DAPM_ENUM(rx_int1_mix2_inp, BOLERO_CDC_RX_INP_MUX_SIDETONE_SRC_CFG0, 4,
475 rx_sidetone_mix_text);
476RX_MACRO_DAPM_ENUM(rx_int2_mix2_inp, BOLERO_CDC_RX_INP_MUX_SIDETONE_SRC_CFG0, 6,
477 rx_sidetone_mix_text);
478
479RX_MACRO_DAPM_ENUM(rx_mix_tx0, BOLERO_CDC_RX_INP_MUX_RX_MIX_CFG4, 4,
480 rx_echo_mux_text);
481RX_MACRO_DAPM_ENUM(rx_mix_tx1, BOLERO_CDC_RX_INP_MUX_RX_MIX_CFG4, 0,
482 rx_echo_mux_text);
483RX_MACRO_DAPM_ENUM(rx_mix_tx2, BOLERO_CDC_RX_INP_MUX_RX_MIX_CFG4, 0,
484 rx_echo_mux_text);
485
486RX_MACRO_DAPM_ENUM(iir0_inp0, BOLERO_CDC_RX_IIR_INP_MUX_IIR0_MIX_CFG0, 0,
487 iir_inp_mux_text);
488RX_MACRO_DAPM_ENUM(iir0_inp1, BOLERO_CDC_RX_IIR_INP_MUX_IIR0_MIX_CFG1, 0,
489 iir_inp_mux_text);
490RX_MACRO_DAPM_ENUM(iir0_inp2, BOLERO_CDC_RX_IIR_INP_MUX_IIR0_MIX_CFG2, 0,
491 iir_inp_mux_text);
492RX_MACRO_DAPM_ENUM(iir0_inp3, BOLERO_CDC_RX_IIR_INP_MUX_IIR0_MIX_CFG3, 0,
493 iir_inp_mux_text);
494RX_MACRO_DAPM_ENUM(iir1_inp0, BOLERO_CDC_RX_IIR_INP_MUX_IIR1_MIX_CFG0, 0,
495 iir_inp_mux_text);
496RX_MACRO_DAPM_ENUM(iir1_inp1, BOLERO_CDC_RX_IIR_INP_MUX_IIR1_MIX_CFG1, 0,
497 iir_inp_mux_text);
498RX_MACRO_DAPM_ENUM(iir1_inp2, BOLERO_CDC_RX_IIR_INP_MUX_IIR1_MIX_CFG2, 0,
499 iir_inp_mux_text);
500RX_MACRO_DAPM_ENUM(iir1_inp3, BOLERO_CDC_RX_IIR_INP_MUX_IIR1_MIX_CFG3, 0,
501 iir_inp_mux_text);
502
503RX_MACRO_DAPM_ENUM(rx_int0_1_interp, SND_SOC_NOPM, 0,
504 rx_int0_1_interp_mux_text);
505RX_MACRO_DAPM_ENUM(rx_int1_1_interp, SND_SOC_NOPM, 0,
506 rx_int1_1_interp_mux_text);
507RX_MACRO_DAPM_ENUM(rx_int2_1_interp, SND_SOC_NOPM, 0,
508 rx_int2_1_interp_mux_text);
509
510RX_MACRO_DAPM_ENUM(rx_int0_2_interp, SND_SOC_NOPM, 0,
511 rx_int0_2_interp_mux_text);
512RX_MACRO_DAPM_ENUM(rx_int1_2_interp, SND_SOC_NOPM, 0,
513 rx_int1_2_interp_mux_text);
514RX_MACRO_DAPM_ENUM(rx_int2_2_interp, SND_SOC_NOPM, 0,
515 rx_int2_2_interp_mux_text);
516
517RX_MACRO_DAPM_ENUM_EXT(rx_int0_dem_inp, BOLERO_CDC_RX_RX0_RX_PATH_CFG1, 0,
518 rx_int_dem_inp_mux_text, snd_soc_dapm_get_enum_double,
519 rx_macro_int_dem_inp_mux_put);
520RX_MACRO_DAPM_ENUM_EXT(rx_int1_dem_inp, BOLERO_CDC_RX_RX1_RX_PATH_CFG1, 0,
521 rx_int_dem_inp_mux_text, snd_soc_dapm_get_enum_double,
522 rx_macro_int_dem_inp_mux_put);
523
524RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx0, SND_SOC_NOPM, 0, rx_macro_mux_text,
525 rx_macro_mux_get, rx_macro_mux_put);
526RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx1, SND_SOC_NOPM, 0, rx_macro_mux_text,
527 rx_macro_mux_get, rx_macro_mux_put);
528RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx2, SND_SOC_NOPM, 0, rx_macro_mux_text,
529 rx_macro_mux_get, rx_macro_mux_put);
530RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx3, SND_SOC_NOPM, 0, rx_macro_mux_text,
531 rx_macro_mux_get, rx_macro_mux_put);
532RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx4, SND_SOC_NOPM, 0, rx_macro_mux_text,
533 rx_macro_mux_get, rx_macro_mux_put);
534RX_MACRO_DAPM_ENUM_EXT(rx_macro_rx5, SND_SOC_NOPM, 0, rx_macro_mux_text,
535 rx_macro_mux_get, rx_macro_mux_put);
536
537static struct snd_soc_dai_ops rx_macro_dai_ops = {
538 .hw_params = rx_macro_hw_params,
539 .get_channel_map = rx_macro_get_channel_map,
540};
541
542static struct snd_soc_dai_driver rx_macro_dai[] = {
543 {
544 .name = "rx_macro_rx1",
545 .id = RX_MACRO_AIF1_PB,
546 .playback = {
547 .stream_name = "RX_MACRO_AIF1 Playback",
548 .rates = RX_MACRO_RATES | RX_MACRO_FRAC_RATES,
549 .formats = RX_MACRO_FORMATS,
550 .rate_max = 384000,
551 .rate_min = 8000,
552 .channels_min = 1,
553 .channels_max = 2,
554 },
555 .ops = &rx_macro_dai_ops,
556 },
557 {
558 .name = "rx_macro_rx2",
559 .id = RX_MACRO_AIF2_PB,
560 .playback = {
561 .stream_name = "RX_MACRO_AIF2 Playback",
562 .rates = RX_MACRO_RATES | RX_MACRO_FRAC_RATES,
563 .formats = RX_MACRO_FORMATS,
564 .rate_max = 384000,
565 .rate_min = 8000,
566 .channels_min = 1,
567 .channels_max = 2,
568 },
569 .ops = &rx_macro_dai_ops,
570 },
571 {
572 .name = "rx_macro_rx3",
573 .id = RX_MACRO_AIF3_PB,
574 .playback = {
575 .stream_name = "RX_MACRO_AIF3 Playback",
576 .rates = RX_MACRO_RATES | RX_MACRO_FRAC_RATES,
577 .formats = RX_MACRO_FORMATS,
578 .rate_max = 384000,
579 .rate_min = 8000,
580 .channels_min = 1,
581 .channels_max = 2,
582 },
583 .ops = &rx_macro_dai_ops,
584 },
585 {
586 .name = "rx_macro_rx4",
587 .id = RX_MACRO_AIF4_PB,
588 .playback = {
589 .stream_name = "RX_MACRO_AIF4 Playback",
590 .rates = RX_MACRO_RATES | RX_MACRO_FRAC_RATES,
591 .formats = RX_MACRO_FORMATS,
592 .rate_max = 384000,
593 .rate_min = 8000,
594 .channels_min = 1,
595 .channels_max = 2,
596 },
597 .ops = &rx_macro_dai_ops,
598 },
599};
600
Laxminath Kasam497a6512018-09-17 16:11:52 +0530601static int get_impedance_index(int imped)
602{
603 int i = 0;
604
605 if (imped < imped_index[i].imped_val) {
606 pr_debug("%s, detected impedance is less than %d Ohm\n",
607 __func__, imped_index[i].imped_val);
608 i = 0;
609 goto ret;
610 }
611 if (imped >= imped_index[ARRAY_SIZE(imped_index) - 1].imped_val) {
612 pr_debug("%s, detected impedance is greater than %d Ohm\n",
613 __func__,
614 imped_index[ARRAY_SIZE(imped_index) - 1].imped_val);
615 i = ARRAY_SIZE(imped_index) - 1;
616 goto ret;
617 }
618 for (i = 0; i < ARRAY_SIZE(imped_index) - 1; i++) {
619 if (imped >= imped_index[i].imped_val &&
620 imped < imped_index[i + 1].imped_val)
621 break;
622 }
623ret:
624 pr_debug("%s: selected impedance index = %d\n",
625 __func__, imped_index[i].index);
626 return imped_index[i].index;
627}
628
629/*
630 * rx_macro_wcd_clsh_imped_config -
631 * This function updates HPHL and HPHR gain settings
632 * according to the impedance value.
633 *
Meng Wang15c825d2018-09-06 10:49:18 +0800634 * @component: codec pointer handle
Laxminath Kasam497a6512018-09-17 16:11:52 +0530635 * @imped: impedance value of HPHL/R
636 * @reset: bool variable to reset registers when teardown
637 */
Meng Wang15c825d2018-09-06 10:49:18 +0800638static void rx_macro_wcd_clsh_imped_config(struct snd_soc_component *component,
Laxminath Kasam497a6512018-09-17 16:11:52 +0530639 int imped, bool reset)
640{
641 int i;
642 int index = 0;
643 int table_size;
644
645 static const struct rx_macro_reg_mask_val
646 (*imped_table_ptr)[MAX_IMPED_PARAMS];
647
648 table_size = ARRAY_SIZE(imped_table);
649 imped_table_ptr = imped_table;
650 /* reset = 1, which means request is to reset the register values */
651 if (reset) {
652 for (i = 0; i < MAX_IMPED_PARAMS; i++)
Meng Wang15c825d2018-09-06 10:49:18 +0800653 snd_soc_component_update_bits(component,
Laxminath Kasam497a6512018-09-17 16:11:52 +0530654 imped_table_ptr[index][i].reg,
655 imped_table_ptr[index][i].mask, 0);
656 return;
657 }
658 index = get_impedance_index(imped);
659 if (index >= (ARRAY_SIZE(imped_index) - 1)) {
660 pr_debug("%s, impedance not in range = %d\n", __func__, imped);
661 return;
662 }
663 if (index >= table_size) {
664 pr_debug("%s, impedance index not in range = %d\n", __func__,
665 index);
666 return;
667 }
668 for (i = 0; i < MAX_IMPED_PARAMS; i++)
Meng Wang15c825d2018-09-06 10:49:18 +0800669 snd_soc_component_update_bits(component,
Laxminath Kasam497a6512018-09-17 16:11:52 +0530670 imped_table_ptr[index][i].reg,
671 imped_table_ptr[index][i].mask,
672 imped_table_ptr[index][i].val);
673}
674
Meng Wang15c825d2018-09-06 10:49:18 +0800675static bool rx_macro_get_data(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530676 struct device **rx_dev,
677 struct rx_macro_priv **rx_priv,
678 const char *func_name)
679{
Meng Wang15c825d2018-09-06 10:49:18 +0800680 *rx_dev = bolero_get_device_ptr(component->dev, RX_MACRO);
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530681
682 if (!(*rx_dev)) {
Meng Wang15c825d2018-09-06 10:49:18 +0800683 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530684 "%s: null device for macro!\n", func_name);
685 return false;
686 }
687
688 *rx_priv = dev_get_drvdata((*rx_dev));
689 if (!(*rx_priv)) {
Meng Wang15c825d2018-09-06 10:49:18 +0800690 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530691 "%s: priv is null for macro!\n", func_name);
692 return false;
693 }
694
Meng Wang15c825d2018-09-06 10:49:18 +0800695 if (!(*rx_priv)->component) {
696 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530697 "%s: tx_priv codec is not initialized!\n", func_name);
698 return false;
699 }
700
701 return true;
702}
703
704static int rx_macro_int_dem_inp_mux_put(struct snd_kcontrol *kcontrol,
705 struct snd_ctl_elem_value *ucontrol)
706{
707 struct snd_soc_dapm_widget *widget =
708 snd_soc_dapm_kcontrol_widget(kcontrol);
Meng Wang15c825d2018-09-06 10:49:18 +0800709 struct snd_soc_component *component =
710 snd_soc_dapm_to_component(widget->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530711 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value;
712 unsigned int val = 0;
713 unsigned short look_ahead_dly_reg =
714 BOLERO_CDC_RX_RX0_RX_PATH_CFG0;
715
716 val = ucontrol->value.enumerated.item[0];
717 if (val >= e->items)
718 return -EINVAL;
719
Meng Wang15c825d2018-09-06 10:49:18 +0800720 dev_dbg(component->dev, "%s: wname: %s, val: 0x%x\n", __func__,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530721 widget->name, val);
722
723 if (e->reg == BOLERO_CDC_RX_RX0_RX_PATH_CFG1)
724 look_ahead_dly_reg = BOLERO_CDC_RX_RX0_RX_PATH_CFG0;
725 else if (e->reg == BOLERO_CDC_RX_RX1_RX_PATH_CFG1)
726 look_ahead_dly_reg = BOLERO_CDC_RX_RX1_RX_PATH_CFG0;
727
728 /* Set Look Ahead Delay */
Meng Wang15c825d2018-09-06 10:49:18 +0800729 snd_soc_component_update_bits(component, look_ahead_dly_reg,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530730 0x08, (val ? 0x08 : 0x00));
731 /* Set DEM INP Select */
732 return snd_soc_dapm_put_enum_double(kcontrol, ucontrol);
733}
734
735static int rx_macro_set_prim_interpolator_rate(struct snd_soc_dai *dai,
736 u8 rate_reg_val,
737 u32 sample_rate)
738{
739 u8 int_1_mix1_inp = 0;
740 u32 j = 0, port = 0;
741 u16 int_mux_cfg0 = 0, int_mux_cfg1 = 0;
742 u16 int_fs_reg = 0;
743 u8 int_mux_cfg0_val = 0, int_mux_cfg1_val = 0;
744 u8 inp0_sel = 0, inp1_sel = 0, inp2_sel = 0;
Meng Wang15c825d2018-09-06 10:49:18 +0800745 struct snd_soc_component *component = dai->component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530746 struct device *rx_dev = NULL;
747 struct rx_macro_priv *rx_priv = NULL;
748
Meng Wang15c825d2018-09-06 10:49:18 +0800749 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530750 return -EINVAL;
751
752 for_each_set_bit(port, &rx_priv->active_ch_mask[dai->id],
753 RX_MACRO_PORTS_MAX) {
754 int_1_mix1_inp = port;
755 if ((int_1_mix1_inp < RX_MACRO_RX0) ||
756 (int_1_mix1_inp > RX_MACRO_PORTS_MAX)) {
757 pr_err("%s: Invalid RX port, Dai ID is %d\n",
758 __func__, dai->id);
759 return -EINVAL;
760 }
761
762 int_mux_cfg0 = BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG0;
763
764 /*
765 * Loop through all interpolator MUX inputs and find out
766 * to which interpolator input, the rx port
767 * is connected
768 */
769 for (j = 0; j < INTERP_MAX; j++) {
770 int_mux_cfg1 = int_mux_cfg0 + 4;
771
Meng Wang15c825d2018-09-06 10:49:18 +0800772 int_mux_cfg0_val = snd_soc_component_read32(
773 component, int_mux_cfg0);
774 int_mux_cfg1_val = snd_soc_component_read32(
775 component, int_mux_cfg1);
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530776 inp0_sel = int_mux_cfg0_val & 0x07;
777 inp1_sel = (int_mux_cfg0_val >> 4) & 0x038;
778 inp2_sel = (int_mux_cfg1_val >> 4) & 0x038;
779 if ((inp0_sel == int_1_mix1_inp) ||
780 (inp1_sel == int_1_mix1_inp) ||
781 (inp2_sel == int_1_mix1_inp)) {
782 int_fs_reg = BOLERO_CDC_RX_RX0_RX_PATH_CTL +
783 0x80 * j;
784 pr_debug("%s: AIF_PB DAI(%d) connected to INT%u_1\n",
785 __func__, dai->id, j);
786 pr_debug("%s: set INT%u_1 sample rate to %u\n",
787 __func__, j, sample_rate);
788 /* sample_rate is in Hz */
Meng Wang15c825d2018-09-06 10:49:18 +0800789 snd_soc_component_update_bits(component,
790 int_fs_reg,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530791 0x0F, rate_reg_val);
792 }
793 int_mux_cfg0 += 8;
794 }
795 }
796
797 return 0;
798}
799
800static int rx_macro_set_mix_interpolator_rate(struct snd_soc_dai *dai,
801 u8 rate_reg_val,
802 u32 sample_rate)
803{
804 u8 int_2_inp = 0;
805 u32 j = 0, port = 0;
806 u16 int_mux_cfg1 = 0, int_fs_reg = 0;
807 u8 int_mux_cfg1_val = 0;
Meng Wang15c825d2018-09-06 10:49:18 +0800808 struct snd_soc_component *component = dai->component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530809 struct device *rx_dev = NULL;
810 struct rx_macro_priv *rx_priv = NULL;
811
Meng Wang15c825d2018-09-06 10:49:18 +0800812 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530813 return -EINVAL;
814
815 for_each_set_bit(port, &rx_priv->active_ch_mask[dai->id],
816 RX_MACRO_PORTS_MAX) {
817 int_2_inp = port;
818 if ((int_2_inp < RX_MACRO_RX0) ||
819 (int_2_inp > RX_MACRO_PORTS_MAX)) {
820 pr_err("%s: Invalid RX port, Dai ID is %d\n",
821 __func__, dai->id);
822 return -EINVAL;
823 }
824
825 int_mux_cfg1 = BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG1;
826 for (j = 0; j < INTERP_MAX; j++) {
Meng Wang15c825d2018-09-06 10:49:18 +0800827 int_mux_cfg1_val = snd_soc_component_read32(
828 component, int_mux_cfg1) &
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530829 0x07;
830 if (int_mux_cfg1_val == int_2_inp) {
831 int_fs_reg = BOLERO_CDC_RX_RX0_RX_PATH_MIX_CTL +
832 0x80 * j;
833 pr_debug("%s: AIF_PB DAI(%d) connected to INT%u_2\n",
834 __func__, dai->id, j);
835 pr_debug("%s: set INT%u_2 sample rate to %u\n",
836 __func__, j, sample_rate);
Meng Wang15c825d2018-09-06 10:49:18 +0800837 snd_soc_component_update_bits(
838 component, int_fs_reg,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530839 0x0F, rate_reg_val);
840 }
841 int_mux_cfg1 += 8;
842 }
843 }
844 return 0;
845}
846
Laxminath Kasamac396d52018-09-06 12:53:26 +0530847static bool rx_macro_is_fractional_sample_rate(u32 sample_rate)
848{
849 switch (sample_rate) {
850 case SAMPLING_RATE_44P1KHZ:
851 case SAMPLING_RATE_88P2KHZ:
852 case SAMPLING_RATE_176P4KHZ:
853 case SAMPLING_RATE_352P8KHZ:
854 return true;
855 default:
856 return false;
857 }
858 return false;
859}
860
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530861static int rx_macro_set_interpolator_rate(struct snd_soc_dai *dai,
862 u32 sample_rate)
863{
Meng Wang15c825d2018-09-06 10:49:18 +0800864 struct snd_soc_component *component = dai->component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530865 int rate_val = 0;
866 int i = 0, ret = 0;
Laxminath Kasamac396d52018-09-06 12:53:26 +0530867 struct device *rx_dev = NULL;
868 struct rx_macro_priv *rx_priv = NULL;
869
Meng Wang15c825d2018-09-06 10:49:18 +0800870 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamac396d52018-09-06 12:53:26 +0530871 return -EINVAL;
872
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530873
874 for (i = 0; i < ARRAY_SIZE(sr_val_tbl); i++) {
875 if (sample_rate == sr_val_tbl[i].sample_rate) {
876 rate_val = sr_val_tbl[i].rate_val;
Laxminath Kasamac396d52018-09-06 12:53:26 +0530877 if (rx_macro_is_fractional_sample_rate(sample_rate))
878 rx_priv->is_native_on = true;
879 else
880 rx_priv->is_native_on = false;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530881 break;
882 }
883 }
884 if ((i == ARRAY_SIZE(sr_val_tbl)) || (rate_val < 0)) {
Meng Wang15c825d2018-09-06 10:49:18 +0800885 dev_err(component->dev, "%s: Unsupported sample rate: %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530886 __func__, sample_rate);
887 return -EINVAL;
888 }
889
890 ret = rx_macro_set_prim_interpolator_rate(dai, (u8)rate_val, sample_rate);
891 if (ret)
892 return ret;
893 ret = rx_macro_set_mix_interpolator_rate(dai, (u8)rate_val, sample_rate);
894 if (ret)
895 return ret;
896
897 return ret;
898}
899
900static int rx_macro_hw_params(struct snd_pcm_substream *substream,
901 struct snd_pcm_hw_params *params,
902 struct snd_soc_dai *dai)
903{
Meng Wang15c825d2018-09-06 10:49:18 +0800904 struct snd_soc_component *component = dai->component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530905 int ret = 0;
906 struct device *rx_dev = NULL;
907 struct rx_macro_priv *rx_priv = NULL;
908
Meng Wang15c825d2018-09-06 10:49:18 +0800909 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530910 return -EINVAL;
911
Meng Wang15c825d2018-09-06 10:49:18 +0800912 dev_dbg(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530913 "%s: dai_name = %s DAI-ID %x rate %d num_ch %d\n", __func__,
914 dai->name, dai->id, params_rate(params),
915 params_channels(params));
916
917 switch (substream->stream) {
918 case SNDRV_PCM_STREAM_PLAYBACK:
919 ret = rx_macro_set_interpolator_rate(dai, params_rate(params));
920 if (ret) {
921 pr_err("%s: cannot set sample rate: %u\n",
922 __func__, params_rate(params));
923 return ret;
924 }
925 rx_priv->bit_width[dai->id] = params_width(params);
926 break;
927 case SNDRV_PCM_STREAM_CAPTURE:
928 default:
929 break;
930 }
931 return 0;
932}
933
934static int rx_macro_get_channel_map(struct snd_soc_dai *dai,
935 unsigned int *tx_num, unsigned int *tx_slot,
936 unsigned int *rx_num, unsigned int *rx_slot)
937{
Meng Wang15c825d2018-09-06 10:49:18 +0800938 struct snd_soc_component *component = dai->component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530939 struct device *rx_dev = NULL;
940 struct rx_macro_priv *rx_priv = NULL;
941 unsigned int temp = 0, ch_mask = 0;
942 u16 i = 0;
943
Meng Wang15c825d2018-09-06 10:49:18 +0800944 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530945 return -EINVAL;
946
947 switch (dai->id) {
948 case RX_MACRO_AIF1_PB:
949 case RX_MACRO_AIF2_PB:
950 case RX_MACRO_AIF3_PB:
951 case RX_MACRO_AIF4_PB:
952 for_each_set_bit(temp, &rx_priv->active_ch_mask[dai->id],
953 RX_MACRO_PORTS_MAX) {
Vatsal Bucha1a96a612018-11-26 13:04:56 +0530954 ch_mask |= (1 << temp);
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530955 if (++i == RX_MACRO_MAX_DMA_CH_PER_PORT)
956 break;
957 }
958 *rx_slot = ch_mask;
959 *rx_num = rx_priv->active_ch_cnt[dai->id];
960 break;
961 default:
962 dev_err(rx_dev, "%s: Invalid AIF\n", __func__);
963 break;
964 }
965 return 0;
966}
967
968static int rx_macro_mclk_enable(struct rx_macro_priv *rx_priv,
969 bool mclk_enable, bool dapm)
970{
971 struct regmap *regmap = dev_get_regmap(rx_priv->dev->parent, NULL);
Laxminath Kasambee08192018-07-01 14:38:55 +0530972 int ret = 0, mclk_mux = MCLK_MUX0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530973
Tanya Dixit8530fb92018-09-14 16:01:25 +0530974 if (regmap == NULL) {
975 dev_err(rx_priv->dev, "%s: regmap is NULL\n", __func__);
976 return -EINVAL;
977 }
978
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530979 dev_dbg(rx_priv->dev, "%s: mclk_enable = %u, dapm = %d clk_users= %d\n",
980 __func__, mclk_enable, dapm, rx_priv->rx_mclk_users);
981
982 mutex_lock(&rx_priv->mclk_lock);
983 if (mclk_enable) {
984 if (rx_priv->rx_mclk_users == 0) {
Laxminath Kasam7b9cdb62018-09-28 16:28:54 +0530985 if (rx_priv->is_native_on)
986 mclk_mux = MCLK_MUX1;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530987 ret = bolero_request_clock(rx_priv->dev,
Laxminath Kasambee08192018-07-01 14:38:55 +0530988 RX_MACRO, mclk_mux, true);
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530989 if (ret < 0) {
990 dev_err(rx_priv->dev,
991 "%s: rx request clock enable failed\n",
992 __func__);
993 goto exit;
994 }
Laxminath Kasambee08192018-07-01 14:38:55 +0530995 rx_priv->mclk_mux = mclk_mux;
Laxminath Kasama7ecc582018-06-15 16:55:02 +0530996 regcache_mark_dirty(regmap);
997 regcache_sync_region(regmap,
998 RX_START_OFFSET,
999 RX_MAX_OFFSET);
1000 regmap_update_bits(regmap,
1001 BOLERO_CDC_RX_CLK_RST_CTRL_MCLK_CONTROL,
1002 0x01, 0x01);
1003 regmap_update_bits(regmap,
Ramprasad Katkam9c2394a2018-08-23 13:13:48 +05301004 BOLERO_CDC_RX_CLK_RST_CTRL_MCLK_CONTROL,
1005 0x02, 0x02);
1006 regmap_update_bits(regmap,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301007 BOLERO_CDC_RX_CLK_RST_CTRL_FS_CNT_CONTROL,
1008 0x01, 0x01);
1009 }
1010 rx_priv->rx_mclk_users++;
1011 } else {
1012 if (rx_priv->rx_mclk_users <= 0) {
1013 dev_err(rx_priv->dev, "%s: clock already disabled\n",
1014 __func__);
1015 rx_priv->rx_mclk_users = 0;
1016 goto exit;
1017 }
1018 rx_priv->rx_mclk_users--;
1019 if (rx_priv->rx_mclk_users == 0) {
1020 regmap_update_bits(regmap,
1021 BOLERO_CDC_RX_CLK_RST_CTRL_FS_CNT_CONTROL,
1022 0x01, 0x00);
1023 regmap_update_bits(regmap,
1024 BOLERO_CDC_RX_CLK_RST_CTRL_MCLK_CONTROL,
1025 0x01, 0x00);
Laxminath Kasam7b9cdb62018-09-28 16:28:54 +05301026 mclk_mux = rx_priv->mclk_mux;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301027 bolero_request_clock(rx_priv->dev,
Laxminath Kasambee08192018-07-01 14:38:55 +05301028 RX_MACRO, mclk_mux, false);
1029 rx_priv->mclk_mux = MCLK_MUX0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301030 }
1031 }
1032exit:
1033 mutex_unlock(&rx_priv->mclk_lock);
1034 return ret;
1035}
1036
1037static int rx_macro_mclk_event(struct snd_soc_dapm_widget *w,
1038 struct snd_kcontrol *kcontrol, int event)
1039{
Meng Wang15c825d2018-09-06 10:49:18 +08001040 struct snd_soc_component *component =
1041 snd_soc_dapm_to_component(w->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301042 int ret = 0;
1043 struct device *rx_dev = NULL;
1044 struct rx_macro_priv *rx_priv = NULL;
Laxminath Kasamac396d52018-09-06 12:53:26 +05301045 int mclk_freq = MCLK_FREQ;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301046
Meng Wang15c825d2018-09-06 10:49:18 +08001047 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301048 return -EINVAL;
1049
1050 dev_dbg(rx_dev, "%s: event = %d\n", __func__, event);
1051 switch (event) {
1052 case SND_SOC_DAPM_PRE_PMU:
Laxminath Kasambee08192018-07-01 14:38:55 +05301053 /* if swr_clk_users > 0, call device down */
1054 if (rx_priv->swr_clk_users > 0) {
1055 if ((rx_priv->mclk_mux == MCLK_MUX0 &&
1056 rx_priv->is_native_on) ||
Laxminath Kasamac396d52018-09-06 12:53:26 +05301057 (rx_priv->mclk_mux == MCLK_MUX1 &&
Laxminath Kasambee08192018-07-01 14:38:55 +05301058 !rx_priv->is_native_on)) {
1059 swrm_wcd_notify(
1060 rx_priv->swr_ctrl_data[0].rx_swr_pdev,
1061 SWR_DEVICE_DOWN, NULL);
1062 }
1063 }
Laxminath Kasamac396d52018-09-06 12:53:26 +05301064 if (rx_priv->is_native_on)
1065 mclk_freq = MCLK_FREQ_NATIVE;
1066 swrm_wcd_notify(
1067 rx_priv->swr_ctrl_data[0].rx_swr_pdev,
1068 SWR_CLK_FREQ, &mclk_freq);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301069 ret = rx_macro_mclk_enable(rx_priv, 1, true);
1070 break;
1071 case SND_SOC_DAPM_POST_PMD:
1072 ret = rx_macro_mclk_enable(rx_priv, 0, true);
1073 break;
1074 default:
1075 dev_err(rx_priv->dev,
1076 "%s: invalid DAPM event %d\n", __func__, event);
1077 ret = -EINVAL;
1078 }
1079 return ret;
1080}
1081
1082static int rx_macro_mclk_ctrl(struct device *dev, bool enable)
1083{
1084 struct rx_macro_priv *rx_priv = dev_get_drvdata(dev);
1085 int ret = 0;
1086
1087 if (enable) {
1088 ret = clk_prepare_enable(rx_priv->rx_core_clk);
1089 if (ret < 0) {
1090 dev_err(dev, "%s:rx mclk enable failed\n", __func__);
1091 return ret;
1092 }
1093 ret = clk_prepare_enable(rx_priv->rx_npl_clk);
1094 if (ret < 0) {
1095 clk_disable_unprepare(rx_priv->rx_core_clk);
1096 dev_err(dev, "%s:rx npl_clk enable failed\n",
1097 __func__);
1098 return ret;
1099 }
Laxminath Kasam701e3582018-10-15 20:06:09 +05301100 if (rx_priv->rx_mclk_cnt++ == 0) {
1101 if (rx_priv->dev_up)
1102 iowrite32(0x1, rx_priv->rx_mclk_mode_muxsel);
1103 }
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301104 } else {
1105 if (rx_priv->rx_mclk_cnt <= 0) {
1106 dev_dbg(dev, "%s:rx mclk already disabled\n", __func__);
1107 rx_priv->rx_mclk_cnt = 0;
1108 return 0;
1109 }
Laxminath Kasam701e3582018-10-15 20:06:09 +05301110 if (--rx_priv->rx_mclk_cnt == 0) {
1111 if (rx_priv->dev_up)
1112 iowrite32(0x0, rx_priv->rx_mclk_mode_muxsel);
1113 }
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301114 clk_disable_unprepare(rx_priv->rx_npl_clk);
1115 clk_disable_unprepare(rx_priv->rx_core_clk);
1116 }
1117
1118 return 0;
1119}
1120
Meng Wang15c825d2018-09-06 10:49:18 +08001121static int rx_macro_event_handler(struct snd_soc_component *component,
1122 u16 event, u32 data)
Laxminath Kasam497a6512018-09-17 16:11:52 +05301123{
Vatsal Bucha53b4e142018-11-13 19:36:25 +05301124 u16 reg = 0, reg_mix = 0, rx_idx = 0, mute = 0x0, val = 0;
Laxminath Kasam497a6512018-09-17 16:11:52 +05301125 struct device *rx_dev = NULL;
1126 struct rx_macro_priv *rx_priv = NULL;
1127
Meng Wang15c825d2018-09-06 10:49:18 +08001128 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasam497a6512018-09-17 16:11:52 +05301129 return -EINVAL;
1130
1131 switch (event) {
1132 case BOLERO_MACRO_EVT_RX_MUTE:
1133 rx_idx = data >> 0x10;
1134 mute = data & 0xffff;
Vatsal Bucha53b4e142018-11-13 19:36:25 +05301135 val = mute ? 0x10 : 0x00;
Laxminath Kasam497a6512018-09-17 16:11:52 +05301136 reg = BOLERO_CDC_RX_RX0_RX_PATH_CTL + (rx_idx *
1137 RX_MACRO_RX_PATH_OFFSET);
1138 reg_mix = BOLERO_CDC_RX_RX0_RX_PATH_MIX_CTL + (rx_idx *
1139 RX_MACRO_RX_PATH_OFFSET);
Meng Wang15c825d2018-09-06 10:49:18 +08001140 snd_soc_component_update_bits(component, reg,
1141 0x10, val);
1142 snd_soc_component_update_bits(component, reg_mix,
1143 0x10, val);
Laxminath Kasam497a6512018-09-17 16:11:52 +05301144 break;
1145 case BOLERO_MACRO_EVT_IMPED_TRUE:
Meng Wang15c825d2018-09-06 10:49:18 +08001146 rx_macro_wcd_clsh_imped_config(component, data, true);
Laxminath Kasam497a6512018-09-17 16:11:52 +05301147 break;
1148 case BOLERO_MACRO_EVT_IMPED_FALSE:
Meng Wang15c825d2018-09-06 10:49:18 +08001149 rx_macro_wcd_clsh_imped_config(component, data, false);
Laxminath Kasam497a6512018-09-17 16:11:52 +05301150 break;
Laxminath Kasamfb0d6832018-09-22 01:49:52 +05301151 case BOLERO_MACRO_EVT_SSR_DOWN:
Laxminath Kasam701e3582018-10-15 20:06:09 +05301152 rx_priv->dev_up = false;
Laxminath Kasamfb0d6832018-09-22 01:49:52 +05301153 swrm_wcd_notify(
1154 rx_priv->swr_ctrl_data[0].rx_swr_pdev,
1155 SWR_DEVICE_SSR_DOWN, NULL);
1156 swrm_wcd_notify(
1157 rx_priv->swr_ctrl_data[0].rx_swr_pdev,
1158 SWR_DEVICE_DOWN, NULL);
1159 break;
1160 case BOLERO_MACRO_EVT_SSR_UP:
Laxminath Kasam701e3582018-10-15 20:06:09 +05301161 rx_priv->dev_up = true;
1162 /* enable&disable MCLK_MUX1 to reset GFMUX reg */
1163 bolero_request_clock(rx_priv->dev,
1164 RX_MACRO, MCLK_MUX1, true);
1165 bolero_request_clock(rx_priv->dev,
1166 RX_MACRO, MCLK_MUX1, false);
Laxminath Kasamfb0d6832018-09-22 01:49:52 +05301167 swrm_wcd_notify(
1168 rx_priv->swr_ctrl_data[0].rx_swr_pdev,
1169 SWR_DEVICE_SSR_UP, NULL);
1170 break;
Laxminath Kasam497a6512018-09-17 16:11:52 +05301171 }
1172 return 0;
1173}
1174
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301175static int rx_macro_find_playback_dai_id_for_port(int port_id,
1176 struct rx_macro_priv *rx_priv)
1177{
1178 int i = 0;
1179
1180 for (i = RX_MACRO_AIF1_PB; i < RX_MACRO_MAX_DAIS; i++) {
1181 if (test_bit(port_id, &rx_priv->active_ch_mask[i]))
1182 return i;
1183 }
1184
1185 return -EINVAL;
1186}
1187
Meng Wang15c825d2018-09-06 10:49:18 +08001188static int rx_macro_set_idle_detect_thr(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301189 struct rx_macro_priv *rx_priv,
1190 int interp, int path_type)
1191{
1192 int port_id[4] = { 0, 0, 0, 0 };
Laxminath Kasamb7f823c2018-08-02 13:23:11 +05301193 int *port_ptr = NULL;
1194 int num_ports = 0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301195 int bit_width = 0, i = 0;
1196 int mux_reg = 0, mux_reg_val = 0;
1197 int dai_id = 0, idle_thr = 0;
1198
1199 if ((interp != INTERP_HPHL) && (interp != INTERP_HPHR))
1200 return 0;
1201
1202 if (!rx_priv->idle_det_cfg.hph_idle_detect_en)
1203 return 0;
1204
1205 port_ptr = &port_id[0];
1206 num_ports = 0;
1207
1208 /*
1209 * Read interpolator MUX input registers and find
1210 * which cdc_dma port is connected and store the port
1211 * numbers in port_id array.
1212 */
1213 if (path_type == INTERP_MIX_PATH) {
1214 mux_reg = BOLERO_CDC_RX_INP_MUX_RX_INT0_CFG1 +
1215 2 * interp;
Meng Wang15c825d2018-09-06 10:49:18 +08001216 mux_reg_val = snd_soc_component_read32(component, mux_reg) &
1217 0x0f;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301218
1219 if ((mux_reg_val >= INTn_2_INP_SEL_RX0) &&
1220 (mux_reg_val <= INTn_2_INP_SEL_RX5)) {
1221 *port_ptr++ = mux_reg_val - 1;
1222 num_ports++;
1223 }
1224 }
1225
1226 if (path_type == INTERP_MAIN_PATH) {
1227 mux_reg = BOLERO_CDC_RX_INP_MUX_RX_INT1_CFG0 +
1228 2 * (interp - 1);
Meng Wang15c825d2018-09-06 10:49:18 +08001229 mux_reg_val = snd_soc_component_read32(component, mux_reg) &
1230 0x0f;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301231 i = RX_MACRO_INTERP_MUX_NUM_INPUTS;
1232
1233 while (i) {
1234 if ((mux_reg_val >= INTn_1_INP_SEL_RX0) &&
1235 (mux_reg_val <= INTn_1_INP_SEL_RX5)) {
1236 *port_ptr++ = mux_reg_val -
1237 INTn_1_INP_SEL_RX0;
1238 num_ports++;
1239 }
Meng Wang15c825d2018-09-06 10:49:18 +08001240 mux_reg_val =
1241 (snd_soc_component_read32(component, mux_reg) &
1242 0xf0) >> 4;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301243 mux_reg += 1;
1244 i--;
1245 }
1246 }
1247
Meng Wang15c825d2018-09-06 10:49:18 +08001248 dev_dbg(component->dev, "%s: num_ports: %d, ports[%d %d %d %d]\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301249 __func__, num_ports, port_id[0], port_id[1],
1250 port_id[2], port_id[3]);
1251
1252 i = 0;
1253 while (num_ports) {
1254 dai_id = rx_macro_find_playback_dai_id_for_port(port_id[i++],
1255 rx_priv);
1256
1257 if ((dai_id >= 0) && (dai_id < RX_MACRO_MAX_DAIS)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001258 dev_dbg(component->dev, "%s: dai_id: %d bit_width: %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301259 __func__, dai_id,
1260 rx_priv->bit_width[dai_id]);
1261
1262 if (rx_priv->bit_width[dai_id] > bit_width)
1263 bit_width = rx_priv->bit_width[dai_id];
1264 }
1265 num_ports--;
1266 }
1267
1268 switch (bit_width) {
1269 case 16:
1270 idle_thr = 0xff; /* F16 */
1271 break;
1272 case 24:
1273 case 32:
1274 idle_thr = 0x03; /* F22 */
1275 break;
1276 default:
1277 idle_thr = 0x00;
1278 break;
1279 }
1280
Meng Wang15c825d2018-09-06 10:49:18 +08001281 dev_dbg(component->dev, "%s: (new) idle_thr: %d, (cur) idle_thr: %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301282 __func__, idle_thr, rx_priv->idle_det_cfg.hph_idle_thr);
1283
1284 if ((rx_priv->idle_det_cfg.hph_idle_thr == 0) ||
1285 (idle_thr < rx_priv->idle_det_cfg.hph_idle_thr)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001286 snd_soc_component_write(component,
1287 BOLERO_CDC_RX_IDLE_DETECT_CFG3, idle_thr);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301288 rx_priv->idle_det_cfg.hph_idle_thr = idle_thr;
1289 }
1290
1291 return 0;
1292}
1293
1294static int rx_macro_enable_mix_path(struct snd_soc_dapm_widget *w,
1295 struct snd_kcontrol *kcontrol, int event)
1296{
Meng Wang15c825d2018-09-06 10:49:18 +08001297 struct snd_soc_component *component =
1298 snd_soc_dapm_to_component(w->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301299 u16 gain_reg = 0, mix_reg = 0;
1300 struct device *rx_dev = NULL;
1301 struct rx_macro_priv *rx_priv = NULL;
1302
Meng Wang15c825d2018-09-06 10:49:18 +08001303 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301304 return -EINVAL;
1305
1306 if (w->shift >= INTERP_MAX) {
Meng Wang15c825d2018-09-06 10:49:18 +08001307 dev_err(component->dev, "%s: Invalid Interpolator value %d for name %s\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301308 __func__, w->shift, w->name);
1309 return -EINVAL;
1310 }
1311
1312 gain_reg = BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL +
1313 (w->shift * RX_MACRO_RX_PATH_OFFSET);
1314 mix_reg = BOLERO_CDC_RX_RX0_RX_PATH_MIX_CTL +
1315 (w->shift * RX_MACRO_RX_PATH_OFFSET);
1316
Meng Wang15c825d2018-09-06 10:49:18 +08001317 dev_dbg(component->dev, "%s %d %s\n", __func__, event, w->name);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301318
1319 switch (event) {
1320 case SND_SOC_DAPM_PRE_PMU:
Meng Wang15c825d2018-09-06 10:49:18 +08001321 rx_macro_set_idle_detect_thr(component, rx_priv, w->shift,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301322 INTERP_MIX_PATH);
Meng Wang15c825d2018-09-06 10:49:18 +08001323 rx_macro_enable_interp_clk(component, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301324 /* Clk enable */
Meng Wang15c825d2018-09-06 10:49:18 +08001325 snd_soc_component_update_bits(component, mix_reg, 0x20, 0x20);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301326 break;
1327 case SND_SOC_DAPM_POST_PMU:
Meng Wang15c825d2018-09-06 10:49:18 +08001328 snd_soc_component_write(component, gain_reg,
1329 snd_soc_component_read32(component, gain_reg));
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301330 break;
1331 case SND_SOC_DAPM_POST_PMD:
1332 /* Clk Disable */
Meng Wang15c825d2018-09-06 10:49:18 +08001333 snd_soc_component_update_bits(component, mix_reg, 0x20, 0x00);
1334 rx_macro_enable_interp_clk(component, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301335 /* Reset enable and disable */
Meng Wang15c825d2018-09-06 10:49:18 +08001336 snd_soc_component_update_bits(component, mix_reg, 0x40, 0x40);
1337 snd_soc_component_update_bits(component, mix_reg, 0x40, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301338 break;
1339 }
1340
1341 return 0;
1342}
1343
1344static int rx_macro_enable_main_path(struct snd_soc_dapm_widget *w,
1345 struct snd_kcontrol *kcontrol,
1346 int event)
1347{
Meng Wang15c825d2018-09-06 10:49:18 +08001348 struct snd_soc_component *component =
1349 snd_soc_dapm_to_component(w->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301350 u16 gain_reg = 0;
1351 u16 reg = 0;
1352 struct device *rx_dev = NULL;
1353 struct rx_macro_priv *rx_priv = NULL;
1354
Meng Wang15c825d2018-09-06 10:49:18 +08001355 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301356 return -EINVAL;
1357
Meng Wang15c825d2018-09-06 10:49:18 +08001358 dev_dbg(component->dev, "%s %d %s\n", __func__, event, w->name);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301359
1360 if (w->shift >= INTERP_MAX) {
Meng Wang15c825d2018-09-06 10:49:18 +08001361 dev_err(component->dev, "%s: Invalid Interpolator value %d for name %s\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301362 __func__, w->shift, w->name);
1363 return -EINVAL;
1364 }
1365
1366 reg = BOLERO_CDC_RX_RX0_RX_PATH_CTL + (w->shift *
1367 RX_MACRO_RX_PATH_OFFSET);
1368 gain_reg = BOLERO_CDC_RX_RX0_RX_VOL_CTL + (w->shift *
1369 RX_MACRO_RX_PATH_OFFSET);
1370
1371 switch (event) {
1372 case SND_SOC_DAPM_PRE_PMU:
Meng Wang15c825d2018-09-06 10:49:18 +08001373 rx_macro_set_idle_detect_thr(component, rx_priv, w->shift,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301374 INTERP_MAIN_PATH);
Meng Wang15c825d2018-09-06 10:49:18 +08001375 rx_macro_enable_interp_clk(component, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301376 break;
1377 case SND_SOC_DAPM_POST_PMU:
Meng Wang15c825d2018-09-06 10:49:18 +08001378 snd_soc_component_write(component, gain_reg,
1379 snd_soc_component_read32(component, gain_reg));
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301380 break;
1381 case SND_SOC_DAPM_POST_PMD:
Meng Wang15c825d2018-09-06 10:49:18 +08001382 rx_macro_enable_interp_clk(component, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301383 break;
1384 }
1385
1386 return 0;
1387}
1388
Meng Wang15c825d2018-09-06 10:49:18 +08001389static int rx_macro_config_compander(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301390 struct rx_macro_priv *rx_priv,
1391 int interp_n, int event)
1392{
1393 int comp = 0;
1394 u16 comp_ctl0_reg = 0, rx_path_cfg0_reg = 0;
1395
1396 /* AUX does not have compander */
1397 if (interp_n == INTERP_AUX)
1398 return 0;
1399
1400 comp = interp_n;
Meng Wang15c825d2018-09-06 10:49:18 +08001401 dev_dbg(component->dev, "%s: event %d compander %d, enabled %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301402 __func__, event, comp + 1, rx_priv->comp_enabled[comp]);
1403
1404 if (!rx_priv->comp_enabled[comp])
1405 return 0;
1406
1407 comp_ctl0_reg = BOLERO_CDC_RX_COMPANDER0_CTL0 +
1408 (comp * RX_MACRO_COMP_OFFSET);
1409 rx_path_cfg0_reg = BOLERO_CDC_RX_RX0_RX_PATH_CFG0 +
1410 (comp * RX_MACRO_RX_PATH_OFFSET);
1411
1412 if (SND_SOC_DAPM_EVENT_ON(event)) {
1413 /* Enable Compander Clock */
Meng Wang15c825d2018-09-06 10:49:18 +08001414 snd_soc_component_update_bits(component, comp_ctl0_reg,
1415 0x01, 0x01);
1416 snd_soc_component_update_bits(component, comp_ctl0_reg,
1417 0x02, 0x02);
1418 snd_soc_component_update_bits(component, comp_ctl0_reg,
1419 0x02, 0x00);
1420 snd_soc_component_update_bits(component, rx_path_cfg0_reg,
1421 0x02, 0x02);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301422 }
1423
1424 if (SND_SOC_DAPM_EVENT_OFF(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001425 snd_soc_component_update_bits(component, comp_ctl0_reg,
1426 0x04, 0x04);
1427 snd_soc_component_update_bits(component, rx_path_cfg0_reg,
1428 0x02, 0x00);
1429 snd_soc_component_update_bits(component, comp_ctl0_reg,
1430 0x01, 0x00);
1431 snd_soc_component_update_bits(component, comp_ctl0_reg,
1432 0x04, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301433 }
1434
1435 return 0;
1436}
1437
Meng Wang15c825d2018-09-06 10:49:18 +08001438static void rx_macro_enable_softclip_clk(struct snd_soc_component *component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301439 struct rx_macro_priv *rx_priv,
1440 bool enable)
1441{
1442 if (enable) {
1443 if (rx_priv->softclip_clk_users == 0)
Meng Wang15c825d2018-09-06 10:49:18 +08001444 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301445 BOLERO_CDC_RX_SOFTCLIP_CRC,
1446 0x01, 0x01);
1447 rx_priv->softclip_clk_users++;
1448 } else {
1449 rx_priv->softclip_clk_users--;
1450 if (rx_priv->softclip_clk_users == 0)
Meng Wang15c825d2018-09-06 10:49:18 +08001451 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301452 BOLERO_CDC_RX_SOFTCLIP_CRC,
1453 0x01, 0x00);
1454 }
1455}
1456
Meng Wang15c825d2018-09-06 10:49:18 +08001457static int rx_macro_config_softclip(struct snd_soc_component *component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301458 struct rx_macro_priv *rx_priv,
1459 int event)
1460{
Meng Wang15c825d2018-09-06 10:49:18 +08001461 dev_dbg(component->dev, "%s: event %d, enabled %d\n",
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301462 __func__, event, rx_priv->is_softclip_on);
1463
1464 if (!rx_priv->is_softclip_on)
1465 return 0;
1466
1467 if (SND_SOC_DAPM_EVENT_ON(event)) {
1468 /* Enable Softclip clock */
Meng Wang15c825d2018-09-06 10:49:18 +08001469 rx_macro_enable_softclip_clk(component, rx_priv, true);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301470 /* Enable Softclip control */
Meng Wang15c825d2018-09-06 10:49:18 +08001471 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301472 BOLERO_CDC_RX_SOFTCLIP_SOFTCLIP_CTRL, 0x01, 0x01);
1473 }
1474
1475 if (SND_SOC_DAPM_EVENT_OFF(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001476 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301477 BOLERO_CDC_RX_SOFTCLIP_SOFTCLIP_CTRL, 0x01, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001478 rx_macro_enable_softclip_clk(component, rx_priv, false);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301479 }
1480
1481 return 0;
1482}
1483
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301484static inline void
1485rx_macro_enable_clsh_block(struct rx_macro_priv *rx_priv, bool enable)
1486{
1487 if ((enable && ++rx_priv->clsh_users == 1) ||
1488 (!enable && --rx_priv->clsh_users == 0))
Meng Wang15c825d2018-09-06 10:49:18 +08001489 snd_soc_component_update_bits(rx_priv->component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301490 BOLERO_CDC_RX_CLSH_CRC, 0x01,
1491 (u8) enable);
1492 if (rx_priv->clsh_users < 0)
1493 rx_priv->clsh_users = 0;
1494 dev_dbg(rx_priv->dev, "%s: clsh_users %d, enable %d", __func__,
1495 rx_priv->clsh_users, enable);
1496}
1497
Meng Wang15c825d2018-09-06 10:49:18 +08001498static int rx_macro_config_classh(struct snd_soc_component *component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301499 struct rx_macro_priv *rx_priv,
1500 int interp_n, int event)
1501{
1502 if (SND_SOC_DAPM_EVENT_OFF(event)) {
1503 rx_macro_enable_clsh_block(rx_priv, false);
1504 return 0;
1505 }
1506
1507 if (!SND_SOC_DAPM_EVENT_ON(event))
1508 return 0;
1509
1510 rx_macro_enable_clsh_block(rx_priv, true);
1511 if (interp_n == INTERP_HPHL ||
1512 interp_n == INTERP_HPHR) {
1513 /*
1514 * These K1 values depend on the Headphone Impedance
1515 * For now it is assumed to be 16 ohm
1516 */
Meng Wang15c825d2018-09-06 10:49:18 +08001517 snd_soc_component_update_bits(component,
1518 BOLERO_CDC_RX_CLSH_K1_LSB,
1519 0xFF, 0xC0);
1520 snd_soc_component_update_bits(component,
1521 BOLERO_CDC_RX_CLSH_K1_MSB,
1522 0x0F, 0x00);
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301523 }
1524 switch (interp_n) {
1525 case INTERP_HPHL:
1526 if (rx_priv->is_ear_mode_on)
Meng Wang15c825d2018-09-06 10:49:18 +08001527 snd_soc_component_update_bits(component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301528 BOLERO_CDC_RX_CLSH_HPH_V_PA,
1529 0x3F, 0x39);
1530 else
Meng Wang15c825d2018-09-06 10:49:18 +08001531 snd_soc_component_update_bits(component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301532 BOLERO_CDC_RX_CLSH_HPH_V_PA,
1533 0x3F, 0x1C);
Meng Wang15c825d2018-09-06 10:49:18 +08001534 snd_soc_component_update_bits(component,
1535 BOLERO_CDC_RX_CLSH_DECAY_CTRL,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301536 0x07, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001537 snd_soc_component_update_bits(component,
1538 BOLERO_CDC_RX_RX0_RX_PATH_CFG0,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301539 0x40, 0x40);
1540 break;
1541 case INTERP_HPHR:
Meng Wang15c825d2018-09-06 10:49:18 +08001542 snd_soc_component_update_bits(component,
1543 BOLERO_CDC_RX_CLSH_HPH_V_PA,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301544 0x3F, 0x1C);
Meng Wang15c825d2018-09-06 10:49:18 +08001545 snd_soc_component_update_bits(component,
1546 BOLERO_CDC_RX_CLSH_DECAY_CTRL,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301547 0x07, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001548 snd_soc_component_update_bits(component,
1549 BOLERO_CDC_RX_RX1_RX_PATH_CFG0,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301550 0x40, 0x40);
1551 break;
1552 case INTERP_AUX:
Meng Wang15c825d2018-09-06 10:49:18 +08001553 snd_soc_component_update_bits(component,
1554 BOLERO_CDC_RX_RX2_RX_PATH_CFG0,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301555 0x10, 0x10);
1556 break;
1557 }
1558
1559 return 0;
1560}
1561
Meng Wang15c825d2018-09-06 10:49:18 +08001562static void rx_macro_hd2_control(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301563 u16 interp_idx, int event)
1564{
1565 u16 hd2_scale_reg = 0;
1566 u16 hd2_enable_reg = 0;
1567
1568 switch (interp_idx) {
1569 case INTERP_HPHL:
Laxminath Kasam7adc34e2018-11-09 11:24:38 +05301570 hd2_scale_reg = BOLERO_CDC_RX_RX0_RX_PATH_SEC3;
1571 hd2_enable_reg = BOLERO_CDC_RX_RX0_RX_PATH_CFG0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301572 break;
1573 case INTERP_HPHR:
Laxminath Kasam7adc34e2018-11-09 11:24:38 +05301574 hd2_scale_reg = BOLERO_CDC_RX_RX1_RX_PATH_SEC3;
1575 hd2_enable_reg = BOLERO_CDC_RX_RX1_RX_PATH_CFG0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301576 break;
1577 }
1578
1579 if (hd2_enable_reg && SND_SOC_DAPM_EVENT_ON(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001580 snd_soc_component_update_bits(component, hd2_scale_reg,
1581 0x3C, 0x14);
1582 snd_soc_component_update_bits(component, hd2_enable_reg,
1583 0x04, 0x04);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301584 }
1585
1586 if (hd2_enable_reg && SND_SOC_DAPM_EVENT_OFF(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08001587 snd_soc_component_update_bits(component, hd2_enable_reg,
1588 0x04, 0x00);
1589 snd_soc_component_update_bits(component, hd2_scale_reg,
1590 0x3C, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301591 }
1592}
1593
1594static int rx_macro_get_compander(struct snd_kcontrol *kcontrol,
1595 struct snd_ctl_elem_value *ucontrol)
1596{
Meng Wang15c825d2018-09-06 10:49:18 +08001597 struct snd_soc_component *component =
1598 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301599 int comp = ((struct soc_multi_mixer_control *)
1600 kcontrol->private_value)->shift;
1601 struct device *rx_dev = NULL;
1602 struct rx_macro_priv *rx_priv = NULL;
1603
Meng Wang15c825d2018-09-06 10:49:18 +08001604 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301605 return -EINVAL;
1606
1607 ucontrol->value.integer.value[0] = rx_priv->comp_enabled[comp];
1608 return 0;
1609}
1610
1611static int rx_macro_set_compander(struct snd_kcontrol *kcontrol,
1612 struct snd_ctl_elem_value *ucontrol)
1613{
Meng Wang15c825d2018-09-06 10:49:18 +08001614 struct snd_soc_component *component =
1615 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301616 int comp = ((struct soc_multi_mixer_control *)
1617 kcontrol->private_value)->shift;
1618 int value = ucontrol->value.integer.value[0];
1619 struct device *rx_dev = NULL;
1620 struct rx_macro_priv *rx_priv = NULL;
1621
Meng Wang15c825d2018-09-06 10:49:18 +08001622 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301623 return -EINVAL;
1624
Meng Wang15c825d2018-09-06 10:49:18 +08001625 dev_dbg(component->dev, "%s: Compander %d enable current %d, new %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301626 __func__, comp + 1, rx_priv->comp_enabled[comp], value);
1627 rx_priv->comp_enabled[comp] = value;
1628
1629 return 0;
1630}
1631
1632static int rx_macro_mux_get(struct snd_kcontrol *kcontrol,
1633 struct snd_ctl_elem_value *ucontrol)
1634{
1635 struct snd_soc_dapm_widget *widget =
1636 snd_soc_dapm_kcontrol_widget(kcontrol);
Meng Wang15c825d2018-09-06 10:49:18 +08001637 struct snd_soc_component *component =
1638 snd_soc_dapm_to_component(widget->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301639 struct device *rx_dev = NULL;
1640 struct rx_macro_priv *rx_priv = NULL;
1641
Meng Wang15c825d2018-09-06 10:49:18 +08001642 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301643 return -EINVAL;
1644
1645 ucontrol->value.integer.value[0] =
1646 rx_priv->rx_port_value[widget->shift];
1647 return 0;
1648}
1649
1650static int rx_macro_mux_put(struct snd_kcontrol *kcontrol,
1651 struct snd_ctl_elem_value *ucontrol)
1652{
1653 struct snd_soc_dapm_widget *widget =
1654 snd_soc_dapm_kcontrol_widget(kcontrol);
Meng Wang15c825d2018-09-06 10:49:18 +08001655 struct snd_soc_component *component =
1656 snd_soc_dapm_to_component(widget->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301657 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value;
1658 struct snd_soc_dapm_update *update = NULL;
1659 u32 rx_port_value = ucontrol->value.integer.value[0];
1660 u32 aif_rst = 0;
1661 struct device *rx_dev = NULL;
1662 struct rx_macro_priv *rx_priv = NULL;
1663
Meng Wang15c825d2018-09-06 10:49:18 +08001664 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301665 return -EINVAL;
1666
1667 aif_rst = rx_priv->rx_port_value[widget->shift];
1668 if (!rx_port_value) {
1669 if (aif_rst == 0) {
1670 dev_err(rx_dev, "%s:AIF reset already\n", __func__);
1671 return 0;
1672 }
1673 }
1674 rx_priv->rx_port_value[widget->shift] = rx_port_value;
1675
1676 switch (rx_port_value) {
1677 case 0:
1678 clear_bit(widget->shift,
Laxminath Kasam59c7a1d2018-08-09 16:11:17 +05301679 &rx_priv->active_ch_mask[aif_rst]);
1680 rx_priv->active_ch_cnt[aif_rst]--;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301681 break;
1682 case 1:
1683 case 2:
1684 case 3:
1685 case 4:
1686 set_bit(widget->shift,
Laxminath Kasam59c7a1d2018-08-09 16:11:17 +05301687 &rx_priv->active_ch_mask[rx_port_value]);
1688 rx_priv->active_ch_cnt[rx_port_value]++;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301689 break;
1690 default:
Meng Wang15c825d2018-09-06 10:49:18 +08001691 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301692 "%s:Invalid AIF_ID for RX_MACRO MUX\n", __func__);
1693 goto err;
1694 }
1695
1696 snd_soc_dapm_mux_update_power(widget->dapm, kcontrol,
1697 rx_port_value, e, update);
1698 return 0;
1699err:
1700 return -EINVAL;
1701}
1702
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301703static int rx_macro_get_ear_mode(struct snd_kcontrol *kcontrol,
1704 struct snd_ctl_elem_value *ucontrol)
1705{
Meng Wang15c825d2018-09-06 10:49:18 +08001706 struct snd_soc_component *component =
1707 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301708 struct device *rx_dev = NULL;
1709 struct rx_macro_priv *rx_priv = NULL;
1710
Meng Wang15c825d2018-09-06 10:49:18 +08001711 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301712 return -EINVAL;
1713
1714 ucontrol->value.integer.value[0] = rx_priv->is_ear_mode_on;
1715 return 0;
1716}
1717
1718static int rx_macro_put_ear_mode(struct snd_kcontrol *kcontrol,
1719 struct snd_ctl_elem_value *ucontrol)
1720{
Meng Wang15c825d2018-09-06 10:49:18 +08001721 struct snd_soc_component *component =
1722 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301723 struct device *rx_dev = NULL;
1724 struct rx_macro_priv *rx_priv = NULL;
1725
Meng Wang15c825d2018-09-06 10:49:18 +08001726 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05301727 return -EINVAL;
1728
1729 rx_priv->is_ear_mode_on =
1730 (!ucontrol->value.integer.value[0] ? false : true);
1731 return 0;
1732}
1733
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05301734static int rx_macro_get_hph_hd2_mode(struct snd_kcontrol *kcontrol,
1735 struct snd_ctl_elem_value *ucontrol)
1736{
Meng Wang15c825d2018-09-06 10:49:18 +08001737 struct snd_soc_component *component =
1738 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05301739 struct device *rx_dev = NULL;
1740 struct rx_macro_priv *rx_priv = NULL;
1741
Meng Wang15c825d2018-09-06 10:49:18 +08001742 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05301743 return -EINVAL;
1744
1745 ucontrol->value.integer.value[0] = rx_priv->hph_hd2_mode;
1746 return 0;
1747}
1748
1749static int rx_macro_put_hph_hd2_mode(struct snd_kcontrol *kcontrol,
1750 struct snd_ctl_elem_value *ucontrol)
1751{
Meng Wang15c825d2018-09-06 10:49:18 +08001752 struct snd_soc_component *component =
1753 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05301754 struct device *rx_dev = NULL;
1755 struct rx_macro_priv *rx_priv = NULL;
1756
Meng Wang15c825d2018-09-06 10:49:18 +08001757 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05301758 return -EINVAL;
1759
1760 rx_priv->hph_hd2_mode = ucontrol->value.integer.value[0];
1761 return 0;
1762}
1763
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05301764static int rx_macro_get_hph_pwr_mode(struct snd_kcontrol *kcontrol,
1765 struct snd_ctl_elem_value *ucontrol)
1766{
Meng Wang15c825d2018-09-06 10:49:18 +08001767 struct snd_soc_component *component =
1768 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05301769 struct device *rx_dev = NULL;
1770 struct rx_macro_priv *rx_priv = NULL;
1771
Meng Wang15c825d2018-09-06 10:49:18 +08001772 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05301773 return -EINVAL;
1774
1775 ucontrol->value.integer.value[0] = rx_priv->hph_pwr_mode;
1776 return 0;
1777}
1778
1779static int rx_macro_put_hph_pwr_mode(struct snd_kcontrol *kcontrol,
1780 struct snd_ctl_elem_value *ucontrol)
1781{
Meng Wang15c825d2018-09-06 10:49:18 +08001782 struct snd_soc_component *component =
1783 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05301784 struct device *rx_dev = NULL;
1785 struct rx_macro_priv *rx_priv = NULL;
1786
Meng Wang15c825d2018-09-06 10:49:18 +08001787 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05301788 return -EINVAL;
1789
1790 rx_priv->hph_pwr_mode = ucontrol->value.integer.value[0];
1791 return 0;
1792}
1793
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301794static int rx_macro_vbat_bcl_gsm_mode_func_get(struct snd_kcontrol *kcontrol,
1795 struct snd_ctl_elem_value *ucontrol)
1796{
Meng Wang15c825d2018-09-06 10:49:18 +08001797 struct snd_soc_component *component =
1798 snd_soc_kcontrol_component(kcontrol);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301799
1800 ucontrol->value.integer.value[0] =
Meng Wang15c825d2018-09-06 10:49:18 +08001801 ((snd_soc_component_read32(
1802 component, BOLERO_CDC_RX_BCL_VBAT_CFG) & 0x04) ?
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301803 1 : 0);
1804
Meng Wang15c825d2018-09-06 10:49:18 +08001805 dev_dbg(component->dev, "%s: value: %lu\n", __func__,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301806 ucontrol->value.integer.value[0]);
1807
1808 return 0;
1809}
1810
1811static int rx_macro_vbat_bcl_gsm_mode_func_put(struct snd_kcontrol *kcontrol,
1812 struct snd_ctl_elem_value *ucontrol)
1813{
Meng Wang15c825d2018-09-06 10:49:18 +08001814 struct snd_soc_component *component =
1815 snd_soc_kcontrol_component(kcontrol);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301816
Meng Wang15c825d2018-09-06 10:49:18 +08001817 dev_dbg(component->dev, "%s: value: %lu\n", __func__,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301818 ucontrol->value.integer.value[0]);
1819
1820 /* Set Vbat register configuration for GSM mode bit based on value */
1821 if (ucontrol->value.integer.value[0])
Meng Wang15c825d2018-09-06 10:49:18 +08001822 snd_soc_component_update_bits(component,
1823 BOLERO_CDC_RX_BCL_VBAT_CFG,
1824 0x04, 0x04);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301825 else
Meng Wang15c825d2018-09-06 10:49:18 +08001826 snd_soc_component_update_bits(component,
1827 BOLERO_CDC_RX_BCL_VBAT_CFG,
1828 0x04, 0x00);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301829
1830 return 0;
1831}
1832
1833static int rx_macro_soft_clip_enable_get(struct snd_kcontrol *kcontrol,
1834 struct snd_ctl_elem_value *ucontrol)
1835{
Meng Wang15c825d2018-09-06 10:49:18 +08001836 struct snd_soc_component *component =
1837 snd_soc_kcontrol_component(kcontrol);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301838 struct device *rx_dev = NULL;
1839 struct rx_macro_priv *rx_priv = NULL;
1840
Meng Wang15c825d2018-09-06 10:49:18 +08001841 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301842 return -EINVAL;
1843
1844 ucontrol->value.integer.value[0] = rx_priv->is_softclip_on;
1845
Meng Wang15c825d2018-09-06 10:49:18 +08001846 dev_dbg(component->dev, "%s: ucontrol->value.integer.value[0] = %ld\n",
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301847 __func__, ucontrol->value.integer.value[0]);
1848
1849 return 0;
1850}
1851
1852static int rx_macro_soft_clip_enable_put(struct snd_kcontrol *kcontrol,
1853 struct snd_ctl_elem_value *ucontrol)
1854{
Meng Wang15c825d2018-09-06 10:49:18 +08001855 struct snd_soc_component *component =
1856 snd_soc_kcontrol_component(kcontrol);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301857 struct device *rx_dev = NULL;
1858 struct rx_macro_priv *rx_priv = NULL;
1859
Meng Wang15c825d2018-09-06 10:49:18 +08001860 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301861 return -EINVAL;
1862
Meng Wang15c825d2018-09-06 10:49:18 +08001863 rx_priv->is_softclip_on = ucontrol->value.integer.value[0];
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301864
Meng Wang15c825d2018-09-06 10:49:18 +08001865 dev_dbg(component->dev, "%s: soft clip enable = %d\n", __func__,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301866 rx_priv->is_softclip_on);
1867
1868 return 0;
1869}
1870
1871static int rx_macro_enable_vbat(struct snd_soc_dapm_widget *w,
1872 struct snd_kcontrol *kcontrol,
1873 int event)
1874{
Meng Wang15c825d2018-09-06 10:49:18 +08001875 struct snd_soc_component *component =
1876 snd_soc_dapm_to_component(w->dapm);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301877 struct device *rx_dev = NULL;
1878 struct rx_macro_priv *rx_priv = NULL;
1879
Meng Wang15c825d2018-09-06 10:49:18 +08001880 dev_dbg(component->dev, "%s %s %d\n", __func__, w->name, event);
1881 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301882 return -EINVAL;
1883
1884 switch (event) {
1885 case SND_SOC_DAPM_PRE_PMU:
1886 /* Enable clock for VBAT block */
Meng Wang15c825d2018-09-06 10:49:18 +08001887 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301888 BOLERO_CDC_RX_BCL_VBAT_PATH_CTL, 0x10, 0x10);
1889 /* Enable VBAT block */
Meng Wang15c825d2018-09-06 10:49:18 +08001890 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301891 BOLERO_CDC_RX_BCL_VBAT_CFG, 0x01, 0x01);
1892 /* Update interpolator with 384K path */
Meng Wang15c825d2018-09-06 10:49:18 +08001893 snd_soc_component_update_bits(component,
1894 BOLERO_CDC_RX_RX2_RX_PATH_CFG1, 0x80, 0x80);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301895 /* Update DSM FS rate */
Meng Wang15c825d2018-09-06 10:49:18 +08001896 snd_soc_component_update_bits(component,
1897 BOLERO_CDC_RX_RX2_RX_PATH_SEC7, 0x02, 0x02);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301898 /* Use attenuation mode */
Meng Wang15c825d2018-09-06 10:49:18 +08001899 snd_soc_component_update_bits(component,
1900 BOLERO_CDC_RX_BCL_VBAT_CFG, 0x02, 0x00);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301901 /* BCL block needs softclip clock to be enabled */
Meng Wang15c825d2018-09-06 10:49:18 +08001902 rx_macro_enable_softclip_clk(component, rx_priv, true);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301903 /* Enable VBAT at channel level */
Meng Wang15c825d2018-09-06 10:49:18 +08001904 snd_soc_component_update_bits(component,
1905 BOLERO_CDC_RX_RX2_RX_PATH_CFG1, 0x02, 0x02);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301906 /* Set the ATTK1 gain */
Meng Wang15c825d2018-09-06 10:49:18 +08001907 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301908 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD1,
1909 0xFF, 0xFF);
Meng Wang15c825d2018-09-06 10:49:18 +08001910 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301911 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD2,
1912 0xFF, 0x03);
Meng Wang15c825d2018-09-06 10:49:18 +08001913 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301914 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD3,
1915 0xFF, 0x00);
1916 /* Set the ATTK2 gain */
Meng Wang15c825d2018-09-06 10:49:18 +08001917 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301918 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD4,
1919 0xFF, 0xFF);
Meng Wang15c825d2018-09-06 10:49:18 +08001920 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301921 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD5,
1922 0xFF, 0x03);
Meng Wang15c825d2018-09-06 10:49:18 +08001923 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301924 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD6,
1925 0xFF, 0x00);
1926 /* Set the ATTK3 gain */
Meng Wang15c825d2018-09-06 10:49:18 +08001927 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301928 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD7,
1929 0xFF, 0xFF);
Meng Wang15c825d2018-09-06 10:49:18 +08001930 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301931 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD8,
1932 0xFF, 0x03);
Meng Wang15c825d2018-09-06 10:49:18 +08001933 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301934 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD9,
1935 0xFF, 0x00);
1936 break;
1937
1938 case SND_SOC_DAPM_POST_PMD:
Meng Wang15c825d2018-09-06 10:49:18 +08001939 snd_soc_component_update_bits(component,
1940 BOLERO_CDC_RX_RX2_RX_PATH_CFG1,
1941 0x80, 0x00);
1942 snd_soc_component_update_bits(component,
1943 BOLERO_CDC_RX_RX2_RX_PATH_SEC7,
1944 0x02, 0x00);
1945 snd_soc_component_update_bits(component,
1946 BOLERO_CDC_RX_BCL_VBAT_CFG,
1947 0x02, 0x02);
1948 snd_soc_component_update_bits(component,
1949 BOLERO_CDC_RX_RX2_RX_PATH_CFG1,
1950 0x02, 0x00);
1951 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301952 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD1,
1953 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001954 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301955 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD2,
1956 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001957 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301958 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD3,
1959 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001960 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301961 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD4,
1962 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001963 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301964 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD5,
1965 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001966 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301967 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD6,
1968 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001969 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301970 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD7,
1971 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001972 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301973 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD8,
1974 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001975 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301976 BOLERO_CDC_RX_BCL_VBAT_BCL_GAIN_UPD9,
1977 0xFF, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001978 rx_macro_enable_softclip_clk(component, rx_priv, false);
1979 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301980 BOLERO_CDC_RX_BCL_VBAT_CFG, 0x01, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08001981 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05301982 BOLERO_CDC_RX_BCL_VBAT_PATH_CTL, 0x10, 0x00);
1983 break;
1984 default:
1985 dev_err(rx_dev, "%s: Invalid event %d\n", __func__, event);
1986 break;
1987 }
1988 return 0;
1989}
1990
Meng Wang15c825d2018-09-06 10:49:18 +08001991static void rx_macro_idle_detect_control(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05301992 struct rx_macro_priv *rx_priv,
1993 int interp, int event)
1994{
1995 int reg = 0, mask = 0, val = 0;
1996
1997 if (!rx_priv->idle_det_cfg.hph_idle_detect_en)
1998 return;
1999
2000 if (interp == INTERP_HPHL) {
2001 reg = BOLERO_CDC_RX_IDLE_DETECT_PATH_CTL;
2002 mask = 0x01;
2003 val = 0x01;
2004 }
2005 if (interp == INTERP_HPHR) {
2006 reg = BOLERO_CDC_RX_IDLE_DETECT_PATH_CTL;
2007 mask = 0x02;
2008 val = 0x02;
2009 }
2010
2011 if (reg && SND_SOC_DAPM_EVENT_ON(event))
Meng Wang15c825d2018-09-06 10:49:18 +08002012 snd_soc_component_update_bits(component, reg, mask, val);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302013
2014 if (reg && SND_SOC_DAPM_EVENT_OFF(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08002015 snd_soc_component_update_bits(component, reg, mask, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302016 rx_priv->idle_det_cfg.hph_idle_thr = 0;
Meng Wang15c825d2018-09-06 10:49:18 +08002017 snd_soc_component_write(component,
2018 BOLERO_CDC_RX_IDLE_DETECT_CFG3, 0x0);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302019 }
2020}
2021
Meng Wang15c825d2018-09-06 10:49:18 +08002022static void rx_macro_hphdelay_lutbypass(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302023 struct rx_macro_priv *rx_priv,
2024 u16 interp_idx, int event)
2025{
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302026 u16 hph_lut_bypass_reg = 0;
2027 u16 hph_comp_ctrl7 = 0;
2028
2029 switch (interp_idx) {
2030 case INTERP_HPHL:
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302031 hph_lut_bypass_reg = BOLERO_CDC_RX_TOP_HPHL_COMP_LUT;
2032 hph_comp_ctrl7 = BOLERO_CDC_RX_COMPANDER0_CTL7;
2033 break;
2034 case INTERP_HPHR:
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302035 hph_lut_bypass_reg = BOLERO_CDC_RX_TOP_HPHR_COMP_LUT;
2036 hph_comp_ctrl7 = BOLERO_CDC_RX_COMPANDER1_CTL7;
2037 break;
2038 default:
2039 break;
2040 }
2041
2042 if (hph_lut_bypass_reg && SND_SOC_DAPM_EVENT_ON(event)) {
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302043 if (interp_idx == INTERP_HPHL) {
2044 if (rx_priv->is_ear_mode_on)
Meng Wang15c825d2018-09-06 10:49:18 +08002045 snd_soc_component_update_bits(component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302046 BOLERO_CDC_RX_RX0_RX_PATH_CFG1,
2047 0x02, 0x02);
2048 else
Meng Wang15c825d2018-09-06 10:49:18 +08002049 snd_soc_component_update_bits(component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302050 hph_lut_bypass_reg,
2051 0x80, 0x80);
2052 } else {
Meng Wang15c825d2018-09-06 10:49:18 +08002053 snd_soc_component_update_bits(component,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302054 hph_lut_bypass_reg,
2055 0x80, 0x80);
2056 }
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05302057 if (rx_priv->hph_pwr_mode)
Meng Wang15c825d2018-09-06 10:49:18 +08002058 snd_soc_component_update_bits(component,
2059 hph_comp_ctrl7,
2060 0x20, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302061 }
2062
2063 if (hph_lut_bypass_reg && SND_SOC_DAPM_EVENT_OFF(event)) {
Meng Wang15c825d2018-09-06 10:49:18 +08002064 snd_soc_component_update_bits(component,
2065 BOLERO_CDC_RX_RX0_RX_PATH_CFG1,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302066 0x02, 0x00);
Meng Wang15c825d2018-09-06 10:49:18 +08002067 snd_soc_component_update_bits(component, hph_lut_bypass_reg,
2068 0x80, 0x00);
2069 snd_soc_component_update_bits(component, hph_comp_ctrl7,
2070 0x20, 0x0);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302071 }
2072}
2073
Meng Wang15c825d2018-09-06 10:49:18 +08002074static int rx_macro_enable_interp_clk(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302075 int event, int interp_idx)
2076{
Laxminath Kasam35849cc2018-11-14 20:36:08 +05302077 u16 main_reg = 0, dsm_reg = 0, rx_cfg2_reg = 0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302078 struct device *rx_dev = NULL;
2079 struct rx_macro_priv *rx_priv = NULL;
2080
Meng Wang15c825d2018-09-06 10:49:18 +08002081 if (!component) {
2082 pr_err("%s: component is NULL\n", __func__);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302083 return -EINVAL;
2084 }
2085
Meng Wang15c825d2018-09-06 10:49:18 +08002086 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302087 return -EINVAL;
2088
2089 main_reg = BOLERO_CDC_RX_RX0_RX_PATH_CTL +
2090 (interp_idx * RX_MACRO_RX_PATH_OFFSET);
Laxminath Kasam35849cc2018-11-14 20:36:08 +05302091 dsm_reg = BOLERO_CDC_RX_RX0_RX_PATH_DSM_CTL +
2092 (interp_idx * RX_MACRO_RX_PATH_OFFSET);
2093 rx_cfg2_reg = BOLERO_CDC_RX_RX0_RX_PATH_CFG2 +
2094 (interp_idx * RX_MACRO_RX_PATH_OFFSET);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302095
2096 if (SND_SOC_DAPM_EVENT_ON(event)) {
2097 if (rx_priv->main_clk_users[interp_idx] == 0) {
Meng Wang15c825d2018-09-06 10:49:18 +08002098 snd_soc_component_update_bits(component, dsm_reg,
2099 0x01, 0x01);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302100 /* Main path PGA mute enable */
Meng Wang15c825d2018-09-06 10:49:18 +08002101 snd_soc_component_update_bits(component, main_reg,
2102 0x10, 0x10);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302103 /* Clk enable */
Meng Wang15c825d2018-09-06 10:49:18 +08002104 snd_soc_component_update_bits(component, main_reg,
2105 0x20, 0x20);
2106 snd_soc_component_update_bits(component, rx_cfg2_reg,
2107 0x03, 0x03);
2108 rx_macro_idle_detect_control(component, rx_priv,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302109 interp_idx, event);
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05302110 if (rx_priv->hph_hd2_mode)
Meng Wang15c825d2018-09-06 10:49:18 +08002111 rx_macro_hd2_control(
2112 component, interp_idx, event);
2113 rx_macro_hphdelay_lutbypass(component, rx_priv,
2114 interp_idx, event);
2115 rx_macro_config_compander(component, rx_priv,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302116 interp_idx, event);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302117 if (interp_idx == INTERP_AUX)
Meng Wang15c825d2018-09-06 10:49:18 +08002118 rx_macro_config_softclip(component, rx_priv,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302119 event);
Meng Wang15c825d2018-09-06 10:49:18 +08002120 rx_macro_config_classh(component, rx_priv,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302121 interp_idx, event);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302122 }
2123 rx_priv->main_clk_users[interp_idx]++;
2124 }
2125
2126 if (SND_SOC_DAPM_EVENT_OFF(event)) {
2127 rx_priv->main_clk_users[interp_idx]--;
2128 if (rx_priv->main_clk_users[interp_idx] <= 0) {
2129 rx_priv->main_clk_users[interp_idx] = 0;
Laxminath Kasam35849cc2018-11-14 20:36:08 +05302130 /* Clk Disable */
Meng Wang15c825d2018-09-06 10:49:18 +08002131 snd_soc_component_update_bits(component, dsm_reg,
2132 0x01, 0x00);
2133 snd_soc_component_update_bits(component, main_reg,
2134 0x20, 0x00);
Laxminath Kasam35849cc2018-11-14 20:36:08 +05302135 /* Reset enable and disable */
Meng Wang15c825d2018-09-06 10:49:18 +08002136 snd_soc_component_update_bits(component, main_reg,
2137 0x40, 0x40);
2138 snd_soc_component_update_bits(component, main_reg,
2139 0x40, 0x00);
Laxminath Kasam35849cc2018-11-14 20:36:08 +05302140 /* Reset rate to 48K*/
Meng Wang15c825d2018-09-06 10:49:18 +08002141 snd_soc_component_update_bits(component, main_reg,
2142 0x0F, 0x04);
2143 snd_soc_component_update_bits(component, rx_cfg2_reg,
2144 0x03, 0x00);
2145 rx_macro_config_classh(component, rx_priv,
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302146 interp_idx, event);
Meng Wang15c825d2018-09-06 10:49:18 +08002147 rx_macro_config_compander(component, rx_priv,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302148 interp_idx, event);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302149 if (interp_idx == INTERP_AUX)
Meng Wang15c825d2018-09-06 10:49:18 +08002150 rx_macro_config_softclip(component, rx_priv,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302151 event);
Meng Wang15c825d2018-09-06 10:49:18 +08002152 rx_macro_hphdelay_lutbypass(component, rx_priv,
2153 interp_idx, event);
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05302154 if (rx_priv->hph_hd2_mode)
Meng Wang15c825d2018-09-06 10:49:18 +08002155 rx_macro_hd2_control(component, interp_idx,
2156 event);
2157 rx_macro_idle_detect_control(component, rx_priv,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302158 interp_idx, event);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302159 }
2160 }
2161
Meng Wang15c825d2018-09-06 10:49:18 +08002162 dev_dbg(component->dev, "%s event %d main_clk_users %d\n",
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302163 __func__, event, rx_priv->main_clk_users[interp_idx]);
2164
2165 return rx_priv->main_clk_users[interp_idx];
2166}
2167
2168static int rx_macro_enable_rx_path_clk(struct snd_soc_dapm_widget *w,
2169 struct snd_kcontrol *kcontrol, int event)
2170{
Meng Wang15c825d2018-09-06 10:49:18 +08002171 struct snd_soc_component *component =
2172 snd_soc_dapm_to_component(w->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302173 u16 sidetone_reg = 0;
2174
Meng Wang15c825d2018-09-06 10:49:18 +08002175 dev_dbg(component->dev, "%s %d %d\n", __func__, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302176 sidetone_reg = BOLERO_CDC_RX_RX0_RX_PATH_CFG1 +
2177 RX_MACRO_RX_PATH_OFFSET * (w->shift);
2178
2179 switch (event) {
2180 case SND_SOC_DAPM_PRE_PMU:
Meng Wang15c825d2018-09-06 10:49:18 +08002181 rx_macro_enable_interp_clk(component, event, w->shift);
2182 snd_soc_component_update_bits(component, sidetone_reg,
2183 0x10, 0x10);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302184 break;
2185 case SND_SOC_DAPM_POST_PMD:
Meng Wang15c825d2018-09-06 10:49:18 +08002186 snd_soc_component_update_bits(component, sidetone_reg,
2187 0x10, 0x00);
2188 rx_macro_enable_interp_clk(component, event, w->shift);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302189 break;
2190 default:
2191 break;
2192 };
2193 return 0;
2194}
2195
2196static void rx_macro_restore_iir_coeff(struct rx_macro_priv *rx_priv, int iir_idx,
2197 int band_idx)
2198{
2199 u16 reg_add = 0, coeff_idx = 0, idx = 0;
2200 struct regmap *regmap = dev_get_regmap(rx_priv->dev->parent, NULL);
2201
Tanya Dixit8530fb92018-09-14 16:01:25 +05302202 if (regmap == NULL) {
2203 dev_err(rx_priv->dev, "%s: regmap is NULL\n", __func__);
2204 return;
2205 }
2206
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302207 regmap_write(regmap,
2208 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 0x80 * iir_idx),
2209 (band_idx * BAND_MAX * sizeof(uint32_t)) & 0x7F);
2210
2211 reg_add = BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx;
2212
2213 /* 5 coefficients per band and 4 writes per coefficient */
2214 for (coeff_idx = 0; coeff_idx < RX_MACRO_SIDETONE_IIR_COEFF_MAX;
2215 coeff_idx++) {
2216 /* Four 8 bit values(one 32 bit) per coefficient */
2217 regmap_write(regmap, reg_add,
2218 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++]);
2219 regmap_write(regmap, reg_add,
2220 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++]);
2221 regmap_write(regmap, reg_add,
2222 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++]);
2223 regmap_write(regmap, reg_add,
2224 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++]);
2225 }
2226}
2227
2228static int rx_macro_iir_enable_audio_mixer_get(struct snd_kcontrol *kcontrol,
2229 struct snd_ctl_elem_value *ucontrol)
2230{
Meng Wang15c825d2018-09-06 10:49:18 +08002231 struct snd_soc_component *component =
2232 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302233 int iir_idx = ((struct soc_multi_mixer_control *)
2234 kcontrol->private_value)->reg;
2235 int band_idx = ((struct soc_multi_mixer_control *)
2236 kcontrol->private_value)->shift;
2237 /* IIR filter band registers are at integer multiples of 0x80 */
2238 u16 iir_reg = BOLERO_CDC_RX_SIDETONE_IIR0_IIR_CTL + 0x80 * iir_idx;
2239
Meng Wang15c825d2018-09-06 10:49:18 +08002240 ucontrol->value.integer.value[0] = (
2241 snd_soc_component_read32(component, iir_reg) &
2242 (1 << band_idx)) != 0;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302243
Meng Wang15c825d2018-09-06 10:49:18 +08002244 dev_dbg(component->dev, "%s: IIR #%d band #%d enable %d\n", __func__,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302245 iir_idx, band_idx,
2246 (uint32_t)ucontrol->value.integer.value[0]);
2247 return 0;
2248}
2249
2250static int rx_macro_iir_enable_audio_mixer_put(struct snd_kcontrol *kcontrol,
2251 struct snd_ctl_elem_value *ucontrol)
2252{
Meng Wang15c825d2018-09-06 10:49:18 +08002253 struct snd_soc_component *component =
2254 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302255 int iir_idx = ((struct soc_multi_mixer_control *)
2256 kcontrol->private_value)->reg;
2257 int band_idx = ((struct soc_multi_mixer_control *)
2258 kcontrol->private_value)->shift;
2259 bool iir_band_en_status = 0;
2260 int value = ucontrol->value.integer.value[0];
2261 u16 iir_reg = BOLERO_CDC_RX_SIDETONE_IIR0_IIR_CTL + 0x80 * iir_idx;
2262 struct device *rx_dev = NULL;
2263 struct rx_macro_priv *rx_priv = NULL;
2264
Meng Wang15c825d2018-09-06 10:49:18 +08002265 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302266 return -EINVAL;
2267
2268 rx_macro_restore_iir_coeff(rx_priv, iir_idx, band_idx);
2269
2270 /* Mask first 5 bits, 6-8 are reserved */
Meng Wang15c825d2018-09-06 10:49:18 +08002271 snd_soc_component_update_bits(component, iir_reg, (1 << band_idx),
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302272 (value << band_idx));
2273
Meng Wang15c825d2018-09-06 10:49:18 +08002274 iir_band_en_status = ((snd_soc_component_read32(component, iir_reg) &
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302275 (1 << band_idx)) != 0);
Meng Wang15c825d2018-09-06 10:49:18 +08002276 dev_dbg(component->dev, "%s: IIR #%d band #%d enable %d\n", __func__,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302277 iir_idx, band_idx, iir_band_en_status);
2278 return 0;
2279}
2280
Meng Wang15c825d2018-09-06 10:49:18 +08002281static uint32_t get_iir_band_coeff(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302282 int iir_idx, int band_idx,
2283 int coeff_idx)
2284{
2285 uint32_t value = 0;
2286
2287 /* Address does not automatically update if reading */
Meng Wang15c825d2018-09-06 10:49:18 +08002288 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302289 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 0x80 * iir_idx),
2290 ((band_idx * BAND_MAX + coeff_idx)
2291 * sizeof(uint32_t)) & 0x7F);
2292
Meng Wang15c825d2018-09-06 10:49:18 +08002293 value |= snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302294 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx));
2295
Meng Wang15c825d2018-09-06 10:49:18 +08002296 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302297 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 0x80 * iir_idx),
2298 ((band_idx * BAND_MAX + coeff_idx)
2299 * sizeof(uint32_t) + 1) & 0x7F);
2300
Meng Wang15c825d2018-09-06 10:49:18 +08002301 value |= (snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302302 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL +
2303 0x80 * iir_idx)) << 8);
2304
Meng Wang15c825d2018-09-06 10:49:18 +08002305 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302306 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 0x80 * iir_idx),
2307 ((band_idx * BAND_MAX + coeff_idx)
2308 * sizeof(uint32_t) + 2) & 0x7F);
2309
Meng Wang15c825d2018-09-06 10:49:18 +08002310 value |= (snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302311 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL +
2312 0x80 * iir_idx)) << 16);
2313
Meng Wang15c825d2018-09-06 10:49:18 +08002314 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302315 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 0x80 * iir_idx),
2316 ((band_idx * BAND_MAX + coeff_idx)
2317 * sizeof(uint32_t) + 3) & 0x7F);
2318
2319 /* Mask bits top 2 bits since they are reserved */
Meng Wang15c825d2018-09-06 10:49:18 +08002320 value |= ((snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302321 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL +
2322 16 * iir_idx)) & 0x3F) << 24);
2323
2324 return value;
2325}
2326
2327static int rx_macro_iir_band_audio_mixer_get(struct snd_kcontrol *kcontrol,
2328 struct snd_ctl_elem_value *ucontrol)
2329{
Meng Wang15c825d2018-09-06 10:49:18 +08002330 struct snd_soc_component *component =
2331 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302332 int iir_idx = ((struct soc_multi_mixer_control *)
2333 kcontrol->private_value)->reg;
2334 int band_idx = ((struct soc_multi_mixer_control *)
2335 kcontrol->private_value)->shift;
2336
2337 ucontrol->value.integer.value[0] =
Meng Wang15c825d2018-09-06 10:49:18 +08002338 get_iir_band_coeff(component, iir_idx, band_idx, 0);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302339 ucontrol->value.integer.value[1] =
Meng Wang15c825d2018-09-06 10:49:18 +08002340 get_iir_band_coeff(component, iir_idx, band_idx, 1);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302341 ucontrol->value.integer.value[2] =
Meng Wang15c825d2018-09-06 10:49:18 +08002342 get_iir_band_coeff(component, iir_idx, band_idx, 2);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302343 ucontrol->value.integer.value[3] =
Meng Wang15c825d2018-09-06 10:49:18 +08002344 get_iir_band_coeff(component, iir_idx, band_idx, 3);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302345 ucontrol->value.integer.value[4] =
Meng Wang15c825d2018-09-06 10:49:18 +08002346 get_iir_band_coeff(component, iir_idx, band_idx, 4);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302347
Meng Wang15c825d2018-09-06 10:49:18 +08002348 dev_dbg(component->dev, "%s: IIR #%d band #%d b0 = 0x%x\n"
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302349 "%s: IIR #%d band #%d b1 = 0x%x\n"
2350 "%s: IIR #%d band #%d b2 = 0x%x\n"
2351 "%s: IIR #%d band #%d a1 = 0x%x\n"
2352 "%s: IIR #%d band #%d a2 = 0x%x\n",
2353 __func__, iir_idx, band_idx,
2354 (uint32_t)ucontrol->value.integer.value[0],
2355 __func__, iir_idx, band_idx,
2356 (uint32_t)ucontrol->value.integer.value[1],
2357 __func__, iir_idx, band_idx,
2358 (uint32_t)ucontrol->value.integer.value[2],
2359 __func__, iir_idx, band_idx,
2360 (uint32_t)ucontrol->value.integer.value[3],
2361 __func__, iir_idx, band_idx,
2362 (uint32_t)ucontrol->value.integer.value[4]);
2363 return 0;
2364}
2365
Meng Wang15c825d2018-09-06 10:49:18 +08002366static void set_iir_band_coeff(struct snd_soc_component *component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302367 int iir_idx, int band_idx,
2368 uint32_t value)
2369{
Meng Wang15c825d2018-09-06 10:49:18 +08002370 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302371 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx),
2372 (value & 0xFF));
2373
Meng Wang15c825d2018-09-06 10:49:18 +08002374 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302375 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx),
2376 (value >> 8) & 0xFF);
2377
Meng Wang15c825d2018-09-06 10:49:18 +08002378 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302379 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx),
2380 (value >> 16) & 0xFF);
2381
2382 /* Mask top 2 bits, 7-8 are reserved */
Meng Wang15c825d2018-09-06 10:49:18 +08002383 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302384 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B2_CTL + 0x80 * iir_idx),
2385 (value >> 24) & 0x3F);
2386}
2387
2388static int rx_macro_iir_band_audio_mixer_put(struct snd_kcontrol *kcontrol,
2389 struct snd_ctl_elem_value *ucontrol)
2390{
Meng Wang15c825d2018-09-06 10:49:18 +08002391 struct snd_soc_component *component =
2392 snd_soc_kcontrol_component(kcontrol);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302393 int iir_idx = ((struct soc_multi_mixer_control *)
2394 kcontrol->private_value)->reg;
2395 int band_idx = ((struct soc_multi_mixer_control *)
2396 kcontrol->private_value)->shift;
2397 int coeff_idx, idx = 0;
2398 struct device *rx_dev = NULL;
2399 struct rx_macro_priv *rx_priv = NULL;
2400
Meng Wang15c825d2018-09-06 10:49:18 +08002401 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302402 return -EINVAL;
2403
2404 /*
2405 * Mask top bit it is reserved
2406 * Updates addr automatically for each B2 write
2407 */
Meng Wang15c825d2018-09-06 10:49:18 +08002408 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302409 (BOLERO_CDC_RX_SIDETONE_IIR0_IIR_COEF_B1_CTL + 16 * iir_idx),
2410 (band_idx * BAND_MAX * sizeof(uint32_t)) & 0x7F);
2411
2412 /* Store the coefficients in sidetone coeff array */
2413 for (coeff_idx = 0; coeff_idx < RX_MACRO_SIDETONE_IIR_COEFF_MAX;
2414 coeff_idx++) {
2415 uint32_t value = ucontrol->value.integer.value[coeff_idx];
2416
Meng Wang15c825d2018-09-06 10:49:18 +08002417 set_iir_band_coeff(component, iir_idx, band_idx, value);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302418
2419 /* Four 8 bit values(one 32 bit) per coefficient */
2420 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++] =
2421 (value & 0xFF);
2422 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++] =
2423 (value >> 8) & 0xFF;
2424 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++] =
2425 (value >> 16) & 0xFF;
2426 rx_priv->sidetone_coeff_array[iir_idx][band_idx][idx++] =
2427 (value >> 24) & 0xFF;
2428 }
2429
2430 pr_debug("%s: IIR #%d band #%d b0 = 0x%x\n"
2431 "%s: IIR #%d band #%d b1 = 0x%x\n"
2432 "%s: IIR #%d band #%d b2 = 0x%x\n"
2433 "%s: IIR #%d band #%d a1 = 0x%x\n"
2434 "%s: IIR #%d band #%d a2 = 0x%x\n",
2435 __func__, iir_idx, band_idx,
Meng Wang15c825d2018-09-06 10:49:18 +08002436 get_iir_band_coeff(component, iir_idx, band_idx, 0),
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302437 __func__, iir_idx, band_idx,
Meng Wang15c825d2018-09-06 10:49:18 +08002438 get_iir_band_coeff(component, iir_idx, band_idx, 1),
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302439 __func__, iir_idx, band_idx,
Meng Wang15c825d2018-09-06 10:49:18 +08002440 get_iir_band_coeff(component, iir_idx, band_idx, 2),
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302441 __func__, iir_idx, band_idx,
Meng Wang15c825d2018-09-06 10:49:18 +08002442 get_iir_band_coeff(component, iir_idx, band_idx, 3),
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302443 __func__, iir_idx, band_idx,
Meng Wang15c825d2018-09-06 10:49:18 +08002444 get_iir_band_coeff(component, iir_idx, band_idx, 4));
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302445 return 0;
2446}
2447
2448static int rx_macro_set_iir_gain(struct snd_soc_dapm_widget *w,
2449 struct snd_kcontrol *kcontrol, int event)
2450{
Meng Wang15c825d2018-09-06 10:49:18 +08002451 struct snd_soc_component *component =
2452 snd_soc_dapm_to_component(w->dapm);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302453
Meng Wang15c825d2018-09-06 10:49:18 +08002454 dev_dbg(component->dev, "%s: event = %d\n", __func__, event);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302455
2456 switch (event) {
2457 case SND_SOC_DAPM_POST_PMU: /* fall through */
2458 case SND_SOC_DAPM_PRE_PMD:
2459 if (strnstr(w->name, "IIR0", sizeof("IIR0"))) {
Meng Wang15c825d2018-09-06 10:49:18 +08002460 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302461 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B1_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002462 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302463 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B1_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002464 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302465 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B2_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002466 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302467 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B2_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002468 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302469 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B3_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002470 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302471 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B3_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002472 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302473 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B4_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002474 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302475 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B4_CTL));
2476 } else {
Meng Wang15c825d2018-09-06 10:49:18 +08002477 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302478 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B1_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002479 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302480 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B1_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002481 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302482 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B2_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002483 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302484 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B2_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002485 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302486 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B3_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002487 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302488 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B3_CTL));
Meng Wang15c825d2018-09-06 10:49:18 +08002489 snd_soc_component_write(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302490 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B4_CTL,
Meng Wang15c825d2018-09-06 10:49:18 +08002491 snd_soc_component_read32(component,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302492 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B4_CTL));
2493 }
2494 break;
2495 }
2496 return 0;
2497}
2498
2499static const struct snd_kcontrol_new rx_macro_snd_controls[] = {
2500 SOC_SINGLE_SX_TLV("RX_RX0 Digital Volume",
2501 BOLERO_CDC_RX_RX0_RX_VOL_CTL,
2502 0, -84, 40, digital_gain),
2503 SOC_SINGLE_SX_TLV("RX_RX1 Digital Volume",
2504 BOLERO_CDC_RX_RX1_RX_VOL_CTL,
2505 0, -84, 40, digital_gain),
2506 SOC_SINGLE_SX_TLV("RX_RX2 Digital Volume",
2507 BOLERO_CDC_RX_RX2_RX_VOL_CTL,
2508 0, -84, 40, digital_gain),
2509 SOC_SINGLE_SX_TLV("RX_RX0 Mix Digital Volume",
2510 BOLERO_CDC_RX_RX0_RX_VOL_MIX_CTL, 0, -84, 40, digital_gain),
2511 SOC_SINGLE_SX_TLV("RX_RX1 Mix Digital Volume",
2512 BOLERO_CDC_RX_RX1_RX_VOL_MIX_CTL, 0, -84, 40, digital_gain),
2513 SOC_SINGLE_SX_TLV("RX_RX2 Mix Digital Volume",
2514 BOLERO_CDC_RX_RX2_RX_VOL_MIX_CTL, 0, -84, 40, digital_gain),
2515
2516 SOC_SINGLE_EXT("RX_COMP1 Switch", SND_SOC_NOPM, RX_MACRO_COMP1, 1, 0,
2517 rx_macro_get_compander, rx_macro_set_compander),
2518 SOC_SINGLE_EXT("RX_COMP2 Switch", SND_SOC_NOPM, RX_MACRO_COMP2, 1, 0,
2519 rx_macro_get_compander, rx_macro_set_compander),
2520
Laxminath Kasamd2d8d9f2018-08-06 18:10:14 +05302521 SOC_ENUM_EXT("RX_EAR Mode", rx_macro_ear_mode_enum,
2522 rx_macro_get_ear_mode, rx_macro_put_ear_mode),
2523
Laxminath Kasamd3ffb332018-11-14 19:59:21 +05302524 SOC_ENUM_EXT("RX_HPH HD2 Mode", rx_macro_hph_hd2_mode_enum,
2525 rx_macro_get_hph_hd2_mode, rx_macro_put_hph_hd2_mode),
2526
Laxminath Kasamde09dfb2018-11-09 13:00:30 +05302527 SOC_ENUM_EXT("RX_HPH_PWR_MODE", rx_macro_hph_pwr_mode_enum,
2528 rx_macro_get_hph_pwr_mode, rx_macro_put_hph_pwr_mode),
2529
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302530 SOC_ENUM_EXT("RX_GSM mode Enable", rx_macro_vbat_bcl_gsm_mode_enum,
2531 rx_macro_vbat_bcl_gsm_mode_func_get,
2532 rx_macro_vbat_bcl_gsm_mode_func_put),
2533 SOC_SINGLE_EXT("RX_Softclip Enable", SND_SOC_NOPM, 0, 1, 0,
2534 rx_macro_soft_clip_enable_get,
2535 rx_macro_soft_clip_enable_put),
2536
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302537 SOC_SINGLE_SX_TLV("IIR0 INP0 Volume",
2538 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B1_CTL, 0, -84, 40,
2539 digital_gain),
2540 SOC_SINGLE_SX_TLV("IIR0 INP1 Volume",
2541 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B2_CTL, 0, -84, 40,
2542 digital_gain),
2543 SOC_SINGLE_SX_TLV("IIR0 INP2 Volume",
2544 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B3_CTL, 0, -84, 40,
2545 digital_gain),
2546 SOC_SINGLE_SX_TLV("IIR0 INP3 Volume",
2547 BOLERO_CDC_RX_SIDETONE_IIR0_IIR_GAIN_B4_CTL, 0, -84, 40,
2548 digital_gain),
2549 SOC_SINGLE_SX_TLV("IIR1 INP0 Volume",
2550 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B1_CTL, 0, -84, 40,
2551 digital_gain),
2552 SOC_SINGLE_SX_TLV("IIR1 INP1 Volume",
2553 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B2_CTL, 0, -84, 40,
2554 digital_gain),
2555 SOC_SINGLE_SX_TLV("IIR1 INP2 Volume",
2556 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B3_CTL, 0, -84, 40,
2557 digital_gain),
2558 SOC_SINGLE_SX_TLV("IIR1 INP3 Volume",
2559 BOLERO_CDC_RX_SIDETONE_IIR1_IIR_GAIN_B4_CTL, 0, -84, 40,
2560 digital_gain),
2561
2562 SOC_SINGLE_EXT("IIR0 Enable Band1", IIR0, BAND1, 1, 0,
2563 rx_macro_iir_enable_audio_mixer_get,
2564 rx_macro_iir_enable_audio_mixer_put),
2565 SOC_SINGLE_EXT("IIR0 Enable Band2", IIR0, BAND2, 1, 0,
2566 rx_macro_iir_enable_audio_mixer_get,
2567 rx_macro_iir_enable_audio_mixer_put),
2568 SOC_SINGLE_EXT("IIR0 Enable Band3", IIR0, BAND3, 1, 0,
2569 rx_macro_iir_enable_audio_mixer_get,
2570 rx_macro_iir_enable_audio_mixer_put),
2571 SOC_SINGLE_EXT("IIR0 Enable Band4", IIR0, BAND4, 1, 0,
2572 rx_macro_iir_enable_audio_mixer_get,
2573 rx_macro_iir_enable_audio_mixer_put),
2574 SOC_SINGLE_EXT("IIR0 Enable Band5", IIR0, BAND5, 1, 0,
2575 rx_macro_iir_enable_audio_mixer_get,
2576 rx_macro_iir_enable_audio_mixer_put),
2577 SOC_SINGLE_EXT("IIR1 Enable Band1", IIR1, BAND1, 1, 0,
2578 rx_macro_iir_enable_audio_mixer_get,
2579 rx_macro_iir_enable_audio_mixer_put),
2580 SOC_SINGLE_EXT("IIR1 Enable Band2", IIR1, BAND2, 1, 0,
2581 rx_macro_iir_enable_audio_mixer_get,
2582 rx_macro_iir_enable_audio_mixer_put),
2583 SOC_SINGLE_EXT("IIR1 Enable Band3", IIR1, BAND3, 1, 0,
2584 rx_macro_iir_enable_audio_mixer_get,
2585 rx_macro_iir_enable_audio_mixer_put),
2586 SOC_SINGLE_EXT("IIR1 Enable Band4", IIR1, BAND4, 1, 0,
2587 rx_macro_iir_enable_audio_mixer_get,
2588 rx_macro_iir_enable_audio_mixer_put),
2589 SOC_SINGLE_EXT("IIR1 Enable Band5", IIR1, BAND5, 1, 0,
2590 rx_macro_iir_enable_audio_mixer_get,
2591 rx_macro_iir_enable_audio_mixer_put),
2592
2593 SOC_SINGLE_MULTI_EXT("IIR0 Band1", IIR0, BAND1, 255, 0, 5,
2594 rx_macro_iir_band_audio_mixer_get,
2595 rx_macro_iir_band_audio_mixer_put),
2596 SOC_SINGLE_MULTI_EXT("IIR0 Band2", IIR0, BAND2, 255, 0, 5,
2597 rx_macro_iir_band_audio_mixer_get,
2598 rx_macro_iir_band_audio_mixer_put),
2599 SOC_SINGLE_MULTI_EXT("IIR0 Band3", IIR0, BAND3, 255, 0, 5,
2600 rx_macro_iir_band_audio_mixer_get,
2601 rx_macro_iir_band_audio_mixer_put),
2602 SOC_SINGLE_MULTI_EXT("IIR0 Band4", IIR0, BAND4, 255, 0, 5,
2603 rx_macro_iir_band_audio_mixer_get,
2604 rx_macro_iir_band_audio_mixer_put),
2605 SOC_SINGLE_MULTI_EXT("IIR0 Band5", IIR0, BAND5, 255, 0, 5,
2606 rx_macro_iir_band_audio_mixer_get,
2607 rx_macro_iir_band_audio_mixer_put),
2608 SOC_SINGLE_MULTI_EXT("IIR1 Band1", IIR1, BAND1, 255, 0, 5,
2609 rx_macro_iir_band_audio_mixer_get,
2610 rx_macro_iir_band_audio_mixer_put),
2611 SOC_SINGLE_MULTI_EXT("IIR1 Band2", IIR1, BAND2, 255, 0, 5,
2612 rx_macro_iir_band_audio_mixer_get,
2613 rx_macro_iir_band_audio_mixer_put),
2614 SOC_SINGLE_MULTI_EXT("IIR1 Band3", IIR1, BAND3, 255, 0, 5,
2615 rx_macro_iir_band_audio_mixer_get,
2616 rx_macro_iir_band_audio_mixer_put),
2617 SOC_SINGLE_MULTI_EXT("IIR1 Band4", IIR1, BAND4, 255, 0, 5,
2618 rx_macro_iir_band_audio_mixer_get,
2619 rx_macro_iir_band_audio_mixer_put),
2620 SOC_SINGLE_MULTI_EXT("IIR1 Band5", IIR1, BAND5, 255, 0, 5,
2621 rx_macro_iir_band_audio_mixer_get,
2622 rx_macro_iir_band_audio_mixer_put),
2623};
2624
2625static const struct snd_soc_dapm_widget rx_macro_dapm_widgets[] = {
2626 SND_SOC_DAPM_AIF_IN("RX AIF1 PB", "RX_MACRO_AIF1 Playback", 0,
2627 SND_SOC_NOPM, 0, 0),
2628
2629 SND_SOC_DAPM_AIF_IN("RX AIF2 PB", "RX_MACRO_AIF2 Playback", 0,
2630 SND_SOC_NOPM, 0, 0),
2631
2632 SND_SOC_DAPM_AIF_IN("RX AIF3 PB", "RX_MACRO_AIF3 Playback", 0,
2633 SND_SOC_NOPM, 0, 0),
2634
2635 SND_SOC_DAPM_AIF_IN("RX AIF4 PB", "RX_MACRO_AIF4 Playback", 0,
2636 SND_SOC_NOPM, 0, 0),
2637
2638 RX_MACRO_DAPM_MUX("RX_MACRO RX0 MUX", RX_MACRO_RX0, rx_macro_rx0),
2639 RX_MACRO_DAPM_MUX("RX_MACRO RX1 MUX", RX_MACRO_RX1, rx_macro_rx1),
2640 RX_MACRO_DAPM_MUX("RX_MACRO RX2 MUX", RX_MACRO_RX2, rx_macro_rx2),
2641 RX_MACRO_DAPM_MUX("RX_MACRO RX3 MUX", RX_MACRO_RX3, rx_macro_rx3),
2642 RX_MACRO_DAPM_MUX("RX_MACRO RX4 MUX", RX_MACRO_RX4, rx_macro_rx4),
2643 RX_MACRO_DAPM_MUX("RX_MACRO RX5 MUX", RX_MACRO_RX5, rx_macro_rx5),
2644
2645 SND_SOC_DAPM_MIXER("RX_RX0", SND_SOC_NOPM, 0, 0, NULL, 0),
2646 SND_SOC_DAPM_MIXER("RX_RX1", SND_SOC_NOPM, 0, 0, NULL, 0),
2647 SND_SOC_DAPM_MIXER("RX_RX2", SND_SOC_NOPM, 0, 0, NULL, 0),
2648 SND_SOC_DAPM_MIXER("RX_RX3", SND_SOC_NOPM, 0, 0, NULL, 0),
2649 SND_SOC_DAPM_MIXER("RX_RX4", SND_SOC_NOPM, 0, 0, NULL, 0),
2650 SND_SOC_DAPM_MIXER("RX_RX5", SND_SOC_NOPM, 0, 0, NULL, 0),
2651
2652 RX_MACRO_DAPM_MUX("IIR0 INP0 MUX", 0, iir0_inp0),
2653 RX_MACRO_DAPM_MUX("IIR0 INP1 MUX", 0, iir0_inp1),
2654 RX_MACRO_DAPM_MUX("IIR0 INP2 MUX", 0, iir0_inp2),
2655 RX_MACRO_DAPM_MUX("IIR0 INP3 MUX", 0, iir0_inp3),
2656 RX_MACRO_DAPM_MUX("IIR1 INP0 MUX", 0, iir1_inp0),
2657 RX_MACRO_DAPM_MUX("IIR1 INP1 MUX", 0, iir1_inp1),
2658 RX_MACRO_DAPM_MUX("IIR1 INP2 MUX", 0, iir1_inp2),
2659 RX_MACRO_DAPM_MUX("IIR1 INP3 MUX", 0, iir1_inp3),
2660
2661 SND_SOC_DAPM_MIXER_E("IIR0", BOLERO_CDC_RX_SIDETONE_IIR0_IIR_PATH_CTL,
2662 4, 0, NULL, 0, rx_macro_set_iir_gain,
2663 SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD),
2664 SND_SOC_DAPM_MIXER_E("IIR1", BOLERO_CDC_RX_SIDETONE_IIR1_IIR_PATH_CTL,
2665 4, 0, NULL, 0, rx_macro_set_iir_gain,
2666 SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD),
2667 SND_SOC_DAPM_MIXER("SRC0", BOLERO_CDC_RX_SIDETONE_SRC0_ST_SRC_PATH_CTL,
2668 4, 0, NULL, 0),
2669 SND_SOC_DAPM_MIXER("SRC1", BOLERO_CDC_RX_SIDETONE_SRC1_ST_SRC_PATH_CTL,
2670 4, 0, NULL, 0),
2671
2672 RX_MACRO_DAPM_MUX("RX MIX TX0 MUX", 0, rx_mix_tx0),
2673 RX_MACRO_DAPM_MUX("RX MIX TX1 MUX", 0, rx_mix_tx1),
2674 RX_MACRO_DAPM_MUX("RX MIX TX2 MUX", 0, rx_mix_tx2),
2675 RX_MACRO_DAPM_MUX("RX INT0 DEM MUX", 0, rx_int0_dem_inp),
2676 RX_MACRO_DAPM_MUX("RX INT1 DEM MUX", 0, rx_int1_dem_inp),
2677
2678 SND_SOC_DAPM_MUX_E("RX INT0_2 MUX", SND_SOC_NOPM, INTERP_HPHL, 0,
2679 &rx_int0_2_mux, rx_macro_enable_mix_path,
2680 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2681 SND_SOC_DAPM_POST_PMD),
2682 SND_SOC_DAPM_MUX_E("RX INT1_2 MUX", SND_SOC_NOPM, INTERP_HPHR, 0,
2683 &rx_int1_2_mux, rx_macro_enable_mix_path,
2684 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2685 SND_SOC_DAPM_POST_PMD),
2686 SND_SOC_DAPM_MUX_E("RX INT2_2 MUX", SND_SOC_NOPM, INTERP_AUX, 0,
2687 &rx_int2_2_mux, rx_macro_enable_mix_path,
2688 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2689 SND_SOC_DAPM_POST_PMD),
2690
2691 RX_MACRO_DAPM_MUX("RX INT0_1 MIX1 INP0", 0, rx_int0_1_mix_inp0),
2692 RX_MACRO_DAPM_MUX("RX INT0_1 MIX1 INP1", 0, rx_int0_1_mix_inp1),
2693 RX_MACRO_DAPM_MUX("RX INT0_1 MIX1 INP2", 0, rx_int0_1_mix_inp2),
2694 RX_MACRO_DAPM_MUX("RX INT1_1 MIX1 INP0", 0, rx_int1_1_mix_inp0),
2695 RX_MACRO_DAPM_MUX("RX INT1_1 MIX1 INP1", 0, rx_int1_1_mix_inp1),
2696 RX_MACRO_DAPM_MUX("RX INT1_1 MIX1 INP2", 0, rx_int1_1_mix_inp2),
2697 RX_MACRO_DAPM_MUX("RX INT2_1 MIX1 INP0", 0, rx_int2_1_mix_inp0),
2698 RX_MACRO_DAPM_MUX("RX INT2_1 MIX1 INP1", 0, rx_int2_1_mix_inp1),
2699 RX_MACRO_DAPM_MUX("RX INT2_1 MIX1 INP2", 0, rx_int2_1_mix_inp2),
2700
2701 SND_SOC_DAPM_MUX_E("RX INT0_1 INTERP", SND_SOC_NOPM, INTERP_HPHL, 0,
2702 &rx_int0_1_interp_mux, rx_macro_enable_main_path,
2703 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2704 SND_SOC_DAPM_POST_PMD),
2705 SND_SOC_DAPM_MUX_E("RX INT1_1 INTERP", SND_SOC_NOPM, INTERP_HPHR, 0,
2706 &rx_int1_1_interp_mux, rx_macro_enable_main_path,
2707 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2708 SND_SOC_DAPM_POST_PMD),
2709 SND_SOC_DAPM_MUX_E("RX INT2_1 INTERP", SND_SOC_NOPM, INTERP_AUX, 0,
2710 &rx_int2_1_interp_mux, rx_macro_enable_main_path,
2711 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
2712 SND_SOC_DAPM_POST_PMD),
2713
2714 RX_MACRO_DAPM_MUX("RX INT0_2 INTERP", 0, rx_int0_2_interp),
2715 RX_MACRO_DAPM_MUX("RX INT1_2 INTERP", 0, rx_int1_2_interp),
2716 RX_MACRO_DAPM_MUX("RX INT2_2 INTERP", 0, rx_int2_2_interp),
2717
2718 SND_SOC_DAPM_MIXER("RX INT0_1 MIX1", SND_SOC_NOPM, 0, 0, NULL, 0),
2719 SND_SOC_DAPM_MIXER("RX INT0 SEC MIX", SND_SOC_NOPM, 0, 0, NULL, 0),
2720 SND_SOC_DAPM_MIXER("RX INT1_1 MIX1", SND_SOC_NOPM, 0, 0, NULL, 0),
2721 SND_SOC_DAPM_MIXER("RX INT1 SEC MIX", SND_SOC_NOPM, 0, 0, NULL, 0),
2722 SND_SOC_DAPM_MIXER("RX INT2_1 MIX1", SND_SOC_NOPM, 0, 0, NULL, 0),
2723 SND_SOC_DAPM_MIXER("RX INT2 SEC MIX", SND_SOC_NOPM, 0, 0, NULL, 0),
2724
2725 SND_SOC_DAPM_MUX_E("RX INT0 MIX2 INP", SND_SOC_NOPM, INTERP_HPHL,
2726 0, &rx_int0_mix2_inp_mux, rx_macro_enable_rx_path_clk,
2727 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
2728 SND_SOC_DAPM_MUX_E("RX INT1 MIX2 INP", SND_SOC_NOPM, INTERP_HPHR,
2729 0, &rx_int1_mix2_inp_mux, rx_macro_enable_rx_path_clk,
2730 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
2731 SND_SOC_DAPM_MUX_E("RX INT2 MIX2 INP", SND_SOC_NOPM, INTERP_AUX,
2732 0, &rx_int2_mix2_inp_mux, rx_macro_enable_rx_path_clk,
2733 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
2734
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302735 SND_SOC_DAPM_MIXER_E("RX INT2_1 VBAT", SND_SOC_NOPM,
2736 0, 0, rx_int2_1_vbat_mix_switch,
2737 ARRAY_SIZE(rx_int2_1_vbat_mix_switch),
2738 rx_macro_enable_vbat,
2739 SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
2740
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302741 SND_SOC_DAPM_MIXER("RX INT0 MIX2", SND_SOC_NOPM, 0, 0, NULL, 0),
2742 SND_SOC_DAPM_MIXER("RX INT1 MIX2", SND_SOC_NOPM, 0, 0, NULL, 0),
2743 SND_SOC_DAPM_MIXER("RX INT2 MIX2", SND_SOC_NOPM, 0, 0, NULL, 0),
2744
2745 SND_SOC_DAPM_OUTPUT("HPHL_OUT"),
2746 SND_SOC_DAPM_OUTPUT("HPHR_OUT"),
2747 SND_SOC_DAPM_OUTPUT("AUX_OUT"),
2748
2749 SND_SOC_DAPM_INPUT("RX_TX DEC0_INP"),
2750 SND_SOC_DAPM_INPUT("RX_TX DEC1_INP"),
2751 SND_SOC_DAPM_INPUT("RX_TX DEC2_INP"),
2752 SND_SOC_DAPM_INPUT("RX_TX DEC3_INP"),
2753
2754 SND_SOC_DAPM_SUPPLY_S("RX_MCLK", 0, SND_SOC_NOPM, 0, 0,
2755 rx_macro_mclk_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD),
2756};
2757
2758static const struct snd_soc_dapm_route rx_audio_map[] = {
2759 {"RX AIF1 PB", NULL, "RX_MCLK"},
2760 {"RX AIF2 PB", NULL, "RX_MCLK"},
2761 {"RX AIF3 PB", NULL, "RX_MCLK"},
2762 {"RX AIF4 PB", NULL, "RX_MCLK"},
2763
2764 {"RX_MACRO RX0 MUX", "AIF1_PB", "RX AIF1 PB"},
2765 {"RX_MACRO RX1 MUX", "AIF1_PB", "RX AIF1 PB"},
2766 {"RX_MACRO RX2 MUX", "AIF1_PB", "RX AIF1 PB"},
2767 {"RX_MACRO RX3 MUX", "AIF1_PB", "RX AIF1 PB"},
2768 {"RX_MACRO RX4 MUX", "AIF1_PB", "RX AIF1 PB"},
2769 {"RX_MACRO RX5 MUX", "AIF1_PB", "RX AIF1 PB"},
2770
2771 {"RX_MACRO RX0 MUX", "AIF2_PB", "RX AIF2 PB"},
2772 {"RX_MACRO RX1 MUX", "AIF2_PB", "RX AIF2 PB"},
2773 {"RX_MACRO RX2 MUX", "AIF2_PB", "RX AIF2 PB"},
2774 {"RX_MACRO RX3 MUX", "AIF2_PB", "RX AIF2 PB"},
2775 {"RX_MACRO RX4 MUX", "AIF2_PB", "RX AIF2 PB"},
2776 {"RX_MACRO RX5 MUX", "AIF2_PB", "RX AIF2 PB"},
2777
2778 {"RX_MACRO RX0 MUX", "AIF3_PB", "RX AIF3 PB"},
2779 {"RX_MACRO RX1 MUX", "AIF3_PB", "RX AIF3 PB"},
2780 {"RX_MACRO RX2 MUX", "AIF3_PB", "RX AIF3 PB"},
2781 {"RX_MACRO RX3 MUX", "AIF3_PB", "RX AIF3 PB"},
2782 {"RX_MACRO RX4 MUX", "AIF3_PB", "RX AIF3 PB"},
2783 {"RX_MACRO RX5 MUX", "AIF3_PB", "RX AIF3 PB"},
2784
2785 {"RX_MACRO RX0 MUX", "AIF4_PB", "RX AIF4 PB"},
2786 {"RX_MACRO RX1 MUX", "AIF4_PB", "RX AIF4 PB"},
2787 {"RX_MACRO RX2 MUX", "AIF4_PB", "RX AIF4 PB"},
2788 {"RX_MACRO RX3 MUX", "AIF4_PB", "RX AIF4 PB"},
2789 {"RX_MACRO RX4 MUX", "AIF4_PB", "RX AIF4 PB"},
2790 {"RX_MACRO RX5 MUX", "AIF4_PB", "RX AIF4 PB"},
2791
2792 {"RX_RX0", NULL, "RX_MACRO RX0 MUX"},
2793 {"RX_RX1", NULL, "RX_MACRO RX1 MUX"},
2794 {"RX_RX2", NULL, "RX_MACRO RX2 MUX"},
2795 {"RX_RX3", NULL, "RX_MACRO RX3 MUX"},
2796 {"RX_RX4", NULL, "RX_MACRO RX4 MUX"},
2797 {"RX_RX5", NULL, "RX_MACRO RX5 MUX"},
2798
2799 {"RX INT0_1 MIX1 INP0", "RX0", "RX_RX0"},
2800 {"RX INT0_1 MIX1 INP0", "RX1", "RX_RX1"},
2801 {"RX INT0_1 MIX1 INP0", "RX2", "RX_RX2"},
2802 {"RX INT0_1 MIX1 INP0", "RX3", "RX_RX3"},
2803 {"RX INT0_1 MIX1 INP0", "RX4", "RX_RX4"},
2804 {"RX INT0_1 MIX1 INP0", "RX5", "RX_RX5"},
2805 {"RX INT0_1 MIX1 INP0", "IIR0", "IIR0"},
2806 {"RX INT0_1 MIX1 INP0", "IIR1", "IIR1"},
2807 {"RX INT0_1 MIX1 INP1", "RX0", "RX_RX0"},
2808 {"RX INT0_1 MIX1 INP1", "RX1", "RX_RX1"},
2809 {"RX INT0_1 MIX1 INP1", "RX2", "RX_RX2"},
2810 {"RX INT0_1 MIX1 INP1", "RX3", "RX_RX3"},
2811 {"RX INT0_1 MIX1 INP1", "RX4", "RX_RX4"},
2812 {"RX INT0_1 MIX1 INP1", "RX5", "RX_RX5"},
2813 {"RX INT0_1 MIX1 INP1", "IIR0", "IIR0"},
2814 {"RX INT0_1 MIX1 INP1", "IIR1", "IIR1"},
2815 {"RX INT0_1 MIX1 INP2", "RX0", "RX_RX0"},
2816 {"RX INT0_1 MIX1 INP2", "RX1", "RX_RX1"},
2817 {"RX INT0_1 MIX1 INP2", "RX2", "RX_RX2"},
2818 {"RX INT0_1 MIX1 INP2", "RX3", "RX_RX3"},
2819 {"RX INT0_1 MIX1 INP2", "RX4", "RX_RX4"},
2820 {"RX INT0_1 MIX1 INP2", "RX5", "RX_RX5"},
2821 {"RX INT0_1 MIX1 INP2", "IIR0", "IIR0"},
2822 {"RX INT0_1 MIX1 INP2", "IIR1", "IIR1"},
2823
2824 {"RX INT1_1 MIX1 INP0", "RX0", "RX_RX0"},
2825 {"RX INT1_1 MIX1 INP0", "RX1", "RX_RX1"},
2826 {"RX INT1_1 MIX1 INP0", "RX2", "RX_RX2"},
2827 {"RX INT1_1 MIX1 INP0", "RX3", "RX_RX3"},
2828 {"RX INT1_1 MIX1 INP0", "RX4", "RX_RX4"},
2829 {"RX INT1_1 MIX1 INP0", "RX5", "RX_RX5"},
2830 {"RX INT1_1 MIX1 INP0", "IIR0", "IIR0"},
2831 {"RX INT1_1 MIX1 INP0", "IIR1", "IIR1"},
2832 {"RX INT1_1 MIX1 INP1", "RX0", "RX_RX0"},
2833 {"RX INT1_1 MIX1 INP1", "RX1", "RX_RX1"},
2834 {"RX INT1_1 MIX1 INP1", "RX2", "RX_RX2"},
2835 {"RX INT1_1 MIX1 INP1", "RX3", "RX_RX3"},
2836 {"RX INT1_1 MIX1 INP1", "RX4", "RX_RX4"},
2837 {"RX INT1_1 MIX1 INP1", "RX5", "RX_RX5"},
2838 {"RX INT1_1 MIX1 INP1", "IIR0", "IIR0"},
2839 {"RX INT1_1 MIX1 INP1", "IIR1", "IIR1"},
2840 {"RX INT1_1 MIX1 INP2", "RX0", "RX_RX0"},
2841 {"RX INT1_1 MIX1 INP2", "RX1", "RX_RX1"},
2842 {"RX INT1_1 MIX1 INP2", "RX2", "RX_RX2"},
2843 {"RX INT1_1 MIX1 INP2", "RX3", "RX_RX3"},
2844 {"RX INT1_1 MIX1 INP2", "RX4", "RX_RX4"},
2845 {"RX INT1_1 MIX1 INP2", "RX5", "RX_RX5"},
2846 {"RX INT1_1 MIX1 INP2", "IIR0", "IIR0"},
2847 {"RX INT1_1 MIX1 INP2", "IIR1", "IIR1"},
2848
2849 {"RX INT2_1 MIX1 INP0", "RX0", "RX_RX0"},
2850 {"RX INT2_1 MIX1 INP0", "RX1", "RX_RX1"},
2851 {"RX INT2_1 MIX1 INP0", "RX2", "RX_RX2"},
2852 {"RX INT2_1 MIX1 INP0", "RX3", "RX_RX3"},
2853 {"RX INT2_1 MIX1 INP0", "RX4", "RX_RX4"},
2854 {"RX INT2_1 MIX1 INP0", "RX5", "RX_RX5"},
2855 {"RX INT2_1 MIX1 INP0", "IIR0", "IIR0"},
2856 {"RX INT2_1 MIX1 INP0", "IIR1", "IIR1"},
2857 {"RX INT2_1 MIX1 INP1", "RX0", "RX_RX0"},
2858 {"RX INT2_1 MIX1 INP1", "RX1", "RX_RX1"},
2859 {"RX INT2_1 MIX1 INP1", "RX2", "RX_RX2"},
2860 {"RX INT2_1 MIX1 INP1", "RX3", "RX_RX3"},
2861 {"RX INT2_1 MIX1 INP1", "RX4", "RX_RX4"},
2862 {"RX INT2_1 MIX1 INP1", "RX5", "RX_RX5"},
2863 {"RX INT2_1 MIX1 INP1", "IIR0", "IIR0"},
2864 {"RX INT2_1 MIX1 INP1", "IIR1", "IIR1"},
2865 {"RX INT2_1 MIX1 INP2", "RX0", "RX_RX0"},
2866 {"RX INT2_1 MIX1 INP2", "RX1", "RX_RX1"},
2867 {"RX INT2_1 MIX1 INP2", "RX2", "RX_RX2"},
2868 {"RX INT2_1 MIX1 INP2", "RX3", "RX_RX3"},
2869 {"RX INT2_1 MIX1 INP2", "RX4", "RX_RX4"},
2870 {"RX INT2_1 MIX1 INP2", "RX5", "RX_RX5"},
2871 {"RX INT2_1 MIX1 INP2", "IIR0", "IIR0"},
2872 {"RX INT2_1 MIX1 INP2", "IIR1", "IIR1"},
2873
2874 {"RX INT0_1 MIX1", NULL, "RX INT0_1 MIX1 INP0"},
2875 {"RX INT0_1 MIX1", NULL, "RX INT0_1 MIX1 INP1"},
2876 {"RX INT0_1 MIX1", NULL, "RX INT0_1 MIX1 INP2"},
2877 {"RX INT1_1 MIX1", NULL, "RX INT1_1 MIX1 INP0"},
2878 {"RX INT1_1 MIX1", NULL, "RX INT1_1 MIX1 INP1"},
2879 {"RX INT1_1 MIX1", NULL, "RX INT1_1 MIX1 INP2"},
2880 {"RX INT2_1 MIX1", NULL, "RX INT2_1 MIX1 INP0"},
2881 {"RX INT2_1 MIX1", NULL, "RX INT2_1 MIX1 INP1"},
2882 {"RX INT2_1 MIX1", NULL, "RX INT2_1 MIX1 INP2"},
2883
2884 /* Mixing path INT0 */
2885 {"RX INT0_2 MUX", "RX0", "RX_RX0"},
2886 {"RX INT0_2 MUX", "RX1", "RX_RX1"},
2887 {"RX INT0_2 MUX", "RX2", "RX_RX2"},
2888 {"RX INT0_2 MUX", "RX3", "RX_RX3"},
2889 {"RX INT0_2 MUX", "RX4", "RX_RX4"},
2890 {"RX INT0_2 MUX", "RX5", "RX_RX5"},
2891 {"RX INT0_2 INTERP", NULL, "RX INT0_2 MUX"},
2892 {"RX INT0 SEC MIX", NULL, "RX INT0_2 INTERP"},
2893
2894 /* Mixing path INT1 */
2895 {"RX INT1_2 MUX", "RX0", "RX_RX0"},
2896 {"RX INT1_2 MUX", "RX1", "RX_RX1"},
2897 {"RX INT1_2 MUX", "RX2", "RX_RX2"},
2898 {"RX INT1_2 MUX", "RX3", "RX_RX3"},
2899 {"RX INT1_2 MUX", "RX4", "RX_RX4"},
2900 {"RX INT1_2 MUX", "RX5", "RX_RX5"},
2901 {"RX INT1_2 INTERP", NULL, "RX INT1_2 MUX"},
2902 {"RX INT1 SEC MIX", NULL, "RX INT1_2 INTERP"},
2903
2904 /* Mixing path INT2 */
2905 {"RX INT2_2 MUX", "RX0", "RX_RX0"},
2906 {"RX INT2_2 MUX", "RX1", "RX_RX1"},
2907 {"RX INT2_2 MUX", "RX2", "RX_RX2"},
2908 {"RX INT2_2 MUX", "RX3", "RX_RX3"},
2909 {"RX INT2_2 MUX", "RX4", "RX_RX4"},
2910 {"RX INT2_2 MUX", "RX5", "RX_RX5"},
2911 {"RX INT2_2 INTERP", NULL, "RX INT2_2 MUX"},
2912 {"RX INT2 SEC MIX", NULL, "RX INT2_2 INTERP"},
2913
2914 {"RX INT0_1 INTERP", NULL, "RX INT0_1 MIX1"},
2915 {"RX INT0 SEC MIX", NULL, "RX INT0_1 INTERP"},
2916 {"RX INT0 MIX2", NULL, "RX INT0 SEC MIX"},
2917 {"RX INT0 MIX2", NULL, "RX INT0 MIX2 INP"},
2918 {"RX INT0 DEM MUX", "CLSH_DSM_OUT", "RX INT0 MIX2"},
2919 {"HPHL_OUT", NULL, "RX INT0 DEM MUX"},
Laxminath Kasamfc281ad2018-08-06 20:19:40 +05302920 {"HPHL_OUT", NULL, "RX_MCLK"},
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302921
2922 {"RX INT1_1 INTERP", NULL, "RX INT1_1 MIX1"},
2923 {"RX INT1 SEC MIX", NULL, "RX INT1_1 INTERP"},
2924 {"RX INT1 MIX2", NULL, "RX INT1 SEC MIX"},
2925 {"RX INT1 MIX2", NULL, "RX INT1 MIX2 INP"},
2926 {"RX INT1 DEM MUX", "CLSH_DSM_OUT", "RX INT1 MIX2"},
2927 {"HPHR_OUT", NULL, "RX INT1 DEM MUX"},
Laxminath Kasamfc281ad2018-08-06 20:19:40 +05302928 {"HPHR_OUT", NULL, "RX_MCLK"},
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302929
2930 {"RX INT2_1 INTERP", NULL, "RX INT2_1 MIX1"},
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05302931
2932 {"RX INT2_1 VBAT", "RX AUX VBAT Enable", "RX INT2_1 INTERP"},
2933 {"RX INT2 SEC MIX", NULL, "RX INT2_1 VBAT"},
2934
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302935 {"RX INT2 SEC MIX", NULL, "RX INT2_1 INTERP"},
2936 {"RX INT2 MIX2", NULL, "RX INT2 SEC MIX"},
2937 {"RX INT2 MIX2", NULL, "RX INT2 MIX2 INP"},
2938 {"AUX_OUT", NULL, "RX INT2 MIX2"},
Laxminath Kasamfc281ad2018-08-06 20:19:40 +05302939 {"AUX_OUT", NULL, "RX_MCLK"},
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302940
Laxminath Kasamfc281ad2018-08-06 20:19:40 +05302941 {"IIR0", NULL, "RX_MCLK"},
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302942 {"IIR0", NULL, "IIR0 INP0 MUX"},
2943 {"IIR0 INP0 MUX", "DEC0", "RX_TX DEC0_INP"},
2944 {"IIR0 INP0 MUX", "DEC1", "RX_TX DEC1_INP"},
2945 {"IIR0 INP0 MUX", "DEC2", "RX_TX DEC2_INP"},
2946 {"IIR0 INP0 MUX", "DEC3", "RX_TX DEC3_INP"},
2947 {"IIR0 INP0 MUX", "RX0", "RX_RX0"},
2948 {"IIR0 INP0 MUX", "RX1", "RX_RX1"},
2949 {"IIR0 INP0 MUX", "RX2", "RX_RX2"},
2950 {"IIR0 INP0 MUX", "RX3", "RX_RX3"},
2951 {"IIR0 INP0 MUX", "RX4", "RX_RX4"},
2952 {"IIR0 INP0 MUX", "RX5", "RX_RX5"},
2953 {"IIR0", NULL, "IIR0 INP1 MUX"},
2954 {"IIR0 INP1 MUX", "DEC0", "RX_TX DEC0_INP"},
2955 {"IIR0 INP1 MUX", "DEC1", "RX_TX DEC1_INP"},
2956 {"IIR0 INP1 MUX", "DEC2", "RX_TX DEC2_INP"},
2957 {"IIR0 INP1 MUX", "DEC3", "RX_TX DEC3_INP"},
2958 {"IIR0 INP1 MUX", "RX0", "RX_RX0"},
2959 {"IIR0 INP1 MUX", "RX1", "RX_RX1"},
2960 {"IIR0 INP1 MUX", "RX2", "RX_RX2"},
2961 {"IIR0 INP1 MUX", "RX3", "RX_RX3"},
2962 {"IIR0 INP1 MUX", "RX4", "RX_RX4"},
2963 {"IIR0 INP1 MUX", "RX5", "RX_RX5"},
2964 {"IIR0", NULL, "IIR0 INP2 MUX"},
2965 {"IIR0 INP2 MUX", "DEC0", "RX_TX DEC0_INP"},
2966 {"IIR0 INP2 MUX", "DEC1", "RX_TX DEC1_INP"},
2967 {"IIR0 INP2 MUX", "DEC2", "RX_TX DEC2_INP"},
2968 {"IIR0 INP2 MUX", "DEC3", "RX_TX DEC3_INP"},
2969 {"IIR0 INP2 MUX", "RX0", "RX_RX0"},
2970 {"IIR0 INP2 MUX", "RX1", "RX_RX1"},
2971 {"IIR0 INP2 MUX", "RX2", "RX_RX2"},
2972 {"IIR0 INP2 MUX", "RX3", "RX_RX3"},
2973 {"IIR0 INP2 MUX", "RX4", "RX_RX4"},
2974 {"IIR0 INP2 MUX", "RX5", "RX_RX5"},
2975 {"IIR0", NULL, "IIR0 INP3 MUX"},
2976 {"IIR0 INP3 MUX", "DEC0", "RX_TX DEC0_INP"},
2977 {"IIR0 INP3 MUX", "DEC1", "RX_TX DEC1_INP"},
2978 {"IIR0 INP3 MUX", "DEC2", "RX_TX DEC2_INP"},
2979 {"IIR0 INP3 MUX", "DEC3", "RX_TX DEC3_INP"},
2980 {"IIR0 INP3 MUX", "RX0", "RX_RX0"},
2981 {"IIR0 INP3 MUX", "RX1", "RX_RX1"},
2982 {"IIR0 INP3 MUX", "RX2", "RX_RX2"},
2983 {"IIR0 INP3 MUX", "RX3", "RX_RX3"},
2984 {"IIR0 INP3 MUX", "RX4", "RX_RX4"},
2985 {"IIR0 INP3 MUX", "RX5", "RX_RX5"},
2986
Laxminath Kasamfc281ad2018-08-06 20:19:40 +05302987 {"IIR1", NULL, "RX_MCLK"},
Laxminath Kasama7ecc582018-06-15 16:55:02 +05302988 {"IIR1", NULL, "IIR1 INP0 MUX"},
2989 {"IIR1 INP0 MUX", "DEC0", "RX_TX DEC0_INP"},
2990 {"IIR1 INP0 MUX", "DEC1", "RX_TX DEC1_INP"},
2991 {"IIR1 INP0 MUX", "DEC2", "RX_TX DEC2_INP"},
2992 {"IIR1 INP0 MUX", "DEC3", "RX_TX DEC3_INP"},
2993 {"IIR1 INP0 MUX", "RX0", "RX_RX0"},
2994 {"IIR1 INP0 MUX", "RX1", "RX_RX1"},
2995 {"IIR1 INP0 MUX", "RX2", "RX_RX2"},
2996 {"IIR1 INP0 MUX", "RX3", "RX_RX3"},
2997 {"IIR1 INP0 MUX", "RX4", "RX_RX4"},
2998 {"IIR1 INP0 MUX", "RX5", "RX_RX5"},
2999 {"IIR1", NULL, "IIR1 INP1 MUX"},
3000 {"IIR1 INP1 MUX", "DEC0", "RX_TX DEC0_INP"},
3001 {"IIR1 INP1 MUX", "DEC1", "RX_TX DEC1_INP"},
3002 {"IIR1 INP1 MUX", "DEC2", "RX_TX DEC2_INP"},
3003 {"IIR1 INP1 MUX", "DEC3", "RX_TX DEC3_INP"},
3004 {"IIR1 INP1 MUX", "RX0", "RX_RX0"},
3005 {"IIR1 INP1 MUX", "RX1", "RX_RX1"},
3006 {"IIR1 INP1 MUX", "RX2", "RX_RX2"},
3007 {"IIR1 INP1 MUX", "RX3", "RX_RX3"},
3008 {"IIR1 INP1 MUX", "RX4", "RX_RX4"},
3009 {"IIR1 INP1 MUX", "RX5", "RX_RX5"},
3010 {"IIR1", NULL, "IIR1 INP2 MUX"},
3011 {"IIR1 INP2 MUX", "DEC0", "RX_TX DEC0_INP"},
3012 {"IIR1 INP2 MUX", "DEC1", "RX_TX DEC1_INP"},
3013 {"IIR1 INP2 MUX", "DEC2", "RX_TX DEC2_INP"},
3014 {"IIR1 INP2 MUX", "DEC3", "RX_TX DEC3_INP"},
3015 {"IIR1 INP2 MUX", "RX0", "RX_RX0"},
3016 {"IIR1 INP2 MUX", "RX1", "RX_RX1"},
3017 {"IIR1 INP2 MUX", "RX2", "RX_RX2"},
3018 {"IIR1 INP2 MUX", "RX3", "RX_RX3"},
3019 {"IIR1 INP2 MUX", "RX4", "RX_RX4"},
3020 {"IIR1 INP2 MUX", "RX5", "RX_RX5"},
3021 {"IIR1", NULL, "IIR1 INP3 MUX"},
3022 {"IIR1 INP3 MUX", "DEC0", "RX_TX DEC0_INP"},
3023 {"IIR1 INP3 MUX", "DEC1", "RX_TX DEC1_INP"},
3024 {"IIR1 INP3 MUX", "DEC2", "RX_TX DEC2_INP"},
3025 {"IIR1 INP3 MUX", "DEC3", "RX_TX DEC3_INP"},
3026 {"IIR1 INP3 MUX", "RX0", "RX_RX0"},
3027 {"IIR1 INP3 MUX", "RX1", "RX_RX1"},
3028 {"IIR1 INP3 MUX", "RX2", "RX_RX2"},
3029 {"IIR1 INP3 MUX", "RX3", "RX_RX3"},
3030 {"IIR1 INP3 MUX", "RX4", "RX_RX4"},
3031 {"IIR1 INP3 MUX", "RX5", "RX_RX5"},
3032
3033 {"SRC0", NULL, "IIR0"},
3034 {"SRC1", NULL, "IIR1"},
3035 {"RX INT0 MIX2 INP", "SRC0", "SRC0"},
3036 {"RX INT0 MIX2 INP", "SRC1", "SRC1"},
3037 {"RX INT1 MIX2 INP", "SRC0", "SRC0"},
3038 {"RX INT1 MIX2 INP", "SRC1", "SRC1"},
3039 {"RX INT2 MIX2 INP", "SRC0", "SRC0"},
3040 {"RX INT2 MIX2 INP", "SRC1", "SRC1"},
3041};
3042
3043static int rx_swrm_clock(void *handle, bool enable)
3044{
3045 struct rx_macro_priv *rx_priv = (struct rx_macro_priv *) handle;
3046 struct regmap *regmap = dev_get_regmap(rx_priv->dev->parent, NULL);
3047 int ret = 0;
3048
Tanya Dixit8530fb92018-09-14 16:01:25 +05303049 if (regmap == NULL) {
3050 dev_err(rx_priv->dev, "%s: regmap is NULL\n", __func__);
3051 return -EINVAL;
3052 }
3053
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303054 mutex_lock(&rx_priv->swr_clk_lock);
3055
3056 dev_dbg(rx_priv->dev, "%s: swrm clock %s\n",
3057 __func__, (enable ? "enable" : "disable"));
3058 if (enable) {
3059 if (rx_priv->swr_clk_users == 0) {
3060 ret = rx_macro_mclk_enable(rx_priv, 1, true);
3061 if (ret < 0) {
3062 dev_err(rx_priv->dev,
3063 "%s: rx request clock enable failed\n",
3064 __func__);
3065 goto exit;
3066 }
3067 regmap_update_bits(regmap,
3068 BOLERO_CDC_RX_CLK_RST_CTRL_SWR_CONTROL,
Ramprasad Katkam9c2394a2018-08-23 13:13:48 +05303069 0x02, 0x02);
3070 regmap_update_bits(regmap,
3071 BOLERO_CDC_RX_CLK_RST_CTRL_SWR_CONTROL,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303072 0x01, 0x01);
3073 regmap_update_bits(regmap,
3074 BOLERO_CDC_RX_CLK_RST_CTRL_SWR_CONTROL,
Ramprasad Katkam9c2394a2018-08-23 13:13:48 +05303075 0x02, 0x00);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303076 msm_cdc_pinctrl_select_active_state(
3077 rx_priv->rx_swr_gpio_p);
3078 }
3079 rx_priv->swr_clk_users++;
3080 } else {
3081 if (rx_priv->swr_clk_users <= 0) {
3082 dev_err(rx_priv->dev,
3083 "%s: rx swrm clock users already reset\n",
3084 __func__);
3085 rx_priv->swr_clk_users = 0;
3086 goto exit;
3087 }
3088 rx_priv->swr_clk_users--;
3089 if (rx_priv->swr_clk_users == 0) {
3090 regmap_update_bits(regmap,
3091 BOLERO_CDC_RX_CLK_RST_CTRL_SWR_CONTROL,
3092 0x01, 0x00);
3093 msm_cdc_pinctrl_select_sleep_state(
3094 rx_priv->rx_swr_gpio_p);
3095 rx_macro_mclk_enable(rx_priv, 0, true);
3096 }
3097 }
3098 dev_dbg(rx_priv->dev, "%s: swrm clock users %d\n",
3099 __func__, rx_priv->swr_clk_users);
3100exit:
3101 mutex_unlock(&rx_priv->swr_clk_lock);
3102 return ret;
3103}
3104
Meng Wang15c825d2018-09-06 10:49:18 +08003105static void rx_macro_init_bcl_pmic_reg(struct snd_soc_component *component)
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303106{
3107 struct device *rx_dev = NULL;
3108 struct rx_macro_priv *rx_priv = NULL;
3109
Meng Wang15c825d2018-09-06 10:49:18 +08003110 if (!component) {
3111 pr_err("%s: NULL component pointer!\n", __func__);
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303112 return;
3113 }
3114
Meng Wang15c825d2018-09-06 10:49:18 +08003115 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303116 return;
3117
3118 switch (rx_priv->bcl_pmic_params.id) {
3119 case 0:
3120 /* Enable ID0 to listen to respective PMIC group interrupts */
Meng Wang15c825d2018-09-06 10:49:18 +08003121 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303122 BOLERO_CDC_RX_BCL_VBAT_DECODE_CTL1, 0x02, 0x02);
3123 /* Update MC_SID0 */
Meng Wang15c825d2018-09-06 10:49:18 +08003124 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303125 BOLERO_CDC_RX_BCL_VBAT_DECODE_CFG1, 0x0F,
3126 rx_priv->bcl_pmic_params.sid);
3127 /* Update MC_PPID0 */
Meng Wang15c825d2018-09-06 10:49:18 +08003128 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303129 BOLERO_CDC_RX_BCL_VBAT_DECODE_CFG2, 0xFF,
3130 rx_priv->bcl_pmic_params.ppid);
3131 break;
3132 case 1:
3133 /* Enable ID1 to listen to respective PMIC group interrupts */
Meng Wang15c825d2018-09-06 10:49:18 +08003134 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303135 BOLERO_CDC_RX_BCL_VBAT_DECODE_CTL1, 0x01, 0x01);
3136 /* Update MC_SID1 */
Meng Wang15c825d2018-09-06 10:49:18 +08003137 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303138 BOLERO_CDC_RX_BCL_VBAT_DECODE_CFG3, 0x0F,
3139 rx_priv->bcl_pmic_params.sid);
3140 /* Update MC_PPID1 */
Meng Wang15c825d2018-09-06 10:49:18 +08003141 snd_soc_component_update_bits(component,
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303142 BOLERO_CDC_RX_BCL_VBAT_DECODE_CFG1, 0xFF,
3143 rx_priv->bcl_pmic_params.ppid);
3144 break;
3145 default:
Md Mansoor Ahmed26d8bdd2018-11-20 10:56:01 +05303146 dev_err(rx_dev, "%s: PMIC ID is invalid %d\n",
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303147 __func__, rx_priv->bcl_pmic_params.id);
3148 break;
3149 }
3150}
3151
Meng Wang15c825d2018-09-06 10:49:18 +08003152static int rx_macro_init(struct snd_soc_component *component)
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303153{
Meng Wang15c825d2018-09-06 10:49:18 +08003154 struct snd_soc_dapm_context *dapm =
3155 snd_soc_component_get_dapm(component);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303156 int ret = 0;
3157 struct device *rx_dev = NULL;
3158 struct rx_macro_priv *rx_priv = NULL;
3159
Meng Wang15c825d2018-09-06 10:49:18 +08003160 rx_dev = bolero_get_device_ptr(component->dev, RX_MACRO);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303161 if (!rx_dev) {
Meng Wang15c825d2018-09-06 10:49:18 +08003162 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303163 "%s: null device for macro!\n", __func__);
3164 return -EINVAL;
3165 }
3166 rx_priv = dev_get_drvdata(rx_dev);
3167 if (!rx_priv) {
Meng Wang15c825d2018-09-06 10:49:18 +08003168 dev_err(component->dev,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303169 "%s: priv is null for macro!\n", __func__);
3170 return -EINVAL;
3171 }
3172
3173 ret = snd_soc_dapm_new_controls(dapm, rx_macro_dapm_widgets,
3174 ARRAY_SIZE(rx_macro_dapm_widgets));
3175 if (ret < 0) {
3176 dev_err(rx_dev, "%s: failed to add controls\n", __func__);
3177 return ret;
3178 }
3179 ret = snd_soc_dapm_add_routes(dapm, rx_audio_map,
3180 ARRAY_SIZE(rx_audio_map));
3181 if (ret < 0) {
3182 dev_err(rx_dev, "%s: failed to add routes\n", __func__);
3183 return ret;
3184 }
3185 ret = snd_soc_dapm_new_widgets(dapm->card);
3186 if (ret < 0) {
3187 dev_err(rx_dev, "%s: failed to add widgets\n", __func__);
3188 return ret;
3189 }
Meng Wang15c825d2018-09-06 10:49:18 +08003190 ret = snd_soc_add_component_controls(component, rx_macro_snd_controls,
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303191 ARRAY_SIZE(rx_macro_snd_controls));
3192 if (ret < 0) {
3193 dev_err(rx_dev, "%s: failed to add snd_ctls\n", __func__);
3194 return ret;
3195 }
Laxminath Kasam701e3582018-10-15 20:06:09 +05303196 rx_priv->dev_up = true;
Laxminath Kasam638b5602018-09-24 13:19:52 +05303197 snd_soc_dapm_ignore_suspend(dapm, "RX_MACRO_AIF1 Playback");
3198 snd_soc_dapm_ignore_suspend(dapm, "RX_MACRO_AIF2 Playback");
3199 snd_soc_dapm_ignore_suspend(dapm, "RX_MACRO_AIF3 Playback");
3200 snd_soc_dapm_ignore_suspend(dapm, "RX_MACRO_AIF4 Playback");
3201 snd_soc_dapm_ignore_suspend(dapm, "HPHL_OUT");
3202 snd_soc_dapm_ignore_suspend(dapm, "HPHR_OUT");
3203 snd_soc_dapm_ignore_suspend(dapm, "AUX_OUT");
3204 snd_soc_dapm_ignore_suspend(dapm, "RX_TX DEC0_INP");
3205 snd_soc_dapm_ignore_suspend(dapm, "RX_TX DEC1_INP");
3206 snd_soc_dapm_ignore_suspend(dapm, "RX_TX DEC2_INP");
3207 snd_soc_dapm_ignore_suspend(dapm, "RX_TX DEC3_INP");
3208 snd_soc_dapm_sync(dapm);
3209
Meng Wang15c825d2018-09-06 10:49:18 +08003210 snd_soc_component_update_bits(component,
3211 BOLERO_CDC_RX_RX0_RX_PATH_DSM_CTL,
3212 0x01, 0x01);
3213 snd_soc_component_update_bits(component,
3214 BOLERO_CDC_RX_RX1_RX_PATH_DSM_CTL,
3215 0x01, 0x01);
3216 snd_soc_component_update_bits(component,
3217 BOLERO_CDC_RX_RX2_RX_PATH_DSM_CTL,
3218 0x01, 0x01);
3219 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX0_RX_PATH_SEC7,
3220 0x07, 0x02);
3221 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX1_RX_PATH_SEC7,
3222 0x07, 0x02);
3223 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX2_RX_PATH_SEC7,
3224 0x07, 0x02);
3225 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX0_RX_PATH_CFG3,
3226 0x03, 0x02);
3227 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX1_RX_PATH_CFG3,
3228 0x03, 0x02);
3229 snd_soc_component_update_bits(component, BOLERO_CDC_RX_RX2_RX_PATH_CFG3,
3230 0x03, 0x02);
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303231
Meng Wang15c825d2018-09-06 10:49:18 +08003232 rx_macro_init_bcl_pmic_reg(component);
3233
3234 rx_priv->component = component;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303235
3236 return 0;
3237}
3238
Meng Wang15c825d2018-09-06 10:49:18 +08003239static int rx_macro_deinit(struct snd_soc_component *component)
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303240{
3241 struct device *rx_dev = NULL;
3242 struct rx_macro_priv *rx_priv = NULL;
3243
Meng Wang15c825d2018-09-06 10:49:18 +08003244 if (!rx_macro_get_data(component, &rx_dev, &rx_priv, __func__))
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303245 return -EINVAL;
3246
Meng Wang15c825d2018-09-06 10:49:18 +08003247 rx_priv->component = NULL;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303248
3249 return 0;
3250}
3251
3252static void rx_macro_add_child_devices(struct work_struct *work)
3253{
3254 struct rx_macro_priv *rx_priv = NULL;
3255 struct platform_device *pdev = NULL;
3256 struct device_node *node = NULL;
3257 struct rx_swr_ctrl_data *swr_ctrl_data = NULL, *temp = NULL;
3258 int ret = 0;
3259 u16 count = 0, ctrl_num = 0;
3260 struct rx_swr_ctrl_platform_data *platdata = NULL;
3261 char plat_dev_name[RX_SWR_STRING_LEN] = "";
3262 bool rx_swr_master_node = false;
3263
3264 rx_priv = container_of(work, struct rx_macro_priv,
3265 rx_macro_add_child_devices_work);
3266 if (!rx_priv) {
3267 pr_err("%s: Memory for rx_priv does not exist\n",
3268 __func__);
3269 return;
3270 }
3271
3272 if (!rx_priv->dev) {
3273 pr_err("%s: RX device does not exist\n", __func__);
3274 return;
3275 }
3276
3277 if(!rx_priv->dev->of_node) {
3278 dev_err(rx_priv->dev,
3279 "%s: DT node for RX dev does not exist\n", __func__);
3280 return;
3281 }
3282
3283 platdata = &rx_priv->swr_plat_data;
3284 rx_priv->child_count = 0;
3285
3286 for_each_available_child_of_node(rx_priv->dev->of_node, node) {
3287 rx_swr_master_node = false;
3288 if (strnstr(node->name, "rx_swr_master",
3289 strlen("rx_swr_master")) != NULL)
3290 rx_swr_master_node = true;
3291
3292 if(rx_swr_master_node)
3293 strlcpy(plat_dev_name, "rx_swr_ctrl",
3294 (RX_SWR_STRING_LEN - 1));
3295 else
3296 strlcpy(plat_dev_name, node->name,
3297 (RX_SWR_STRING_LEN - 1));
3298
3299 pdev = platform_device_alloc(plat_dev_name, -1);
3300 if (!pdev) {
3301 dev_err(rx_priv->dev, "%s: pdev memory alloc failed\n",
3302 __func__);
3303 ret = -ENOMEM;
3304 goto err;
3305 }
3306 pdev->dev.parent = rx_priv->dev;
3307 pdev->dev.of_node = node;
3308
3309 if (rx_swr_master_node) {
3310 ret = platform_device_add_data(pdev, platdata,
3311 sizeof(*platdata));
3312 if (ret) {
3313 dev_err(&pdev->dev,
3314 "%s: cannot add plat data ctrl:%d\n",
3315 __func__, ctrl_num);
3316 goto fail_pdev_add;
3317 }
3318 }
3319
3320 ret = platform_device_add(pdev);
3321 if (ret) {
3322 dev_err(&pdev->dev,
3323 "%s: Cannot add platform device\n",
3324 __func__);
3325 goto fail_pdev_add;
3326 }
3327
3328 if (rx_swr_master_node) {
3329 temp = krealloc(swr_ctrl_data,
3330 (ctrl_num + 1) * sizeof(
3331 struct rx_swr_ctrl_data),
3332 GFP_KERNEL);
3333 if (!temp) {
3334 ret = -ENOMEM;
3335 goto fail_pdev_add;
3336 }
3337 swr_ctrl_data = temp;
3338 swr_ctrl_data[ctrl_num].rx_swr_pdev = pdev;
3339 ctrl_num++;
3340 dev_dbg(&pdev->dev,
3341 "%s: Added soundwire ctrl device(s)\n",
3342 __func__);
3343 rx_priv->swr_ctrl_data = swr_ctrl_data;
3344 }
3345 if (rx_priv->child_count < RX_MACRO_CHILD_DEVICES_MAX)
3346 rx_priv->pdev_child_devices[
3347 rx_priv->child_count++] = pdev;
3348 else
3349 goto err;
3350 }
3351 return;
3352fail_pdev_add:
3353 for (count = 0; count < rx_priv->child_count; count++)
3354 platform_device_put(rx_priv->pdev_child_devices[count]);
3355err:
3356 return;
3357}
3358
3359static void rx_macro_init_ops(struct macro_ops *ops, char __iomem *rx_io_base)
3360{
3361 memset(ops, 0, sizeof(struct macro_ops));
3362 ops->init = rx_macro_init;
3363 ops->exit = rx_macro_deinit;
3364 ops->io_base = rx_io_base;
3365 ops->dai_ptr = rx_macro_dai;
3366 ops->num_dais = ARRAY_SIZE(rx_macro_dai);
3367 ops->mclk_fn = rx_macro_mclk_ctrl;
Laxminath Kasam497a6512018-09-17 16:11:52 +05303368 ops->event_handler = rx_macro_event_handler;
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303369}
3370
3371static int rx_macro_probe(struct platform_device *pdev)
3372{
3373 struct macro_ops ops = {0};
3374 struct rx_macro_priv *rx_priv = NULL;
3375 u32 rx_base_addr = 0, muxsel = 0;
3376 char __iomem *rx_io_base = NULL, *muxsel_io = NULL;
3377 int ret = 0;
3378 struct clk *rx_core_clk = NULL, *rx_npl_clk = NULL;
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303379 u8 bcl_pmic_params[3];
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303380
3381 rx_priv = devm_kzalloc(&pdev->dev, sizeof(struct rx_macro_priv),
3382 GFP_KERNEL);
3383 if (!rx_priv)
3384 return -ENOMEM;
3385
3386 rx_priv->dev = &pdev->dev;
3387 ret = of_property_read_u32(pdev->dev.of_node, "reg",
3388 &rx_base_addr);
3389 if (ret) {
3390 dev_err(&pdev->dev, "%s: could not find %s entry in dt\n",
3391 __func__, "reg");
3392 return ret;
3393 }
3394 ret = of_property_read_u32(pdev->dev.of_node, "qcom,rx_mclk_mode_muxsel",
3395 &muxsel);
3396 if (ret) {
3397 dev_err(&pdev->dev, "%s: could not find %s entry in dt\n",
3398 __func__, "reg");
3399 return ret;
3400 }
3401 rx_priv->rx_swr_gpio_p = of_parse_phandle(pdev->dev.of_node,
3402 "qcom,rx-swr-gpios", 0);
3403 if (!rx_priv->rx_swr_gpio_p) {
3404 dev_err(&pdev->dev, "%s: swr_gpios handle not provided!\n",
3405 __func__);
3406 return -EINVAL;
3407 }
3408 rx_io_base = devm_ioremap(&pdev->dev, rx_base_addr,
3409 RX_MACRO_MAX_OFFSET);
3410 if (!rx_io_base) {
3411 dev_err(&pdev->dev, "%s: ioremap failed\n", __func__);
3412 return -ENOMEM;
3413 }
3414 rx_priv->rx_io_base = rx_io_base;
3415 muxsel_io = devm_ioremap(&pdev->dev, muxsel, 0x4);
3416 if (!muxsel_io) {
3417 dev_err(&pdev->dev, "%s: ioremap failed for muxsel\n",
3418 __func__);
3419 return -ENOMEM;
3420 }
3421 rx_priv->rx_mclk_mode_muxsel = muxsel_io;
3422 INIT_WORK(&rx_priv->rx_macro_add_child_devices_work,
3423 rx_macro_add_child_devices);
3424 rx_priv->swr_plat_data.handle = (void *) rx_priv;
3425 rx_priv->swr_plat_data.read = NULL;
3426 rx_priv->swr_plat_data.write = NULL;
3427 rx_priv->swr_plat_data.bulk_write = NULL;
3428 rx_priv->swr_plat_data.clk = rx_swrm_clock;
3429 rx_priv->swr_plat_data.handle_irq = NULL;
3430
3431 /* Register MCLK for rx macro */
3432 rx_core_clk = devm_clk_get(&pdev->dev, "rx_core_clk");
3433 if (IS_ERR(rx_core_clk)) {
3434 ret = PTR_ERR(rx_core_clk);
3435 dev_err(&pdev->dev, "%s: clk get %s failed %d\n",
3436 __func__, "rx_core_clk", ret);
3437 return ret;
3438 }
3439 rx_priv->rx_core_clk = rx_core_clk;
3440 /* Register npl clk for soundwire */
3441 rx_npl_clk = devm_clk_get(&pdev->dev, "rx_npl_clk");
3442 if (IS_ERR(rx_npl_clk)) {
3443 ret = PTR_ERR(rx_npl_clk);
3444 dev_err(&pdev->dev, "%s: clk get %s failed %d\n",
3445 __func__, "rx_npl_clk", ret);
3446 return ret;
3447 }
3448 rx_priv->rx_npl_clk = rx_npl_clk;
Aditya Bavanari4f3d5642018-09-18 22:19:10 +05303449
3450 ret = of_property_read_u8_array(pdev->dev.of_node,
3451 "qcom,rx-bcl-pmic-params", bcl_pmic_params,
3452 sizeof(bcl_pmic_params));
3453 if (ret) {
3454 dev_dbg(&pdev->dev, "%s: could not find %s entry in dt\n",
3455 __func__, "qcom,rx-bcl-pmic-params");
3456 } else {
3457 rx_priv->bcl_pmic_params.id = bcl_pmic_params[0];
3458 rx_priv->bcl_pmic_params.sid = bcl_pmic_params[1];
3459 rx_priv->bcl_pmic_params.ppid = bcl_pmic_params[2];
3460 }
3461
Laxminath Kasama7ecc582018-06-15 16:55:02 +05303462 dev_set_drvdata(&pdev->dev, rx_priv);
3463 mutex_init(&rx_priv->mclk_lock);
3464 mutex_init(&rx_priv->swr_clk_lock);
3465 rx_macro_init_ops(&ops, rx_io_base);
3466
3467 ret = bolero_register_macro(&pdev->dev, RX_MACRO, &ops);
3468 if (ret) {
3469 dev_err(&pdev->dev,
3470 "%s: register macro failed\n", __func__);
3471 goto err_reg_macro;
3472 }
3473 schedule_work(&rx_priv->rx_macro_add_child_devices_work);
3474
3475 return 0;
3476
3477err_reg_macro:
3478 mutex_destroy(&rx_priv->mclk_lock);
3479 mutex_destroy(&rx_priv->swr_clk_lock);
3480 return ret;
3481}
3482
3483static int rx_macro_remove(struct platform_device *pdev)
3484{
3485 struct rx_macro_priv *rx_priv = NULL;
3486 u16 count = 0;
3487
3488 rx_priv = dev_get_drvdata(&pdev->dev);
3489
3490 if (!rx_priv)
3491 return -EINVAL;
3492
3493 for (count = 0; count < rx_priv->child_count &&
3494 count < RX_MACRO_CHILD_DEVICES_MAX; count++)
3495 platform_device_unregister(rx_priv->pdev_child_devices[count]);
3496
3497 bolero_unregister_macro(&pdev->dev, RX_MACRO);
3498 mutex_destroy(&rx_priv->mclk_lock);
3499 mutex_destroy(&rx_priv->swr_clk_lock);
3500 kfree(rx_priv->swr_ctrl_data);
3501 return 0;
3502}
3503
3504static const struct of_device_id rx_macro_dt_match[] = {
3505 {.compatible = "qcom,rx-macro"},
3506 {}
3507};
3508
3509static struct platform_driver rx_macro_driver = {
3510 .driver = {
3511 .name = "rx_macro",
3512 .owner = THIS_MODULE,
3513 .of_match_table = rx_macro_dt_match,
3514 },
3515 .probe = rx_macro_probe,
3516 .remove = rx_macro_remove,
3517};
3518
3519module_platform_driver(rx_macro_driver);
3520
3521MODULE_DESCRIPTION("RX macro driver");
3522MODULE_LICENSE("GPL v2");