xref: /linux/sound/soc/fsl/fsl_qmc_audio.c (revision 48a710760e10a4f36e11233a21860796ba204b1e)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * ALSA SoC using the QUICC Multichannel Controller (QMC)
4  *
5  * Copyright 2022 CS GROUP France
6  *
7  * Author: Herve Codina <herve.codina@bootlin.com>
8  */
9 
10 #include <linux/dma-mapping.h>
11 #include <linux/module.h>
12 #include <linux/of.h>
13 #include <linux/of_platform.h>
14 #include <linux/platform_device.h>
15 #include <linux/slab.h>
16 #include <soc/fsl/qe/qmc.h>
17 #include <sound/pcm_params.h>
18 #include <sound/soc.h>
19 
20 struct qmc_dai {
21 	char *name;
22 	int id;
23 	struct device *dev;
24 	unsigned int nb_tx_ts;
25 	unsigned int nb_rx_ts;
26 
27 	unsigned int nb_chans_avail;
28 	unsigned int nb_chans_used_tx;
29 	unsigned int nb_chans_used_rx;
30 	struct qmc_chan **qmc_chans;
31 };
32 
33 struct qmc_audio {
34 	struct device *dev;
35 	unsigned int num_dais;
36 	struct qmc_dai *dais;
37 	struct snd_soc_dai_driver *dai_drivers;
38 };
39 
40 struct qmc_dai_prtd {
41 	struct qmc_dai *qmc_dai;
42 
43 	snd_pcm_uframes_t buffer_ended;
44 	snd_pcm_uframes_t buffer_size;
45 	snd_pcm_uframes_t period_size;
46 
47 	dma_addr_t ch_dma_addr_start;
48 	dma_addr_t ch_dma_addr_current;
49 	dma_addr_t ch_dma_addr_end;
50 	size_t ch_dma_size;
51 	size_t ch_dma_offset;
52 
53 	unsigned int channels;
54 	struct snd_pcm_substream *substream;
55 };
56 
57 static int qmc_audio_pcm_construct(struct snd_soc_component *component,
58 				   struct snd_soc_pcm_runtime *rtd)
59 {
60 	struct snd_card *card = rtd->card->snd_card;
61 	int ret;
62 
63 	ret = dma_coerce_mask_and_coherent(card->dev, DMA_BIT_MASK(32));
64 	if (ret)
65 		return ret;
66 
67 	snd_pcm_set_managed_buffer_all(rtd->pcm, SNDRV_DMA_TYPE_DEV, card->dev,
68 				       64 * 1024, 64 * 1024);
69 	return 0;
70 }
71 
72 static bool qmc_audio_access_is_interleaved(snd_pcm_access_t access)
73 {
74 	switch (access) {
75 	case SNDRV_PCM_ACCESS_MMAP_INTERLEAVED:
76 	case SNDRV_PCM_ACCESS_RW_INTERLEAVED:
77 		return true;
78 	default:
79 		break;
80 	}
81 	return false;
82 }
83 
84 static int qmc_audio_pcm_hw_params(struct snd_soc_component *component,
85 				   struct snd_pcm_substream *substream,
86 				   struct snd_pcm_hw_params *params)
87 {
88 	struct snd_pcm_runtime *runtime = substream->runtime;
89 	struct qmc_dai_prtd *prtd = substream->runtime->private_data;
90 
91 	/*
92 	 * In interleaved mode, the driver uses one QMC channel for all audio
93 	 * channels whereas in non-interleaved mode, it uses one QMC channel per
94 	 * audio channel.
95 	 */
96 	prtd->channels = qmc_audio_access_is_interleaved(params_access(params)) ?
97 				1 : params_channels(params);
98 
99 	prtd->substream = substream;
100 
101 	prtd->buffer_ended = 0;
102 	prtd->buffer_size = params_buffer_size(params);
103 	prtd->period_size = params_period_size(params);
104 
105 	prtd->ch_dma_addr_start = runtime->dma_addr;
106 	prtd->ch_dma_offset = params_buffer_bytes(params) / prtd->channels;
107 	prtd->ch_dma_addr_end = runtime->dma_addr + prtd->ch_dma_offset;
108 	prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
109 	prtd->ch_dma_size = params_period_bytes(params) / prtd->channels;
110 
111 	return 0;
112 }
113 
114 static void qmc_audio_pcm_write_complete(void *context);
115 
116 static int qmc_audio_pcm_write_submit(struct qmc_dai_prtd *prtd)
117 {
118 	unsigned int i;
119 	int ret;
120 
121 	for (i = 0; i < prtd->channels; i++) {
122 		ret = qmc_chan_write_submit(prtd->qmc_dai->qmc_chans[i],
123 					    prtd->ch_dma_addr_current + i * prtd->ch_dma_offset,
124 					    prtd->ch_dma_size,
125 					    i == prtd->channels - 1 ? qmc_audio_pcm_write_complete :
126 								      NULL, prtd);
127 		if (ret) {
128 			dev_err(prtd->qmc_dai->dev, "write_submit %u failed %d\n",
129 				i, ret);
130 			return ret;
131 		}
132 	}
133 
134 	return 0;
135 }
136 
137 static void qmc_audio_pcm_write_complete(void *context)
138 {
139 	struct qmc_dai_prtd *prtd = context;
140 
141 	prtd->buffer_ended += prtd->period_size;
142 	if (prtd->buffer_ended >= prtd->buffer_size)
143 		prtd->buffer_ended = 0;
144 
145 	prtd->ch_dma_addr_current += prtd->ch_dma_size;
146 	if (prtd->ch_dma_addr_current >= prtd->ch_dma_addr_end)
147 		prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
148 
149 	qmc_audio_pcm_write_submit(prtd);
150 
151 	snd_pcm_period_elapsed(prtd->substream);
152 }
153 
154 static void qmc_audio_pcm_read_complete(void *context, size_t length, unsigned int flags);
155 
156 static int qmc_audio_pcm_read_submit(struct qmc_dai_prtd *prtd)
157 {
158 	unsigned int i;
159 	int ret;
160 
161 	for (i = 0; i < prtd->channels; i++) {
162 		ret = qmc_chan_read_submit(prtd->qmc_dai->qmc_chans[i],
163 					   prtd->ch_dma_addr_current + i * prtd->ch_dma_offset,
164 					   prtd->ch_dma_size,
165 					   i == prtd->channels - 1 ? qmc_audio_pcm_read_complete :
166 								     NULL, prtd);
167 		if (ret) {
168 			dev_err(prtd->qmc_dai->dev, "read_submit %u failed %d\n",
169 				i, ret);
170 			return ret;
171 		}
172 	}
173 
174 	return 0;
175 }
176 
177 static void qmc_audio_pcm_read_complete(void *context, size_t length, unsigned int flags)
178 {
179 	struct qmc_dai_prtd *prtd = context;
180 
181 	if (length != prtd->ch_dma_size) {
182 		dev_err(prtd->qmc_dai->dev, "read complete length = %zu, exp %zu\n",
183 			length, prtd->ch_dma_size);
184 	}
185 
186 	prtd->buffer_ended += prtd->period_size;
187 	if (prtd->buffer_ended >= prtd->buffer_size)
188 		prtd->buffer_ended = 0;
189 
190 	prtd->ch_dma_addr_current += prtd->ch_dma_size;
191 	if (prtd->ch_dma_addr_current >= prtd->ch_dma_addr_end)
192 		prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
193 
194 	qmc_audio_pcm_read_submit(prtd);
195 
196 	snd_pcm_period_elapsed(prtd->substream);
197 }
198 
199 static int qmc_audio_pcm_trigger(struct snd_soc_component *component,
200 				 struct snd_pcm_substream *substream, int cmd)
201 {
202 	struct qmc_dai_prtd *prtd = substream->runtime->private_data;
203 	int ret;
204 
205 	if (!prtd->qmc_dai) {
206 		dev_err(component->dev, "qmc_dai is not set\n");
207 		return -EINVAL;
208 	}
209 
210 	switch (cmd) {
211 	case SNDRV_PCM_TRIGGER_START:
212 		prtd->buffer_ended = 0;
213 		prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
214 
215 		if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
216 			/* Submit first chunk ... */
217 			ret = qmc_audio_pcm_write_submit(prtd);
218 			if (ret)
219 				return ret;
220 
221 			/* ... prepare next one ... */
222 			prtd->ch_dma_addr_current += prtd->ch_dma_size;
223 			if (prtd->ch_dma_addr_current >= prtd->ch_dma_addr_end)
224 				prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
225 
226 			/* ... and send it */
227 			ret = qmc_audio_pcm_write_submit(prtd);
228 			if (ret)
229 				return ret;
230 		} else {
231 			/* Submit first chunk ... */
232 			ret = qmc_audio_pcm_read_submit(prtd);
233 			if (ret)
234 				return ret;
235 
236 			/* ... prepare next one ... */
237 			prtd->ch_dma_addr_current += prtd->ch_dma_size;
238 			if (prtd->ch_dma_addr_current >= prtd->ch_dma_addr_end)
239 				prtd->ch_dma_addr_current = prtd->ch_dma_addr_start;
240 
241 			/* ... and send it */
242 			ret = qmc_audio_pcm_read_submit(prtd);
243 			if (ret)
244 				return ret;
245 		}
246 		break;
247 
248 	case SNDRV_PCM_TRIGGER_RESUME:
249 	case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
250 		break;
251 
252 	case SNDRV_PCM_TRIGGER_STOP:
253 	case SNDRV_PCM_TRIGGER_SUSPEND:
254 	case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
255 		break;
256 
257 	default:
258 		return -EINVAL;
259 	}
260 
261 	return 0;
262 }
263 
264 static snd_pcm_uframes_t qmc_audio_pcm_pointer(struct snd_soc_component *component,
265 					       struct snd_pcm_substream *substream)
266 {
267 	struct qmc_dai_prtd *prtd = substream->runtime->private_data;
268 
269 	return prtd->buffer_ended;
270 }
271 
272 static int qmc_audio_of_xlate_dai_name(struct snd_soc_component *component,
273 				       const struct of_phandle_args *args,
274 				       const char **dai_name)
275 {
276 	struct qmc_audio *qmc_audio = dev_get_drvdata(component->dev);
277 	struct snd_soc_dai_driver *dai_driver;
278 	int id = args->args[0];
279 	int i;
280 
281 	for (i = 0; i  < qmc_audio->num_dais; i++) {
282 		dai_driver = qmc_audio->dai_drivers + i;
283 		if (dai_driver->id == id) {
284 			*dai_name = dai_driver->name;
285 			return 0;
286 		}
287 	}
288 
289 	return -EINVAL;
290 }
291 
292 static const struct snd_pcm_hardware qmc_audio_pcm_hardware = {
293 	.info			= SNDRV_PCM_INFO_MMAP |
294 				  SNDRV_PCM_INFO_MMAP_VALID |
295 				  SNDRV_PCM_INFO_INTERLEAVED |
296 				  SNDRV_PCM_INFO_NONINTERLEAVED |
297 				  SNDRV_PCM_INFO_PAUSE,
298 	.period_bytes_min	= 32,
299 	.period_bytes_max	= 64 * 1024,
300 	.periods_min		= 2,
301 	.periods_max		= 2 * 1024,
302 	.buffer_bytes_max	= 64 * 1024,
303 };
304 
305 static int qmc_audio_pcm_open(struct snd_soc_component *component,
306 			      struct snd_pcm_substream *substream)
307 {
308 	struct snd_pcm_runtime *runtime = substream->runtime;
309 	struct qmc_dai_prtd *prtd;
310 	int ret;
311 
312 	snd_soc_set_runtime_hwparams(substream, &qmc_audio_pcm_hardware);
313 
314 	/* ensure that buffer size is a multiple of period size */
315 	ret = snd_pcm_hw_constraint_integer(runtime, SNDRV_PCM_HW_PARAM_PERIODS);
316 	if (ret < 0)
317 		return ret;
318 
319 	prtd = kzalloc(sizeof(*prtd), GFP_KERNEL);
320 	if (!prtd)
321 		return -ENOMEM;
322 
323 	runtime->private_data = prtd;
324 
325 	return 0;
326 }
327 
328 static int qmc_audio_pcm_close(struct snd_soc_component *component,
329 			       struct snd_pcm_substream *substream)
330 {
331 	struct qmc_dai_prtd *prtd = substream->runtime->private_data;
332 
333 	kfree(prtd);
334 	return 0;
335 }
336 
337 static const struct snd_soc_component_driver qmc_audio_soc_platform = {
338 	.open			= qmc_audio_pcm_open,
339 	.close			= qmc_audio_pcm_close,
340 	.hw_params		= qmc_audio_pcm_hw_params,
341 	.trigger		= qmc_audio_pcm_trigger,
342 	.pointer		= qmc_audio_pcm_pointer,
343 	.pcm_construct		= qmc_audio_pcm_construct,
344 	.of_xlate_dai_name	= qmc_audio_of_xlate_dai_name,
345 };
346 
347 static unsigned int qmc_dai_get_index(struct snd_soc_dai *dai)
348 {
349 	struct qmc_audio *qmc_audio = snd_soc_dai_get_drvdata(dai);
350 
351 	return dai->driver - qmc_audio->dai_drivers;
352 }
353 
354 static struct qmc_dai *qmc_dai_get_data(struct snd_soc_dai *dai)
355 {
356 	struct qmc_audio *qmc_audio = snd_soc_dai_get_drvdata(dai);
357 	unsigned int index;
358 
359 	index = qmc_dai_get_index(dai);
360 	if (index > qmc_audio->num_dais)
361 		return NULL;
362 
363 	return qmc_audio->dais + index;
364 }
365 
366 /*
367  * The constraints for format/channel is to match with the number of 8bit
368  * time-slots available.
369  */
370 static int qmc_dai_hw_rule_channels_by_format(struct qmc_dai *qmc_dai,
371 					      struct snd_pcm_hw_params *params,
372 					      unsigned int nb_ts)
373 {
374 	struct snd_interval *c = hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
375 	snd_pcm_format_t format = params_format(params);
376 	struct snd_interval ch = {0};
377 
378 	switch (snd_pcm_format_physical_width(format)) {
379 	case 8:
380 		ch.max = nb_ts;
381 		break;
382 	case 16:
383 		ch.max = nb_ts / 2;
384 		break;
385 	case 32:
386 		ch.max = nb_ts / 4;
387 		break;
388 	case 64:
389 		ch.max = nb_ts / 8;
390 		break;
391 	default:
392 		dev_err(qmc_dai->dev, "format physical width %u not supported\n",
393 			snd_pcm_format_physical_width(format));
394 		return -EINVAL;
395 	}
396 
397 	ch.min = ch.max ? 1 : 0;
398 
399 	return snd_interval_refine(c, &ch);
400 }
401 
402 static int qmc_dai_hw_rule_playback_channels_by_format(struct snd_pcm_hw_params *params,
403 						       struct snd_pcm_hw_rule *rule)
404 {
405 	struct qmc_dai *qmc_dai = rule->private;
406 
407 	return qmc_dai_hw_rule_channels_by_format(qmc_dai, params, qmc_dai->nb_tx_ts);
408 }
409 
410 static int qmc_dai_hw_rule_capture_channels_by_format(struct snd_pcm_hw_params *params,
411 						      struct snd_pcm_hw_rule *rule)
412 {
413 	struct qmc_dai *qmc_dai = rule->private;
414 
415 	return qmc_dai_hw_rule_channels_by_format(qmc_dai, params, qmc_dai->nb_rx_ts);
416 }
417 
418 static int qmc_dai_hw_rule_format_by_channels(struct qmc_dai *qmc_dai,
419 					      struct snd_pcm_hw_params *params,
420 					      unsigned int nb_ts)
421 {
422 	struct snd_mask *f_old = hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT);
423 	unsigned int channels = params_channels(params);
424 	unsigned int slot_width;
425 	snd_pcm_format_t format;
426 	struct snd_mask f_new;
427 
428 	if (!channels || channels > nb_ts) {
429 		dev_err(qmc_dai->dev, "channels %u not supported\n",
430 			nb_ts);
431 		return -EINVAL;
432 	}
433 
434 	slot_width = (nb_ts / channels) * 8;
435 
436 	snd_mask_none(&f_new);
437 	pcm_for_each_format(format) {
438 		if (snd_mask_test_format(f_old, format)) {
439 			if (snd_pcm_format_physical_width(format) <= slot_width)
440 				snd_mask_set_format(&f_new, format);
441 		}
442 	}
443 
444 	return snd_mask_refine(f_old, &f_new);
445 }
446 
447 static int qmc_dai_hw_rule_playback_format_by_channels(struct snd_pcm_hw_params *params,
448 						       struct snd_pcm_hw_rule *rule)
449 {
450 	struct qmc_dai *qmc_dai = rule->private;
451 
452 	return qmc_dai_hw_rule_format_by_channels(qmc_dai, params, qmc_dai->nb_tx_ts);
453 }
454 
455 static int qmc_dai_hw_rule_capture_format_by_channels(struct snd_pcm_hw_params *params,
456 						      struct snd_pcm_hw_rule *rule)
457 {
458 	struct qmc_dai *qmc_dai = rule->private;
459 
460 	return qmc_dai_hw_rule_format_by_channels(qmc_dai, params, qmc_dai->nb_rx_ts);
461 }
462 
463 static int qmc_dai_constraints_interleaved(struct snd_pcm_substream *substream,
464 					   struct qmc_dai *qmc_dai)
465 {
466 	snd_pcm_hw_rule_func_t hw_rule_channels_by_format;
467 	snd_pcm_hw_rule_func_t hw_rule_format_by_channels;
468 	unsigned int frame_bits;
469 	u64 access;
470 	int ret;
471 
472 	if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
473 		hw_rule_channels_by_format = qmc_dai_hw_rule_capture_channels_by_format;
474 		hw_rule_format_by_channels = qmc_dai_hw_rule_capture_format_by_channels;
475 		frame_bits = qmc_dai->nb_rx_ts * 8;
476 	} else {
477 		hw_rule_channels_by_format = qmc_dai_hw_rule_playback_channels_by_format;
478 		hw_rule_format_by_channels = qmc_dai_hw_rule_playback_format_by_channels;
479 		frame_bits = qmc_dai->nb_tx_ts * 8;
480 	}
481 
482 	ret = snd_pcm_hw_rule_add(substream->runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
483 				  hw_rule_channels_by_format, qmc_dai,
484 				  SNDRV_PCM_HW_PARAM_FORMAT, -1);
485 	if (ret) {
486 		dev_err(qmc_dai->dev, "Failed to add channels rule (%d)\n", ret);
487 		return ret;
488 	}
489 
490 	ret = snd_pcm_hw_rule_add(substream->runtime, 0,  SNDRV_PCM_HW_PARAM_FORMAT,
491 				  hw_rule_format_by_channels, qmc_dai,
492 				  SNDRV_PCM_HW_PARAM_CHANNELS, -1);
493 	if (ret) {
494 		dev_err(qmc_dai->dev, "Failed to add format rule (%d)\n", ret);
495 		return ret;
496 	}
497 
498 	ret = snd_pcm_hw_constraint_single(substream->runtime,
499 					   SNDRV_PCM_HW_PARAM_FRAME_BITS,
500 					   frame_bits);
501 	if (ret < 0) {
502 		dev_err(qmc_dai->dev, "Failed to add frame_bits constraint (%d)\n", ret);
503 		return ret;
504 	}
505 
506 	access = 1ULL << (__force int)SNDRV_PCM_ACCESS_MMAP_INTERLEAVED |
507 		 1ULL << (__force int)SNDRV_PCM_ACCESS_RW_INTERLEAVED;
508 	ret = snd_pcm_hw_constraint_mask64(substream->runtime, SNDRV_PCM_HW_PARAM_ACCESS,
509 					   access);
510 	if (ret) {
511 		dev_err(qmc_dai->dev, "Failed to add hw_param_access constraint (%d)\n", ret);
512 		return ret;
513 	}
514 
515 	return 0;
516 }
517 
518 static int qmc_dai_constraints_noninterleaved(struct snd_pcm_substream *substream,
519 					      struct qmc_dai *qmc_dai)
520 {
521 	unsigned int frame_bits;
522 	u64 access;
523 	int ret;
524 
525 	frame_bits = (substream->stream == SNDRV_PCM_STREAM_CAPTURE) ?
526 			qmc_dai->nb_rx_ts * 8 : qmc_dai->nb_tx_ts * 8;
527 	ret = snd_pcm_hw_constraint_single(substream->runtime,
528 					   SNDRV_PCM_HW_PARAM_FRAME_BITS,
529 					   frame_bits);
530 	if (ret < 0) {
531 		dev_err(qmc_dai->dev, "Failed to add frame_bits constraint (%d)\n", ret);
532 		return ret;
533 	}
534 
535 	access = 1ULL << (__force int)SNDRV_PCM_ACCESS_MMAP_NONINTERLEAVED |
536 		 1ULL << (__force int)SNDRV_PCM_ACCESS_RW_NONINTERLEAVED;
537 	ret = snd_pcm_hw_constraint_mask64(substream->runtime, SNDRV_PCM_HW_PARAM_ACCESS,
538 					   access);
539 	if (ret) {
540 		dev_err(qmc_dai->dev, "Failed to add hw_param_access constraint (%d)\n", ret);
541 		return ret;
542 	}
543 
544 	return 0;
545 }
546 
547 static int qmc_dai_startup(struct snd_pcm_substream *substream,
548 			   struct snd_soc_dai *dai)
549 {
550 	struct qmc_dai_prtd *prtd = substream->runtime->private_data;
551 	struct qmc_dai *qmc_dai;
552 
553 	qmc_dai = qmc_dai_get_data(dai);
554 	if (!qmc_dai) {
555 		dev_err(dai->dev, "Invalid dai\n");
556 		return -EINVAL;
557 	}
558 
559 	prtd->qmc_dai = qmc_dai;
560 
561 	return qmc_dai->nb_chans_avail > 1 ?
562 		qmc_dai_constraints_noninterleaved(substream, qmc_dai) :
563 		qmc_dai_constraints_interleaved(substream, qmc_dai);
564 }
565 
566 static int qmc_dai_hw_params(struct snd_pcm_substream *substream,
567 			     struct snd_pcm_hw_params *params,
568 			     struct snd_soc_dai *dai)
569 {
570 	struct qmc_chan_param chan_param = {0};
571 	unsigned int nb_chans_used;
572 	struct qmc_dai *qmc_dai;
573 	unsigned int i;
574 	int ret;
575 
576 	qmc_dai = qmc_dai_get_data(dai);
577 	if (!qmc_dai) {
578 		dev_err(dai->dev, "Invalid dai\n");
579 		return -EINVAL;
580 	}
581 
582 	/*
583 	 * In interleaved mode, the driver uses one QMC channel for all audio
584 	 * channels whereas in non-interleaved mode, it uses one QMC channel per
585 	 * audio channel.
586 	 */
587 	nb_chans_used = qmc_audio_access_is_interleaved(params_access(params)) ?
588 				1 : params_channels(params);
589 
590 	if (nb_chans_used > qmc_dai->nb_chans_avail) {
591 		dev_err(dai->dev, "Not enough qmc_chans. Need %u, avail %u\n",
592 			nb_chans_used, qmc_dai->nb_chans_avail);
593 		return -EINVAL;
594 	}
595 
596 	if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
597 		chan_param.mode = QMC_TRANSPARENT;
598 		chan_param.transp.max_rx_buf_size = params_period_bytes(params) / nb_chans_used;
599 		for (i = 0; i < nb_chans_used; i++) {
600 			ret = qmc_chan_set_param(qmc_dai->qmc_chans[i], &chan_param);
601 			if (ret) {
602 				dev_err(dai->dev, "qmc_chans[%u], set param failed %d\n",
603 					i, ret);
604 				return ret;
605 			}
606 		}
607 		qmc_dai->nb_chans_used_rx = nb_chans_used;
608 	} else {
609 		qmc_dai->nb_chans_used_tx = nb_chans_used;
610 	}
611 
612 	return 0;
613 }
614 
615 static int qmc_dai_trigger(struct snd_pcm_substream *substream, int cmd,
616 			   struct snd_soc_dai *dai)
617 {
618 	unsigned int nb_chans_used;
619 	struct qmc_dai *qmc_dai;
620 	unsigned int i;
621 	int direction;
622 	int ret = 0;
623 	int ret_tmp;
624 
625 	qmc_dai = qmc_dai_get_data(dai);
626 	if (!qmc_dai) {
627 		dev_err(dai->dev, "Invalid dai\n");
628 		return -EINVAL;
629 	}
630 
631 	if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
632 		direction = QMC_CHAN_WRITE;
633 		nb_chans_used = qmc_dai->nb_chans_used_tx;
634 	} else {
635 		direction = QMC_CHAN_READ;
636 		nb_chans_used = qmc_dai->nb_chans_used_rx;
637 	}
638 
639 	switch (cmd) {
640 	case SNDRV_PCM_TRIGGER_START:
641 	case SNDRV_PCM_TRIGGER_RESUME:
642 	case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
643 		for (i = 0; i < nb_chans_used; i++) {
644 			ret = qmc_chan_start(qmc_dai->qmc_chans[i], direction);
645 			if (ret)
646 				goto err_stop;
647 		}
648 		break;
649 
650 	case SNDRV_PCM_TRIGGER_STOP:
651 		/* Stop and reset all QMC channels and return the first error encountered */
652 		for (i = 0; i < nb_chans_used; i++) {
653 			ret_tmp = qmc_chan_stop(qmc_dai->qmc_chans[i], direction);
654 			if (!ret)
655 				ret = ret_tmp;
656 			if (ret_tmp)
657 				continue;
658 
659 			ret_tmp = qmc_chan_reset(qmc_dai->qmc_chans[i], direction);
660 			if (!ret)
661 				ret = ret_tmp;
662 		}
663 		if (ret)
664 			return ret;
665 		break;
666 
667 	case SNDRV_PCM_TRIGGER_SUSPEND:
668 	case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
669 		/* Stop all QMC channels and return the first error encountered */
670 		for (i = 0; i < nb_chans_used; i++) {
671 			ret_tmp = qmc_chan_stop(qmc_dai->qmc_chans[i], direction);
672 			if (!ret)
673 				ret = ret_tmp;
674 		}
675 		if (ret)
676 			return ret;
677 		break;
678 
679 	default:
680 		return -EINVAL;
681 	}
682 
683 	return 0;
684 
685 err_stop:
686 	while (i--) {
687 		qmc_chan_stop(qmc_dai->qmc_chans[i], direction);
688 		qmc_chan_reset(qmc_dai->qmc_chans[i], direction);
689 	}
690 	return ret;
691 }
692 
693 static const struct snd_soc_dai_ops qmc_dai_ops = {
694 	.startup	= qmc_dai_startup,
695 	.trigger	= qmc_dai_trigger,
696 	.hw_params	= qmc_dai_hw_params,
697 };
698 
699 static u64 qmc_audio_formats(u8 nb_ts, bool is_noninterleaved)
700 {
701 	unsigned int format_width;
702 	unsigned int chan_width;
703 	snd_pcm_format_t format;
704 	u64 formats_mask;
705 
706 	if (!nb_ts)
707 		return 0;
708 
709 	formats_mask = 0;
710 	chan_width = nb_ts * 8;
711 	pcm_for_each_format(format) {
712 		/*
713 		 * Support format other than little-endian (ie big-endian or
714 		 * without endianness such as 8bit formats)
715 		 */
716 		if (snd_pcm_format_little_endian(format) == 1)
717 			continue;
718 
719 		/* Support physical width multiple of 8bit */
720 		format_width = snd_pcm_format_physical_width(format);
721 		if (format_width == 0 || format_width % 8)
722 			continue;
723 
724 		/*
725 		 * And support physical width that can fit N times in the
726 		 * channel
727 		 */
728 		if (format_width > chan_width || chan_width % format_width)
729 			continue;
730 
731 		/*
732 		 * In non interleaved mode, we can only support formats that
733 		 * can fit only 1 time in the channel
734 		 */
735 		if (is_noninterleaved && format_width != chan_width)
736 			continue;
737 
738 		formats_mask |= pcm_format_to_bits(format);
739 	}
740 	return formats_mask;
741 }
742 
743 static int qmc_audio_dai_parse(struct qmc_audio *qmc_audio, struct device_node *np,
744 			       struct qmc_dai *qmc_dai,
745 			       struct snd_soc_dai_driver *qmc_soc_dai_driver)
746 {
747 	struct qmc_chan_ts_info ts_info;
748 	struct qmc_chan_info info;
749 	unsigned long rx_fs_rate;
750 	unsigned long tx_fs_rate;
751 	int prev_last_rx_ts = 0;
752 	int prev_last_tx_ts = 0;
753 	unsigned int nb_tx_ts;
754 	unsigned int nb_rx_ts;
755 	unsigned int i;
756 	int last_rx_ts;
757 	int last_tx_ts;
758 	int count;
759 	u32 val;
760 	int ret;
761 
762 	qmc_dai->dev = qmc_audio->dev;
763 
764 	ret = of_property_read_u32(np, "reg", &val);
765 	if (ret) {
766 		dev_err(qmc_audio->dev, "%pOF: failed to read reg\n", np);
767 		return ret;
768 	}
769 	qmc_dai->id = val;
770 
771 	qmc_dai->name = devm_kasprintf(qmc_audio->dev, GFP_KERNEL, "%s.%d",
772 				       np->parent->name, qmc_dai->id);
773 	if (!qmc_dai->name)
774 		return -ENOMEM;
775 
776 	count = qmc_chan_count_phandles(np, "fsl,qmc-chan");
777 	if (count < 0)
778 		return dev_err_probe(qmc_audio->dev, count,
779 				     "dai %d get number of QMC channel failed\n", qmc_dai->id);
780 	if (!count)
781 		return dev_err_probe(qmc_audio->dev, -EINVAL,
782 				     "dai %d no QMC channel defined\n", qmc_dai->id);
783 
784 	qmc_dai->qmc_chans = devm_kcalloc(qmc_audio->dev, count, sizeof(*qmc_dai->qmc_chans),
785 					  GFP_KERNEL);
786 	if (!qmc_dai->qmc_chans)
787 		return -ENOMEM;
788 
789 	for (i = 0; i < count; i++) {
790 		qmc_dai->qmc_chans[i] = devm_qmc_chan_get_byphandles_index(qmc_audio->dev, np,
791 									   "fsl,qmc-chan", i);
792 		if (IS_ERR(qmc_dai->qmc_chans[i])) {
793 			return dev_err_probe(qmc_audio->dev, PTR_ERR(qmc_dai->qmc_chans[i]),
794 					     "dai %d get QMC channel %d failed\n", qmc_dai->id, i);
795 		}
796 
797 		ret = qmc_chan_get_info(qmc_dai->qmc_chans[i], &info);
798 		if (ret) {
799 			dev_err(qmc_audio->dev, "dai %d get QMC %d channel info failed %d\n",
800 				qmc_dai->id, i, ret);
801 			return ret;
802 		}
803 
804 		if (info.mode != QMC_TRANSPARENT) {
805 			dev_err(qmc_audio->dev, "dai %d QMC chan %d mode %d is not QMC_TRANSPARENT\n",
806 				qmc_dai->id, i, info.mode);
807 			return -EINVAL;
808 		}
809 
810 		/*
811 		 * All channels must have the same number of Tx slots and the
812 		 * same numbers of Rx slots.
813 		 */
814 		if (i == 0) {
815 			nb_tx_ts = info.nb_tx_ts;
816 			nb_rx_ts = info.nb_rx_ts;
817 			tx_fs_rate = info.tx_fs_rate;
818 			rx_fs_rate = info.rx_fs_rate;
819 		} else {
820 			if (nb_tx_ts != info.nb_tx_ts) {
821 				dev_err(qmc_audio->dev, "dai %d QMC chan %d inconsistent number of Tx timeslots (%u instead of %u)\n",
822 					qmc_dai->id, i, info.nb_tx_ts, nb_tx_ts);
823 				return -EINVAL;
824 			}
825 			if (nb_rx_ts != info.nb_rx_ts) {
826 				dev_err(qmc_audio->dev, "dai %d QMC chan %d inconsistent number of Rx timeslots (%u instead of %u)\n",
827 					qmc_dai->id, i, info.nb_rx_ts, nb_rx_ts);
828 				return -EINVAL;
829 			}
830 			if (tx_fs_rate != info.tx_fs_rate) {
831 				dev_err(qmc_audio->dev, "dai %d QMC chan %d inconsistent Tx frame sample rate (%lu instead of %lu)\n",
832 					qmc_dai->id, i, info.tx_fs_rate, tx_fs_rate);
833 				return -EINVAL;
834 			}
835 			if (rx_fs_rate != info.rx_fs_rate) {
836 				dev_err(qmc_audio->dev, "dai %d QMC chan %d inconsistent Rx frame sample rate (%lu instead of %lu)\n",
837 					qmc_dai->id, i, info.rx_fs_rate, rx_fs_rate);
838 				return -EINVAL;
839 			}
840 		}
841 
842 		ret = qmc_chan_get_ts_info(qmc_dai->qmc_chans[i], &ts_info);
843 		if (ret) {
844 			dev_err(qmc_audio->dev, "dai %d get QMC %d channel TS info failed %d\n",
845 				qmc_dai->id, i, ret);
846 			return ret;
847 		}
848 
849 		last_rx_ts = fls64(ts_info.rx_ts_mask);
850 		last_tx_ts = fls64(ts_info.tx_ts_mask);
851 
852 		if (prev_last_rx_ts > last_rx_ts) {
853 			dev_err(qmc_audio->dev, "dai %d QMC chan %d unordered channels (RX timeslot %d before %d)\n",
854 				qmc_dai->id, i, prev_last_rx_ts, last_rx_ts);
855 			return -EINVAL;
856 		}
857 		if (prev_last_tx_ts > last_tx_ts) {
858 			dev_err(qmc_audio->dev, "dai %d QMC chan %d unordered channels (TX timeslot %d before %d)\n",
859 				qmc_dai->id, i, prev_last_tx_ts, last_tx_ts);
860 			return -EINVAL;
861 		}
862 
863 		prev_last_rx_ts = last_rx_ts;
864 		prev_last_tx_ts = last_tx_ts;
865 	}
866 
867 	qmc_dai->nb_chans_avail = count;
868 	qmc_dai->nb_tx_ts = nb_tx_ts * count;
869 	qmc_dai->nb_rx_ts = nb_rx_ts * count;
870 
871 	qmc_soc_dai_driver->id = qmc_dai->id;
872 	qmc_soc_dai_driver->name = qmc_dai->name;
873 
874 	qmc_soc_dai_driver->playback.channels_min = 0;
875 	qmc_soc_dai_driver->playback.channels_max = 0;
876 	if (nb_tx_ts) {
877 		qmc_soc_dai_driver->playback.channels_min = 1;
878 		qmc_soc_dai_driver->playback.channels_max = count > 1 ? count : nb_tx_ts;
879 	}
880 	qmc_soc_dai_driver->playback.formats = qmc_audio_formats(nb_tx_ts,
881 								 count > 1);
882 
883 	qmc_soc_dai_driver->capture.channels_min = 0;
884 	qmc_soc_dai_driver->capture.channels_max = 0;
885 	if (nb_rx_ts) {
886 		qmc_soc_dai_driver->capture.channels_min = 1;
887 		qmc_soc_dai_driver->capture.channels_max = count > 1 ? count : nb_rx_ts;
888 	}
889 	qmc_soc_dai_driver->capture.formats = qmc_audio_formats(nb_rx_ts,
890 								count > 1);
891 
892 	qmc_soc_dai_driver->playback.rates = snd_pcm_rate_to_rate_bit(tx_fs_rate);
893 	qmc_soc_dai_driver->playback.rate_min = tx_fs_rate;
894 	qmc_soc_dai_driver->playback.rate_max = tx_fs_rate;
895 	qmc_soc_dai_driver->capture.rates = snd_pcm_rate_to_rate_bit(rx_fs_rate);
896 	qmc_soc_dai_driver->capture.rate_min = rx_fs_rate;
897 	qmc_soc_dai_driver->capture.rate_max = rx_fs_rate;
898 
899 	qmc_soc_dai_driver->ops = &qmc_dai_ops;
900 
901 	return 0;
902 }
903 
904 static int qmc_audio_probe(struct platform_device *pdev)
905 {
906 	struct device_node *np = pdev->dev.of_node;
907 	struct qmc_audio *qmc_audio;
908 	struct device_node *child;
909 	unsigned int i;
910 	int ret;
911 
912 	qmc_audio = devm_kzalloc(&pdev->dev, sizeof(*qmc_audio), GFP_KERNEL);
913 	if (!qmc_audio)
914 		return -ENOMEM;
915 
916 	qmc_audio->dev = &pdev->dev;
917 
918 	qmc_audio->num_dais = of_get_available_child_count(np);
919 	if (qmc_audio->num_dais) {
920 		qmc_audio->dais = devm_kcalloc(&pdev->dev, qmc_audio->num_dais,
921 					       sizeof(*qmc_audio->dais),
922 					       GFP_KERNEL);
923 		if (!qmc_audio->dais)
924 			return -ENOMEM;
925 
926 		qmc_audio->dai_drivers = devm_kcalloc(&pdev->dev, qmc_audio->num_dais,
927 						      sizeof(*qmc_audio->dai_drivers),
928 						      GFP_KERNEL);
929 		if (!qmc_audio->dai_drivers)
930 			return -ENOMEM;
931 	}
932 
933 	i = 0;
934 	for_each_available_child_of_node(np, child) {
935 		ret = qmc_audio_dai_parse(qmc_audio, child,
936 					  qmc_audio->dais + i,
937 					  qmc_audio->dai_drivers + i);
938 		if (ret) {
939 			of_node_put(child);
940 			return ret;
941 		}
942 		i++;
943 	}
944 
945 	platform_set_drvdata(pdev, qmc_audio);
946 
947 	ret = devm_snd_soc_register_component(qmc_audio->dev,
948 					      &qmc_audio_soc_platform,
949 					      qmc_audio->dai_drivers,
950 					      qmc_audio->num_dais);
951 	if (ret)
952 		return ret;
953 
954 	return 0;
955 }
956 
957 static const struct of_device_id qmc_audio_id_table[] = {
958 	{ .compatible = "fsl,qmc-audio" },
959 	{} /* sentinel */
960 };
961 MODULE_DEVICE_TABLE(of, qmc_audio_id_table);
962 
963 static struct platform_driver qmc_audio_driver = {
964 	.driver = {
965 		.name = "fsl-qmc-audio",
966 		.of_match_table = of_match_ptr(qmc_audio_id_table),
967 	},
968 	.probe = qmc_audio_probe,
969 };
970 module_platform_driver(qmc_audio_driver);
971 
972 MODULE_AUTHOR("Herve Codina <herve.codina@bootlin.com>");
973 MODULE_DESCRIPTION("CPM/QE QMC audio driver");
974 MODULE_LICENSE("GPL");
975