xref: /linux/sound/soc/ux500/ux500_msp_i2s.c (revision 2519439b4b5f6ee95879b1a44fc373127291b1e4)
1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * Copyright (C) ST-Ericsson SA 2012
4  *
5  * Author: Ola Lilja <ola.o.lilja@stericsson.com>,
6  *         Roger Nilsson <roger.xr.nilsson@stericsson.com>,
7  *         Sandeep Kaushik <sandeep.kaushik@st.com>
8  *         for ST-Ericsson.
9  */
10 
11 #include <linux/module.h>
12 #include <linux/platform_device.h>
13 #include <linux/delay.h>
14 #include <linux/slab.h>
15 #include <linux/io.h>
16 #include <linux/of.h>
17 
18 #include <sound/soc.h>
19 
20 #include "ux500_msp_i2s.h"
21 
22  /* Protocol desciptors */
23 static const struct msp_protdesc prot_descs[] = {
24 	{ /* I2S */
25 		MSP_SINGLE_PHASE,
26 		MSP_SINGLE_PHASE,
27 		MSP_PHASE2_START_MODE_IMEDIATE,
28 		MSP_PHASE2_START_MODE_IMEDIATE,
29 		MSP_BTF_MS_BIT_FIRST,
30 		MSP_BTF_MS_BIT_FIRST,
31 		MSP_FRAME_LEN_1,
32 		MSP_FRAME_LEN_1,
33 		MSP_FRAME_LEN_1,
34 		MSP_FRAME_LEN_1,
35 		MSP_ELEM_LEN_32,
36 		MSP_ELEM_LEN_32,
37 		MSP_ELEM_LEN_32,
38 		MSP_ELEM_LEN_32,
39 		MSP_DELAY_1,
40 		MSP_DELAY_1,
41 		MSP_RISING_EDGE,
42 		MSP_FALLING_EDGE,
43 		MSP_FSYNC_POL_ACT_LO,
44 		MSP_FSYNC_POL_ACT_LO,
45 		MSP_SWAP_NONE,
46 		MSP_SWAP_NONE,
47 		MSP_COMPRESS_MODE_LINEAR,
48 		MSP_EXPAND_MODE_LINEAR,
49 		MSP_FSYNC_IGNORE,
50 		31,
51 		15,
52 		32,
53 	}, { /* PCM */
54 		MSP_DUAL_PHASE,
55 		MSP_DUAL_PHASE,
56 		MSP_PHASE2_START_MODE_FSYNC,
57 		MSP_PHASE2_START_MODE_FSYNC,
58 		MSP_BTF_MS_BIT_FIRST,
59 		MSP_BTF_MS_BIT_FIRST,
60 		MSP_FRAME_LEN_1,
61 		MSP_FRAME_LEN_1,
62 		MSP_FRAME_LEN_1,
63 		MSP_FRAME_LEN_1,
64 		MSP_ELEM_LEN_16,
65 		MSP_ELEM_LEN_16,
66 		MSP_ELEM_LEN_16,
67 		MSP_ELEM_LEN_16,
68 		MSP_DELAY_0,
69 		MSP_DELAY_0,
70 		MSP_RISING_EDGE,
71 		MSP_FALLING_EDGE,
72 		MSP_FSYNC_POL_ACT_HI,
73 		MSP_FSYNC_POL_ACT_HI,
74 		MSP_SWAP_NONE,
75 		MSP_SWAP_NONE,
76 		MSP_COMPRESS_MODE_LINEAR,
77 		MSP_EXPAND_MODE_LINEAR,
78 		MSP_FSYNC_IGNORE,
79 		255,
80 		0,
81 		256,
82 	}, { /* Companded PCM */
83 		MSP_SINGLE_PHASE,
84 		MSP_SINGLE_PHASE,
85 		MSP_PHASE2_START_MODE_FSYNC,
86 		MSP_PHASE2_START_MODE_FSYNC,
87 		MSP_BTF_MS_BIT_FIRST,
88 		MSP_BTF_MS_BIT_FIRST,
89 		MSP_FRAME_LEN_1,
90 		MSP_FRAME_LEN_1,
91 		MSP_FRAME_LEN_1,
92 		MSP_FRAME_LEN_1,
93 		MSP_ELEM_LEN_8,
94 		MSP_ELEM_LEN_8,
95 		MSP_ELEM_LEN_8,
96 		MSP_ELEM_LEN_8,
97 		MSP_DELAY_0,
98 		MSP_DELAY_0,
99 		MSP_RISING_EDGE,
100 		MSP_RISING_EDGE,
101 		MSP_FSYNC_POL_ACT_HI,
102 		MSP_FSYNC_POL_ACT_HI,
103 		MSP_SWAP_NONE,
104 		MSP_SWAP_NONE,
105 		MSP_COMPRESS_MODE_LINEAR,
106 		MSP_EXPAND_MODE_LINEAR,
107 		MSP_FSYNC_IGNORE,
108 		255,
109 		0,
110 		256,
111 	},
112 };
113 
114 static void set_prot_desc_tx(struct ux500_msp *msp,
115 			struct msp_protdesc *protdesc,
116 			enum msp_data_size data_size)
117 {
118 	u32 temp_reg = 0;
119 
120 	temp_reg |= MSP_P2_ENABLE_BIT(protdesc->tx_phase_mode);
121 	temp_reg |= MSP_P2_START_MODE_BIT(protdesc->tx_phase2_start_mode);
122 	temp_reg |= MSP_P1_FRAME_LEN_BITS(protdesc->tx_frame_len_1);
123 	temp_reg |= MSP_P2_FRAME_LEN_BITS(protdesc->tx_frame_len_2);
124 	if (msp->def_elem_len) {
125 		temp_reg |= MSP_P1_ELEM_LEN_BITS(protdesc->tx_elem_len_1);
126 		temp_reg |= MSP_P2_ELEM_LEN_BITS(protdesc->tx_elem_len_2);
127 	} else {
128 		temp_reg |= MSP_P1_ELEM_LEN_BITS(data_size);
129 		temp_reg |= MSP_P2_ELEM_LEN_BITS(data_size);
130 	}
131 	temp_reg |= MSP_DATA_DELAY_BITS(protdesc->tx_data_delay);
132 	temp_reg |= MSP_SET_ENDIANNES_BIT(protdesc->tx_byte_order);
133 	temp_reg |= MSP_FSYNC_POL(protdesc->tx_fsync_pol);
134 	temp_reg |= MSP_DATA_WORD_SWAP(protdesc->tx_half_word_swap);
135 	temp_reg |= MSP_SET_COMPANDING_MODE(protdesc->compression_mode);
136 	temp_reg |= MSP_SET_FSYNC_IGNORE(protdesc->frame_sync_ignore);
137 
138 	writel(temp_reg, msp->registers + MSP_TCF);
139 }
140 
141 static void set_prot_desc_rx(struct ux500_msp *msp,
142 			struct msp_protdesc *protdesc,
143 			enum msp_data_size data_size)
144 {
145 	u32 temp_reg = 0;
146 
147 	temp_reg |= MSP_P2_ENABLE_BIT(protdesc->rx_phase_mode);
148 	temp_reg |= MSP_P2_START_MODE_BIT(protdesc->rx_phase2_start_mode);
149 	temp_reg |= MSP_P1_FRAME_LEN_BITS(protdesc->rx_frame_len_1);
150 	temp_reg |= MSP_P2_FRAME_LEN_BITS(protdesc->rx_frame_len_2);
151 	if (msp->def_elem_len) {
152 		temp_reg |= MSP_P1_ELEM_LEN_BITS(protdesc->rx_elem_len_1);
153 		temp_reg |= MSP_P2_ELEM_LEN_BITS(protdesc->rx_elem_len_2);
154 	} else {
155 		temp_reg |= MSP_P1_ELEM_LEN_BITS(data_size);
156 		temp_reg |= MSP_P2_ELEM_LEN_BITS(data_size);
157 	}
158 
159 	temp_reg |= MSP_DATA_DELAY_BITS(protdesc->rx_data_delay);
160 	temp_reg |= MSP_SET_ENDIANNES_BIT(protdesc->rx_byte_order);
161 	temp_reg |= MSP_FSYNC_POL(protdesc->rx_fsync_pol);
162 	temp_reg |= MSP_DATA_WORD_SWAP(protdesc->rx_half_word_swap);
163 	temp_reg |= MSP_SET_COMPANDING_MODE(protdesc->expansion_mode);
164 	temp_reg |= MSP_SET_FSYNC_IGNORE(protdesc->frame_sync_ignore);
165 
166 	writel(temp_reg, msp->registers + MSP_RCF);
167 }
168 
169 static int configure_protocol(struct ux500_msp *msp,
170 			struct ux500_msp_config *config)
171 {
172 	struct msp_protdesc *protdesc;
173 	enum msp_data_size data_size;
174 	u32 temp_reg = 0;
175 
176 	data_size = config->data_size;
177 	msp->def_elem_len = config->def_elem_len;
178 	if (config->default_protdesc == 1) {
179 		if (config->protocol >= MSP_INVALID_PROTOCOL) {
180 			dev_err(msp->dev, "%s: ERROR: Invalid protocol!\n",
181 				__func__);
182 			return -EINVAL;
183 		}
184 		protdesc =
185 		    (struct msp_protdesc *)&prot_descs[config->protocol];
186 	} else {
187 		protdesc = (struct msp_protdesc *)&config->protdesc;
188 	}
189 
190 	if (data_size < MSP_DATA_BITS_DEFAULT || data_size > MSP_DATA_BITS_32) {
191 		dev_err(msp->dev,
192 			"%s: ERROR: Invalid data-size requested (data_size = %d)!\n",
193 			__func__, data_size);
194 		return -EINVAL;
195 	}
196 
197 	if (config->direction & MSP_DIR_TX)
198 		set_prot_desc_tx(msp, protdesc, data_size);
199 	if (config->direction & MSP_DIR_RX)
200 		set_prot_desc_rx(msp, protdesc, data_size);
201 
202 	/* The code below should not be separated. */
203 	temp_reg = readl(msp->registers + MSP_GCR) & ~TX_CLK_POL_RISING;
204 	temp_reg |= MSP_TX_CLKPOL_BIT(!protdesc->tx_clk_pol ^
205 					  config->bclk_inverted);
206 	writel(temp_reg, msp->registers + MSP_GCR);
207 	temp_reg = readl(msp->registers + MSP_GCR) & ~RX_CLK_POL_RISING;
208 	temp_reg |= MSP_RX_CLKPOL_BIT(protdesc->rx_clk_pol ^
209 					  config->bclk_inverted);
210 	writel(temp_reg, msp->registers + MSP_GCR);
211 
212 	return 0;
213 }
214 
215 static int setup_bitclk(struct ux500_msp *msp, struct ux500_msp_config *config)
216 {
217 	struct msp_protdesc *protdesc;
218 	u64 desired_bitclk;
219 	unsigned int bitclk;
220 	u32 reg_val_GCR;
221 	u32 sck_div;
222 	u32 temp_reg;
223 
224 	reg_val_GCR = readl(msp->registers + MSP_GCR);
225 	writel(reg_val_GCR & ~SRG_ENABLE, msp->registers + MSP_GCR);
226 
227 	switch (config->protocol) {
228 	case MSP_PCM_PROTOCOL:
229 	case MSP_PCM_COMPAND_PROTOCOL:
230 	case MSP_I2S_PROTOCOL:
231 		break;
232 	default:
233 		dev_err(msp->dev, "%s: ERROR: Unknown protocol (%d)!\n",
234 			__func__,
235 			config->protocol);
236 		return -EINVAL;
237 	}
238 
239 	if (config->default_protdesc)
240 		protdesc = (struct msp_protdesc *)&prot_descs[config->protocol];
241 	else
242 		protdesc = &config->protdesc;
243 
244 	if (!config->frame_freq || !protdesc->clocks_per_frame)
245 		return -EINVAL;
246 
247 	desired_bitclk = (u64)config->frame_freq * protdesc->clocks_per_frame;
248 	if (desired_bitclk > config->f_inputclk)
249 		return -EINVAL;
250 	bitclk = desired_bitclk;
251 	if (config->f_inputclk % bitclk) {
252 		dev_err(msp->dev,
253 			"Input clock %u cannot generate bit clock %u\n",
254 			config->f_inputclk, bitclk);
255 		return -EINVAL;
256 	}
257 
258 	sck_div = config->f_inputclk / bitclk;
259 	if (!sck_div || sck_div > SCK_DIV_MASK + 1)
260 		return -EINVAL;
261 
262 	temp_reg = (sck_div - 1) & SCK_DIV_MASK;
263 	temp_reg |= FRAME_WIDTH_BITS(protdesc->frame_width);
264 	temp_reg |= FRAME_PERIOD_BITS(protdesc->frame_period);
265 	writel(temp_reg, msp->registers + MSP_SRG);
266 
267 	msp->f_bitclk = config->f_inputclk / sck_div;
268 
269 	/* Enable bit-clock */
270 	udelay(100);
271 	reg_val_GCR = readl(msp->registers + MSP_GCR);
272 	writel(reg_val_GCR | SRG_ENABLE, msp->registers + MSP_GCR);
273 	udelay(100);
274 
275 	return 0;
276 }
277 
278 static int configure_multichannel(struct ux500_msp *msp,
279 				struct ux500_msp_config *config)
280 {
281 	struct msp_protdesc *protdesc;
282 	struct msp_multichannel_config *mcfg;
283 	u32 reg_val_MCR;
284 
285 	if (config->default_protdesc == 1) {
286 		if (config->protocol >= MSP_INVALID_PROTOCOL) {
287 			dev_err(msp->dev,
288 				"%s: ERROR: Invalid protocol (%d)!\n",
289 				__func__, config->protocol);
290 			return -EINVAL;
291 		}
292 		protdesc = (struct msp_protdesc *)
293 				&prot_descs[config->protocol];
294 	} else {
295 		protdesc = (struct msp_protdesc *)&config->protdesc;
296 	}
297 
298 	mcfg = &config->multichannel_config;
299 	if (mcfg->tx_multichannel_enable) {
300 		if (protdesc->tx_phase_mode == MSP_SINGLE_PHASE) {
301 			reg_val_MCR = readl(msp->registers + MSP_MCR);
302 			writel(reg_val_MCR | (mcfg->tx_multichannel_enable ?
303 						1 << TMCEN_BIT : 0),
304 				msp->registers + MSP_MCR);
305 			writel(mcfg->tx_channel_0_enable,
306 				msp->registers + MSP_TCE0);
307 			writel(mcfg->tx_channel_1_enable,
308 				msp->registers + MSP_TCE1);
309 			writel(mcfg->tx_channel_2_enable,
310 				msp->registers + MSP_TCE2);
311 			writel(mcfg->tx_channel_3_enable,
312 				msp->registers + MSP_TCE3);
313 		} else {
314 			dev_err(msp->dev,
315 				"%s: ERROR: Only single-phase supported (TX-mode: %d)!\n",
316 				__func__, protdesc->tx_phase_mode);
317 			return -EINVAL;
318 		}
319 	}
320 	if (mcfg->rx_multichannel_enable) {
321 		if (protdesc->rx_phase_mode == MSP_SINGLE_PHASE) {
322 			reg_val_MCR = readl(msp->registers + MSP_MCR);
323 			writel(reg_val_MCR | (mcfg->rx_multichannel_enable ?
324 						1 << RMCEN_BIT : 0),
325 				msp->registers + MSP_MCR);
326 			writel(mcfg->rx_channel_0_enable,
327 					msp->registers + MSP_RCE0);
328 			writel(mcfg->rx_channel_1_enable,
329 					msp->registers + MSP_RCE1);
330 			writel(mcfg->rx_channel_2_enable,
331 					msp->registers + MSP_RCE2);
332 			writel(mcfg->rx_channel_3_enable,
333 					msp->registers + MSP_RCE3);
334 		} else {
335 			dev_err(msp->dev,
336 				"%s: ERROR: Only single-phase supported (RX-mode: %d)!\n",
337 				__func__, protdesc->rx_phase_mode);
338 			return -EINVAL;
339 		}
340 		if (mcfg->rx_comparison_enable_mode) {
341 			reg_val_MCR = readl(msp->registers + MSP_MCR);
342 			writel(reg_val_MCR |
343 				(mcfg->rx_comparison_enable_mode << RCMPM_BIT),
344 				msp->registers + MSP_MCR);
345 
346 			writel(mcfg->comparison_mask,
347 					msp->registers + MSP_RCM);
348 			writel(mcfg->comparison_value,
349 					msp->registers + MSP_RCV);
350 
351 		}
352 	}
353 
354 	return 0;
355 }
356 
357 static int enable_msp(struct ux500_msp *msp, struct ux500_msp_config *config,
358 		      bool first)
359 {
360 	int status;
361 	u32 reg_val_DMACR;
362 
363 	/* Configure msp with protocol dependent settings */
364 	status = configure_protocol(msp, config);
365 	if (status)
366 		return status;
367 
368 	if (first && config->clock_provider) {
369 		status = setup_bitclk(msp, config);
370 		if (status)
371 			return status;
372 	}
373 
374 	if (config->multichannel_configured == 1) {
375 		status = configure_multichannel(msp, config);
376 		if (status)
377 			return status;
378 	}
379 
380 	reg_val_DMACR = readl(msp->registers + MSP_DMACR);
381 	if (config->direction & MSP_DIR_RX)
382 		reg_val_DMACR |= RX_DMA_ENABLE;
383 	if (config->direction & MSP_DIR_TX)
384 		reg_val_DMACR |= TX_DMA_ENABLE;
385 	writel(reg_val_DMACR, msp->registers + MSP_DMACR);
386 
387 	writel(config->iodelay, msp->registers + MSP_IODLY);
388 
389 	return 0;
390 }
391 
392 static void flush_fifo_rx(struct ux500_msp *msp)
393 {
394 	u32 reg_val_GCR, reg_val_FLR;
395 	u32 limit = 32;
396 
397 	reg_val_GCR = readl(msp->registers + MSP_GCR);
398 	writel(reg_val_GCR | RX_ENABLE, msp->registers + MSP_GCR);
399 
400 	reg_val_FLR = readl(msp->registers + MSP_FLR);
401 	while (!(reg_val_FLR & RX_FIFO_EMPTY) && limit--) {
402 		readl(msp->registers + MSP_DR);
403 		reg_val_FLR = readl(msp->registers + MSP_FLR);
404 	}
405 
406 	writel(reg_val_GCR, msp->registers + MSP_GCR);
407 }
408 
409 static void flush_fifo_tx(struct ux500_msp *msp)
410 {
411 	u32 reg_val_GCR, reg_val_FLR;
412 	u32 limit = 32;
413 
414 	reg_val_GCR = readl(msp->registers + MSP_GCR);
415 	writel(reg_val_GCR | TX_ENABLE, msp->registers + MSP_GCR);
416 	writel(MSP_ITCR_ITEN | MSP_ITCR_TESTFIFO, msp->registers + MSP_ITCR);
417 
418 	reg_val_FLR = readl(msp->registers + MSP_FLR);
419 	while (!(reg_val_FLR & TX_FIFO_EMPTY) && limit--) {
420 		readl(msp->registers + MSP_TSTDR);
421 		reg_val_FLR = readl(msp->registers + MSP_FLR);
422 	}
423 	writel(0x0, msp->registers + MSP_ITCR);
424 	writel(reg_val_GCR, msp->registers + MSP_GCR);
425 }
426 
427 static bool ux500_msp_config_compatible(struct ux500_msp *msp,
428 					struct ux500_msp_config *config)
429 {
430 	struct ux500_msp_config *active = &msp->config;
431 
432 	return active->f_inputclk == config->f_inputclk &&
433 	       active->tx_clk_sel == config->tx_clk_sel &&
434 	       active->rx_clk_sel == config->rx_clk_sel &&
435 	       active->srg_clk_sel == config->srg_clk_sel &&
436 	       active->rx_fsync_pol == config->rx_fsync_pol &&
437 	       active->tx_fsync_pol == config->tx_fsync_pol &&
438 	       active->rx_fsync_sel == config->rx_fsync_sel &&
439 	       active->tx_fsync_sel == config->tx_fsync_sel &&
440 	       active->default_protdesc == config->default_protdesc &&
441 	       active->protocol == config->protocol &&
442 	       active->frame_freq == config->frame_freq &&
443 	       active->data_size == config->data_size &&
444 	       active->def_elem_len == config->def_elem_len &&
445 	       active->clock_provider == config->clock_provider &&
446 	       active->bclk_inverted == config->bclk_inverted &&
447 	       !memcmp(&active->protdesc, &config->protdesc,
448 		       sizeof(active->protdesc));
449 }
450 
451 int ux500_msp_i2s_open(struct ux500_msp *msp,
452 		struct ux500_msp_config *config)
453 {
454 	u32 old_reg, new_reg, mask;
455 	int res;
456 	unsigned int tx_sel, rx_sel, tx_busy, rx_busy;
457 	bool first;
458 
459 	if (in_interrupt()) {
460 		dev_err(msp->dev,
461 			"%s: ERROR: Open called in interrupt context!\n",
462 			__func__);
463 		return -1;
464 	}
465 
466 	tx_sel = (config->direction & MSP_DIR_TX) > 0;
467 	rx_sel = (config->direction & MSP_DIR_RX) > 0;
468 	if (!tx_sel && !rx_sel) {
469 		dev_err(msp->dev, "%s: Error: No direction selected!\n",
470 			__func__);
471 		return -EINVAL;
472 	}
473 
474 	tx_busy = (msp->dir_busy & MSP_DIR_TX) > 0;
475 	rx_busy = (msp->dir_busy & MSP_DIR_RX) > 0;
476 	if (tx_busy && tx_sel) {
477 		dev_err(msp->dev, "%s: Error: TX is in use!\n", __func__);
478 		return -EBUSY;
479 	}
480 	if (rx_busy && rx_sel) {
481 		dev_err(msp->dev, "%s: Error: RX is in use!\n", __func__);
482 		return -EBUSY;
483 	}
484 
485 	first = !msp->dir_busy;
486 	if (!first && !ux500_msp_config_compatible(msp, config)) {
487 		dev_err(msp->dev, "%s: Incompatible duplex configuration\n",
488 			__func__);
489 		return -EBUSY;
490 	}
491 
492 	if (first) {
493 		/* First do the global config register */
494 		mask = RX_CLK_SEL_MASK | TX_CLK_SEL_MASK | RX_FSYNC_MASK |
495 		       TX_FSYNC_MASK | RX_SYNC_SEL_MASK | TX_SYNC_SEL_MASK |
496 		       RX_FIFO_ENABLE_MASK | TX_FIFO_ENABLE_MASK |
497 		       SRG_CLK_SEL_MASK | LOOPBACK_MASK | TX_EXTRA_DELAY_MASK;
498 
499 		new_reg = config->tx_clk_sel | config->rx_clk_sel |
500 			  config->rx_fsync_pol | config->tx_fsync_pol |
501 			  config->rx_fsync_sel | config->tx_fsync_sel |
502 			  config->rx_fifo_config | config->tx_fifo_config |
503 			  config->srg_clk_sel | config->loopback_enable |
504 			  config->tx_data_enable;
505 
506 		old_reg = readl(msp->registers + MSP_GCR);
507 		old_reg &= ~mask;
508 		new_reg |= old_reg;
509 		writel(new_reg, msp->registers + MSP_GCR);
510 		writel(MSP_WMRK_TX_4_ELEMENTS | MSP_WMRK_RX_4_ELEMENTS,
511 		       msp->registers + MSP_WMRK);
512 	}
513 
514 	res = enable_msp(msp, config, first);
515 	if (res < 0) {
516 		dev_err(msp->dev, "%s: ERROR: enable_msp failed (%d)!\n",
517 			__func__, res);
518 		if (tx_sel)
519 			writel(0, msp->registers + MSP_TCF);
520 		if (rx_sel)
521 			writel(0, msp->registers + MSP_RCF);
522 		if (first) {
523 			writel(0, msp->registers + MSP_GCR);
524 			writel(0, msp->registers + MSP_DMACR);
525 			writel(0, msp->registers + MSP_SRG);
526 			writel(0, msp->registers + MSP_MCR);
527 		}
528 		return res;
529 	}
530 
531 	msp->dir_busy |= config->direction;
532 	if (first) {
533 		msp->config = *config;
534 		msp->clock_provider = config->clock_provider;
535 	}
536 	if (config->loopback_enable & 0x80)
537 		msp->loopback_enable = 1;
538 
539 	/* Flush FIFOs */
540 	if (tx_sel)
541 		flush_fifo_tx(msp);
542 	if (rx_sel)
543 		flush_fifo_rx(msp);
544 
545 	if (!msp->dir_running)
546 		msp->msp_state = MSP_STATE_CONFIGURED;
547 	return 0;
548 }
549 
550 static void disable_msp_rx(struct ux500_msp *msp)
551 {
552 	u32 reg_val_GCR, reg_val_DMACR, reg_val_IMSC;
553 
554 	reg_val_GCR = readl(msp->registers + MSP_GCR);
555 	writel(reg_val_GCR & ~RX_ENABLE, msp->registers + MSP_GCR);
556 	reg_val_DMACR = readl(msp->registers + MSP_DMACR);
557 	writel(reg_val_DMACR & ~RX_DMA_ENABLE, msp->registers + MSP_DMACR);
558 	reg_val_IMSC = readl(msp->registers + MSP_IMSC);
559 	writel(reg_val_IMSC &
560 			~(RX_SERVICE_INT | RX_OVERRUN_ERROR_INT),
561 			msp->registers + MSP_IMSC);
562 
563 }
564 
565 static void disable_msp_tx(struct ux500_msp *msp)
566 {
567 	u32 reg_val_GCR, reg_val_DMACR, reg_val_IMSC;
568 
569 	reg_val_GCR = readl(msp->registers + MSP_GCR);
570 	writel(reg_val_GCR & ~TX_ENABLE, msp->registers + MSP_GCR);
571 	reg_val_DMACR = readl(msp->registers + MSP_DMACR);
572 	writel(reg_val_DMACR & ~TX_DMA_ENABLE, msp->registers + MSP_DMACR);
573 	reg_val_IMSC = readl(msp->registers + MSP_IMSC);
574 	writel(reg_val_IMSC &
575 			~(TX_SERVICE_INT | TX_UNDERRUN_ERR_INT),
576 			msp->registers + MSP_IMSC);
577 
578 }
579 
580 static int disable_msp(struct ux500_msp *msp, unsigned int dir)
581 {
582 	u32 reg_val_GCR;
583 	unsigned int disable_tx, disable_rx;
584 
585 	reg_val_GCR = readl(msp->registers + MSP_GCR);
586 	disable_tx = dir & MSP_DIR_TX;
587 	disable_rx = dir & MSP_DIR_RX;
588 	if (disable_tx && disable_rx) {
589 		reg_val_GCR = readl(msp->registers + MSP_GCR);
590 		writel(reg_val_GCR | LOOPBACK_MASK,
591 				msp->registers + MSP_GCR);
592 
593 		/* Flush TX-FIFO */
594 		flush_fifo_tx(msp);
595 
596 		/* Disable TX-channel */
597 		writel((readl(msp->registers + MSP_GCR) &
598 			       (~TX_ENABLE)), msp->registers + MSP_GCR);
599 
600 		/* Flush RX-FIFO */
601 		flush_fifo_rx(msp);
602 
603 		/* Disable Loopback and Receive channel */
604 		writel((readl(msp->registers + MSP_GCR) &
605 				(~(RX_ENABLE | LOOPBACK_MASK))),
606 				msp->registers + MSP_GCR);
607 
608 		disable_msp_tx(msp);
609 		disable_msp_rx(msp);
610 	} else if (disable_tx)
611 		disable_msp_tx(msp);
612 	else if (disable_rx)
613 		disable_msp_rx(msp);
614 
615 	return 0;
616 }
617 
618 int ux500_msp_i2s_trigger(struct ux500_msp *msp, int cmd, int direction)
619 {
620 	u32 reg_val_DMACR, reg_val_GCR, dma_enable_bit, enable_bit;
621 	unsigned int dir;
622 
623 	if (direction == SNDRV_PCM_STREAM_PLAYBACK)
624 		dir = MSP_DIR_TX;
625 	else if (direction == SNDRV_PCM_STREAM_CAPTURE)
626 		dir = MSP_DIR_RX;
627 	else
628 		return -EINVAL;
629 
630 	if (msp->msp_state == MSP_STATE_IDLE) {
631 		dev_err(msp->dev, "%s: ERROR: MSP is not configured!\n",
632 			__func__);
633 		return -EINVAL;
634 	}
635 
636 	switch (cmd) {
637 	case SNDRV_PCM_TRIGGER_START:
638 	case SNDRV_PCM_TRIGGER_RESUME:
639 	case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
640 		if (direction == SNDRV_PCM_STREAM_PLAYBACK) {
641 			enable_bit = TX_ENABLE;
642 			dma_enable_bit = TX_DMA_ENABLE;
643 		} else {
644 			enable_bit = RX_ENABLE;
645 			dma_enable_bit = RX_DMA_ENABLE;
646 		}
647 		if (!(msp->dir_busy & dir))
648 			return -EINVAL;
649 		reg_val_DMACR = readl(msp->registers + MSP_DMACR);
650 		writel(reg_val_DMACR | dma_enable_bit,
651 		       msp->registers + MSP_DMACR);
652 		reg_val_GCR = readl(msp->registers + MSP_GCR);
653 		if (msp->clock_provider)
654 			enable_bit |= FRAME_GEN_ENABLE;
655 		writel(reg_val_GCR | enable_bit, msp->registers + MSP_GCR);
656 		msp->dir_running |= dir;
657 		msp->msp_state = MSP_STATE_RUNNING;
658 		break;
659 
660 	case SNDRV_PCM_TRIGGER_STOP:
661 	case SNDRV_PCM_TRIGGER_SUSPEND:
662 	case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
663 		if (!(msp->dir_busy & dir))
664 			return -EINVAL;
665 		if (direction == SNDRV_PCM_STREAM_PLAYBACK) {
666 			disable_msp_tx(msp);
667 			msp->dir_running &= ~MSP_DIR_TX;
668 		} else {
669 			disable_msp_rx(msp);
670 			msp->dir_running &= ~MSP_DIR_RX;
671 		}
672 		if (!msp->dir_running) {
673 			reg_val_GCR = readl(msp->registers + MSP_GCR);
674 			writel(reg_val_GCR & ~FRAME_GEN_ENABLE,
675 			       msp->registers + MSP_GCR);
676 			msp->msp_state = MSP_STATE_CONFIGURED;
677 		}
678 		break;
679 	default:
680 		return -EINVAL;
681 	}
682 
683 	return 0;
684 }
685 
686 int ux500_msp_i2s_close(struct ux500_msp *msp, unsigned int dir)
687 {
688 	int status = 0;
689 
690 	dev_dbg(msp->dev, "%s: Enter (dir = 0x%01x).\n", __func__, dir);
691 
692 	if (!dir || dir & ~(MSP_DIR_TX | MSP_DIR_RX) ||
693 	    (msp->dir_busy & dir) != dir)
694 		return -EINVAL;
695 
696 	status = disable_msp(msp, dir);
697 	msp->dir_busy &= ~dir;
698 	msp->dir_running &= ~dir;
699 	if (msp->dir_busy && !msp->dir_running) {
700 		writel(readl(msp->registers + MSP_GCR) & ~FRAME_GEN_ENABLE,
701 		       msp->registers + MSP_GCR);
702 		msp->msp_state = MSP_STATE_CONFIGURED;
703 	}
704 	if (msp->dir_busy == 0) {
705 		/* disable sample rate and frame generators */
706 		msp->msp_state = MSP_STATE_IDLE;
707 		writel((readl(msp->registers + MSP_GCR) &
708 			       (~(FRAME_GEN_ENABLE | SRG_ENABLE))),
709 			      msp->registers + MSP_GCR);
710 
711 		writel(0, msp->registers + MSP_GCR);
712 		writel(0, msp->registers + MSP_TCF);
713 		writel(0, msp->registers + MSP_RCF);
714 		writel(0, msp->registers + MSP_DMACR);
715 		writel(0, msp->registers + MSP_SRG);
716 		writel(0, msp->registers + MSP_MCR);
717 		writel(0, msp->registers + MSP_RCM);
718 		writel(0, msp->registers + MSP_RCV);
719 		writel(0, msp->registers + MSP_TCE0);
720 		writel(0, msp->registers + MSP_TCE1);
721 		writel(0, msp->registers + MSP_TCE2);
722 		writel(0, msp->registers + MSP_TCE3);
723 		writel(0, msp->registers + MSP_RCE0);
724 		writel(0, msp->registers + MSP_RCE1);
725 		writel(0, msp->registers + MSP_RCE2);
726 		writel(0, msp->registers + MSP_RCE3);
727 		memset(&msp->config, 0, sizeof(msp->config));
728 		msp->clock_provider = false;
729 	}
730 
731 	return status;
732 
733 }
734 
735 int ux500_msp_i2s_init_msp(struct platform_device *pdev,
736 			struct ux500_msp **msp_p)
737 {
738 	struct resource *res;
739 	struct ux500_msp *msp;
740 
741 	*msp_p = devm_kzalloc(&pdev->dev, sizeof(struct ux500_msp), GFP_KERNEL);
742 	msp = *msp_p;
743 	if (!msp)
744 		return -ENOMEM;
745 
746 	msp->dev = &pdev->dev;
747 
748 	msp->registers = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
749 	if (IS_ERR(msp->registers))
750 		return PTR_ERR(msp->registers);
751 	msp->tx_rx_addr = res->start + MSP_DR;
752 
753 	msp->msp_state = MSP_STATE_IDLE;
754 	msp->loopback_enable = 0;
755 
756 	return 0;
757 }
758 
759 void ux500_msp_i2s_cleanup_msp(struct platform_device *pdev,
760 			struct ux500_msp *msp)
761 {
762 	dev_dbg(msp->dev, "%s: Enter (id = %d).\n", __func__, msp->id);
763 }
764 
765 MODULE_LICENSE("GPL v2");
766