1 // SPDX-License-Identifier: GPL-2.0
3 * ALSA SoC using the QUICC Multichannel Controller (QMC)
5 * Copyright 2022 CS GROUP France
7 * Author: Herve Codina <herve.codina@bootlin.com>
10 #include <linux/dma-mapping.h>
11 #include <linux/module.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>
21 struct qmc_dai_prtd
*prtd_tx
;
22 struct qmc_dai_prtd
*prtd_rx
;
23 struct qmc_chan
*qmc_chan
;
30 unsigned int nb_tx_ts
;
31 unsigned int nb_rx_ts
;
33 unsigned int nb_chans_avail
;
34 unsigned int nb_chans_used_tx
;
35 unsigned int nb_chans_used_rx
;
36 struct qmc_dai_chan
*chans
;
41 unsigned int num_dais
;
43 struct snd_soc_dai_driver
*dai_drivers
;
47 struct qmc_dai
*qmc_dai
;
49 snd_pcm_uframes_t buffer_ended
;
50 snd_pcm_uframes_t buffer_size
;
51 snd_pcm_uframes_t period_size
;
53 dma_addr_t ch_dma_addr_start
;
54 dma_addr_t ch_dma_addr_current
;
55 dma_addr_t ch_dma_addr_end
;
59 unsigned int channels
;
60 DECLARE_BITMAP(chans_pending
, 64);
61 struct snd_pcm_substream
*substream
;
64 static int qmc_audio_pcm_construct(struct snd_soc_component
*component
,
65 struct snd_soc_pcm_runtime
*rtd
)
67 struct snd_card
*card
= rtd
->card
->snd_card
;
70 ret
= dma_coerce_mask_and_coherent(card
->dev
, DMA_BIT_MASK(32));
74 snd_pcm_set_managed_buffer_all(rtd
->pcm
, SNDRV_DMA_TYPE_DEV
, card
->dev
,
75 64 * 1024, 64 * 1024);
79 static bool qmc_audio_access_is_interleaved(snd_pcm_access_t access
)
82 case SNDRV_PCM_ACCESS_MMAP_INTERLEAVED
:
83 case SNDRV_PCM_ACCESS_RW_INTERLEAVED
:
91 static int qmc_audio_pcm_hw_params(struct snd_soc_component
*component
,
92 struct snd_pcm_substream
*substream
,
93 struct snd_pcm_hw_params
*params
)
95 struct snd_pcm_runtime
*runtime
= substream
->runtime
;
96 struct qmc_dai_prtd
*prtd
= substream
->runtime
->private_data
;
99 * In interleaved mode, the driver uses one QMC channel for all audio
100 * channels whereas in non-interleaved mode, it uses one QMC channel per
103 prtd
->channels
= qmc_audio_access_is_interleaved(params_access(params
)) ?
104 1 : params_channels(params
);
106 prtd
->substream
= substream
;
108 prtd
->buffer_ended
= 0;
109 prtd
->buffer_size
= params_buffer_size(params
);
110 prtd
->period_size
= params_period_size(params
);
112 prtd
->ch_dma_addr_start
= runtime
->dma_addr
;
113 prtd
->ch_dma_offset
= params_buffer_bytes(params
) / prtd
->channels
;
114 prtd
->ch_dma_addr_end
= runtime
->dma_addr
+ prtd
->ch_dma_offset
;
115 prtd
->ch_dma_addr_current
= prtd
->ch_dma_addr_start
;
116 prtd
->ch_dma_size
= params_period_bytes(params
) / prtd
->channels
;
121 static void qmc_audio_pcm_write_complete(void *context
);
123 static int qmc_audio_pcm_write_submit(struct qmc_dai_prtd
*prtd
)
128 for (i
= 0; i
< prtd
->channels
; i
++) {
129 bitmap_set(prtd
->chans_pending
, i
, 1);
131 ret
= qmc_chan_write_submit(prtd
->qmc_dai
->chans
[i
].qmc_chan
,
132 prtd
->ch_dma_addr_current
+ i
* prtd
->ch_dma_offset
,
134 qmc_audio_pcm_write_complete
,
135 &prtd
->qmc_dai
->chans
[i
]);
137 dev_err(prtd
->qmc_dai
->dev
, "write_submit %u failed %d\n",
139 bitmap_clear(prtd
->chans_pending
, i
, 1);
147 static void qmc_audio_pcm_write_complete(void *context
)
149 struct qmc_dai_chan
*chan
= context
;
150 struct qmc_dai_prtd
*prtd
;
152 prtd
= chan
->prtd_tx
;
154 /* Mark the current channel as completed */
155 bitmap_clear(prtd
->chans_pending
, chan
- prtd
->qmc_dai
->chans
, 1);
158 * All QMC channels involved must have completed their transfer before
159 * submitting a new one.
161 if (!bitmap_empty(prtd
->chans_pending
, 64))
164 prtd
->buffer_ended
+= prtd
->period_size
;
165 if (prtd
->buffer_ended
>= prtd
->buffer_size
)
166 prtd
->buffer_ended
= 0;
168 prtd
->ch_dma_addr_current
+= prtd
->ch_dma_size
;
169 if (prtd
->ch_dma_addr_current
>= prtd
->ch_dma_addr_end
)
170 prtd
->ch_dma_addr_current
= prtd
->ch_dma_addr_start
;
172 qmc_audio_pcm_write_submit(prtd
);
174 snd_pcm_period_elapsed(prtd
->substream
);
177 static void qmc_audio_pcm_read_complete(void *context
, size_t length
, unsigned int flags
);
179 static int qmc_audio_pcm_read_submit(struct qmc_dai_prtd
*prtd
)
184 for (i
= 0; i
< prtd
->channels
; i
++) {
185 bitmap_set(prtd
->chans_pending
, i
, 1);
187 ret
= qmc_chan_read_submit(prtd
->qmc_dai
->chans
[i
].qmc_chan
,
188 prtd
->ch_dma_addr_current
+ i
* prtd
->ch_dma_offset
,
190 qmc_audio_pcm_read_complete
,
191 &prtd
->qmc_dai
->chans
[i
]);
193 dev_err(prtd
->qmc_dai
->dev
, "read_submit %u failed %d\n",
195 bitmap_clear(prtd
->chans_pending
, i
, 1);
203 static void qmc_audio_pcm_read_complete(void *context
, size_t length
, unsigned int flags
)
205 struct qmc_dai_chan
*chan
= context
;
206 struct qmc_dai_prtd
*prtd
;
208 prtd
= chan
->prtd_rx
;
210 /* Mark the current channel as completed */
211 bitmap_clear(prtd
->chans_pending
, chan
- prtd
->qmc_dai
->chans
, 1);
213 if (length
!= prtd
->ch_dma_size
) {
214 dev_err(prtd
->qmc_dai
->dev
, "read complete length = %zu, exp %zu\n",
215 length
, prtd
->ch_dma_size
);
219 * All QMC channels involved must have completed their transfer before
220 * submitting a new one.
222 if (!bitmap_empty(prtd
->chans_pending
, 64))
225 prtd
->buffer_ended
+= prtd
->period_size
;
226 if (prtd
->buffer_ended
>= prtd
->buffer_size
)
227 prtd
->buffer_ended
= 0;
229 prtd
->ch_dma_addr_current
+= prtd
->ch_dma_size
;
230 if (prtd
->ch_dma_addr_current
>= prtd
->ch_dma_addr_end
)
231 prtd
->ch_dma_addr_current
= prtd
->ch_dma_addr_start
;
233 qmc_audio_pcm_read_submit(prtd
);
235 snd_pcm_period_elapsed(prtd
->substream
);
238 static int qmc_audio_pcm_trigger(struct snd_soc_component
*component
,
239 struct snd_pcm_substream
*substream
, int cmd
)
241 struct qmc_dai_prtd
*prtd
= substream
->runtime
->private_data
;
245 if (!prtd
->qmc_dai
) {
246 dev_err(component
->dev
, "qmc_dai is not set\n");
251 case SNDRV_PCM_TRIGGER_START
:
252 bitmap_zero(prtd
->chans_pending
, 64);
253 if (substream
->stream
== SNDRV_PCM_STREAM_PLAYBACK
) {
254 for (i
= 0; i
< prtd
->channels
; i
++)
255 prtd
->qmc_dai
->chans
[i
].prtd_tx
= prtd
;
257 /* Submit first chunk ... */
258 ret
= qmc_audio_pcm_write_submit(prtd
);
262 /* ... prepare next one ... */
263 prtd
->ch_dma_addr_current
+= prtd
->ch_dma_size
;
264 if (prtd
->ch_dma_addr_current
>= prtd
->ch_dma_addr_end
)
265 prtd
->ch_dma_addr_current
= prtd
->ch_dma_addr_start
;
267 /* ... and send it */
268 ret
= qmc_audio_pcm_write_submit(prtd
);
272 for (i
= 0; i
< prtd
->channels
; i
++)
273 prtd
->qmc_dai
->chans
[i
].prtd_rx
= prtd
;
275 /* Submit first chunk ... */
276 ret
= qmc_audio_pcm_read_submit(prtd
);
280 /* ... prepare next one ... */
281 prtd
->ch_dma_addr_current
+= prtd
->ch_dma_size
;
282 if (prtd
->ch_dma_addr_current
>= prtd
->ch_dma_addr_end
)
283 prtd
->ch_dma_addr_current
= prtd
->ch_dma_addr_start
;
285 /* ... and send it */
286 ret
= qmc_audio_pcm_read_submit(prtd
);
292 case SNDRV_PCM_TRIGGER_RESUME
:
293 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE
:
296 case SNDRV_PCM_TRIGGER_STOP
:
297 case SNDRV_PCM_TRIGGER_SUSPEND
:
298 case SNDRV_PCM_TRIGGER_PAUSE_PUSH
:
308 static snd_pcm_uframes_t
qmc_audio_pcm_pointer(struct snd_soc_component
*component
,
309 struct snd_pcm_substream
*substream
)
311 struct qmc_dai_prtd
*prtd
= substream
->runtime
->private_data
;
313 return prtd
->buffer_ended
;
316 static int qmc_audio_of_xlate_dai_name(struct snd_soc_component
*component
,
317 const struct of_phandle_args
*args
,
318 const char **dai_name
)
320 struct qmc_audio
*qmc_audio
= dev_get_drvdata(component
->dev
);
321 struct snd_soc_dai_driver
*dai_driver
;
322 int id
= args
->args
[0];
325 for (i
= 0; i
< qmc_audio
->num_dais
; i
++) {
326 dai_driver
= qmc_audio
->dai_drivers
+ i
;
327 if (dai_driver
->id
== id
) {
328 *dai_name
= dai_driver
->name
;
336 static const struct snd_pcm_hardware qmc_audio_pcm_hardware
= {
337 .info
= SNDRV_PCM_INFO_MMAP
|
338 SNDRV_PCM_INFO_MMAP_VALID
|
339 SNDRV_PCM_INFO_INTERLEAVED
|
340 SNDRV_PCM_INFO_NONINTERLEAVED
|
341 SNDRV_PCM_INFO_PAUSE
,
342 .period_bytes_min
= 32,
343 .period_bytes_max
= 64 * 1024,
345 .periods_max
= 2 * 1024,
346 .buffer_bytes_max
= 64 * 1024,
349 static int qmc_audio_pcm_open(struct snd_soc_component
*component
,
350 struct snd_pcm_substream
*substream
)
352 struct snd_pcm_runtime
*runtime
= substream
->runtime
;
353 struct qmc_dai_prtd
*prtd
;
356 snd_soc_set_runtime_hwparams(substream
, &qmc_audio_pcm_hardware
);
358 /* ensure that buffer size is a multiple of period size */
359 ret
= snd_pcm_hw_constraint_integer(runtime
, SNDRV_PCM_HW_PARAM_PERIODS
);
363 prtd
= kzalloc(sizeof(*prtd
), GFP_KERNEL
);
367 runtime
->private_data
= prtd
;
372 static int qmc_audio_pcm_close(struct snd_soc_component
*component
,
373 struct snd_pcm_substream
*substream
)
375 struct qmc_dai_prtd
*prtd
= substream
->runtime
->private_data
;
381 static const struct snd_soc_component_driver qmc_audio_soc_platform
= {
382 .open
= qmc_audio_pcm_open
,
383 .close
= qmc_audio_pcm_close
,
384 .hw_params
= qmc_audio_pcm_hw_params
,
385 .trigger
= qmc_audio_pcm_trigger
,
386 .pointer
= qmc_audio_pcm_pointer
,
387 .pcm_construct
= qmc_audio_pcm_construct
,
388 .of_xlate_dai_name
= qmc_audio_of_xlate_dai_name
,
391 static unsigned int qmc_dai_get_index(struct snd_soc_dai
*dai
)
393 struct qmc_audio
*qmc_audio
= snd_soc_dai_get_drvdata(dai
);
395 return dai
->driver
- qmc_audio
->dai_drivers
;
398 static struct qmc_dai
*qmc_dai_get_data(struct snd_soc_dai
*dai
)
400 struct qmc_audio
*qmc_audio
= snd_soc_dai_get_drvdata(dai
);
403 index
= qmc_dai_get_index(dai
);
404 if (index
> qmc_audio
->num_dais
)
407 return qmc_audio
->dais
+ index
;
411 * The constraints for format/channel is to match with the number of 8bit
412 * time-slots available.
414 static int qmc_dai_hw_rule_channels_by_format(struct qmc_dai
*qmc_dai
,
415 struct snd_pcm_hw_params
*params
,
418 struct snd_interval
*c
= hw_param_interval(params
, SNDRV_PCM_HW_PARAM_CHANNELS
);
419 snd_pcm_format_t format
= params_format(params
);
420 struct snd_interval ch
= {0};
422 switch (snd_pcm_format_physical_width(format
)) {
436 dev_err(qmc_dai
->dev
, "format physical width %u not supported\n",
437 snd_pcm_format_physical_width(format
));
441 ch
.min
= ch
.max
? 1 : 0;
443 return snd_interval_refine(c
, &ch
);
446 static int qmc_dai_hw_rule_playback_channels_by_format(struct snd_pcm_hw_params
*params
,
447 struct snd_pcm_hw_rule
*rule
)
449 struct qmc_dai
*qmc_dai
= rule
->private;
451 return qmc_dai_hw_rule_channels_by_format(qmc_dai
, params
, qmc_dai
->nb_tx_ts
);
454 static int qmc_dai_hw_rule_capture_channels_by_format(struct snd_pcm_hw_params
*params
,
455 struct snd_pcm_hw_rule
*rule
)
457 struct qmc_dai
*qmc_dai
= rule
->private;
459 return qmc_dai_hw_rule_channels_by_format(qmc_dai
, params
, qmc_dai
->nb_rx_ts
);
462 static int qmc_dai_hw_rule_format_by_channels(struct qmc_dai
*qmc_dai
,
463 struct snd_pcm_hw_params
*params
,
466 struct snd_mask
*f_old
= hw_param_mask(params
, SNDRV_PCM_HW_PARAM_FORMAT
);
467 unsigned int channels
= params_channels(params
);
468 unsigned int slot_width
;
469 snd_pcm_format_t format
;
470 struct snd_mask f_new
;
472 if (!channels
|| channels
> nb_ts
) {
473 dev_err(qmc_dai
->dev
, "channels %u not supported\n",
478 slot_width
= (nb_ts
/ channels
) * 8;
480 snd_mask_none(&f_new
);
481 pcm_for_each_format(format
) {
482 if (snd_mask_test_format(f_old
, format
)) {
483 if (snd_pcm_format_physical_width(format
) <= slot_width
)
484 snd_mask_set_format(&f_new
, format
);
488 return snd_mask_refine(f_old
, &f_new
);
491 static int qmc_dai_hw_rule_playback_format_by_channels(struct snd_pcm_hw_params
*params
,
492 struct snd_pcm_hw_rule
*rule
)
494 struct qmc_dai
*qmc_dai
= rule
->private;
496 return qmc_dai_hw_rule_format_by_channels(qmc_dai
, params
, qmc_dai
->nb_tx_ts
);
499 static int qmc_dai_hw_rule_capture_format_by_channels(struct snd_pcm_hw_params
*params
,
500 struct snd_pcm_hw_rule
*rule
)
502 struct qmc_dai
*qmc_dai
= rule
->private;
504 return qmc_dai_hw_rule_format_by_channels(qmc_dai
, params
, qmc_dai
->nb_rx_ts
);
507 static int qmc_dai_constraints_interleaved(struct snd_pcm_substream
*substream
,
508 struct qmc_dai
*qmc_dai
)
510 snd_pcm_hw_rule_func_t hw_rule_channels_by_format
;
511 snd_pcm_hw_rule_func_t hw_rule_format_by_channels
;
512 unsigned int frame_bits
;
516 if (substream
->stream
== SNDRV_PCM_STREAM_CAPTURE
) {
517 hw_rule_channels_by_format
= qmc_dai_hw_rule_capture_channels_by_format
;
518 hw_rule_format_by_channels
= qmc_dai_hw_rule_capture_format_by_channels
;
519 frame_bits
= qmc_dai
->nb_rx_ts
* 8;
521 hw_rule_channels_by_format
= qmc_dai_hw_rule_playback_channels_by_format
;
522 hw_rule_format_by_channels
= qmc_dai_hw_rule_playback_format_by_channels
;
523 frame_bits
= qmc_dai
->nb_tx_ts
* 8;
526 ret
= snd_pcm_hw_rule_add(substream
->runtime
, 0, SNDRV_PCM_HW_PARAM_CHANNELS
,
527 hw_rule_channels_by_format
, qmc_dai
,
528 SNDRV_PCM_HW_PARAM_FORMAT
, -1);
530 dev_err(qmc_dai
->dev
, "Failed to add channels rule (%d)\n", ret
);
534 ret
= snd_pcm_hw_rule_add(substream
->runtime
, 0, SNDRV_PCM_HW_PARAM_FORMAT
,
535 hw_rule_format_by_channels
, qmc_dai
,
536 SNDRV_PCM_HW_PARAM_CHANNELS
, -1);
538 dev_err(qmc_dai
->dev
, "Failed to add format rule (%d)\n", ret
);
542 ret
= snd_pcm_hw_constraint_single(substream
->runtime
,
543 SNDRV_PCM_HW_PARAM_FRAME_BITS
,
546 dev_err(qmc_dai
->dev
, "Failed to add frame_bits constraint (%d)\n", ret
);
550 access
= 1ULL << (__force
int)SNDRV_PCM_ACCESS_MMAP_INTERLEAVED
|
551 1ULL << (__force
int)SNDRV_PCM_ACCESS_RW_INTERLEAVED
;
552 ret
= snd_pcm_hw_constraint_mask64(substream
->runtime
, SNDRV_PCM_HW_PARAM_ACCESS
,
555 dev_err(qmc_dai
->dev
, "Failed to add hw_param_access constraint (%d)\n", ret
);
562 static int qmc_dai_constraints_noninterleaved(struct snd_pcm_substream
*substream
,
563 struct qmc_dai
*qmc_dai
)
565 unsigned int frame_bits
;
569 frame_bits
= (substream
->stream
== SNDRV_PCM_STREAM_CAPTURE
) ?
570 qmc_dai
->nb_rx_ts
* 8 : qmc_dai
->nb_tx_ts
* 8;
571 ret
= snd_pcm_hw_constraint_single(substream
->runtime
,
572 SNDRV_PCM_HW_PARAM_FRAME_BITS
,
575 dev_err(qmc_dai
->dev
, "Failed to add frame_bits constraint (%d)\n", ret
);
579 access
= 1ULL << (__force
int)SNDRV_PCM_ACCESS_MMAP_NONINTERLEAVED
|
580 1ULL << (__force
int)SNDRV_PCM_ACCESS_RW_NONINTERLEAVED
;
581 ret
= snd_pcm_hw_constraint_mask64(substream
->runtime
, SNDRV_PCM_HW_PARAM_ACCESS
,
584 dev_err(qmc_dai
->dev
, "Failed to add hw_param_access constraint (%d)\n", ret
);
591 static int qmc_dai_startup(struct snd_pcm_substream
*substream
,
592 struct snd_soc_dai
*dai
)
594 struct qmc_dai_prtd
*prtd
= substream
->runtime
->private_data
;
595 struct qmc_dai
*qmc_dai
;
597 qmc_dai
= qmc_dai_get_data(dai
);
599 dev_err(dai
->dev
, "Invalid dai\n");
603 prtd
->qmc_dai
= qmc_dai
;
605 return qmc_dai
->nb_chans_avail
> 1 ?
606 qmc_dai_constraints_noninterleaved(substream
, qmc_dai
) :
607 qmc_dai_constraints_interleaved(substream
, qmc_dai
);
610 static int qmc_dai_hw_params(struct snd_pcm_substream
*substream
,
611 struct snd_pcm_hw_params
*params
,
612 struct snd_soc_dai
*dai
)
614 struct qmc_chan_param chan_param
= {0};
615 unsigned int nb_chans_used
;
616 struct qmc_dai
*qmc_dai
;
620 qmc_dai
= qmc_dai_get_data(dai
);
622 dev_err(dai
->dev
, "Invalid dai\n");
627 * In interleaved mode, the driver uses one QMC channel for all audio
628 * channels whereas in non-interleaved mode, it uses one QMC channel per
631 nb_chans_used
= qmc_audio_access_is_interleaved(params_access(params
)) ?
632 1 : params_channels(params
);
634 if (nb_chans_used
> qmc_dai
->nb_chans_avail
) {
635 dev_err(dai
->dev
, "Not enough qmc_chans. Need %u, avail %u\n",
636 nb_chans_used
, qmc_dai
->nb_chans_avail
);
640 if (substream
->stream
== SNDRV_PCM_STREAM_CAPTURE
) {
641 chan_param
.mode
= QMC_TRANSPARENT
;
642 chan_param
.transp
.max_rx_buf_size
= params_period_bytes(params
) / nb_chans_used
;
643 for (i
= 0; i
< nb_chans_used
; i
++) {
644 ret
= qmc_chan_set_param(qmc_dai
->chans
[i
].qmc_chan
, &chan_param
);
646 dev_err(dai
->dev
, "chans[%u], set param failed %d\n",
651 qmc_dai
->nb_chans_used_rx
= nb_chans_used
;
653 qmc_dai
->nb_chans_used_tx
= nb_chans_used
;
659 static int qmc_dai_trigger(struct snd_pcm_substream
*substream
, int cmd
,
660 struct snd_soc_dai
*dai
)
662 unsigned int nb_chans_used
;
663 struct qmc_dai
*qmc_dai
;
669 qmc_dai
= qmc_dai_get_data(dai
);
671 dev_err(dai
->dev
, "Invalid dai\n");
675 if (substream
->stream
== SNDRV_PCM_STREAM_PLAYBACK
) {
676 direction
= QMC_CHAN_WRITE
;
677 nb_chans_used
= qmc_dai
->nb_chans_used_tx
;
679 direction
= QMC_CHAN_READ
;
680 nb_chans_used
= qmc_dai
->nb_chans_used_rx
;
684 case SNDRV_PCM_TRIGGER_START
:
685 case SNDRV_PCM_TRIGGER_RESUME
:
686 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE
:
687 for (i
= 0; i
< nb_chans_used
; i
++) {
688 ret
= qmc_chan_start(qmc_dai
->chans
[i
].qmc_chan
, direction
);
694 case SNDRV_PCM_TRIGGER_STOP
:
695 /* Stop and reset all QMC channels and return the first error encountered */
696 for (i
= 0; i
< nb_chans_used
; i
++) {
697 ret_tmp
= qmc_chan_stop(qmc_dai
->chans
[i
].qmc_chan
, direction
);
703 ret_tmp
= qmc_chan_reset(qmc_dai
->chans
[i
].qmc_chan
, direction
);
711 case SNDRV_PCM_TRIGGER_SUSPEND
:
712 case SNDRV_PCM_TRIGGER_PAUSE_PUSH
:
713 /* Stop all QMC channels and return the first error encountered */
714 for (i
= 0; i
< nb_chans_used
; i
++) {
715 ret_tmp
= qmc_chan_stop(qmc_dai
->chans
[i
].qmc_chan
, direction
);
731 qmc_chan_stop(qmc_dai
->chans
[i
].qmc_chan
, direction
);
732 qmc_chan_reset(qmc_dai
->chans
[i
].qmc_chan
, direction
);
737 static const struct snd_soc_dai_ops qmc_dai_ops
= {
738 .startup
= qmc_dai_startup
,
739 .trigger
= qmc_dai_trigger
,
740 .hw_params
= qmc_dai_hw_params
,
743 static u64
qmc_audio_formats(u8 nb_ts
, bool is_noninterleaved
)
745 unsigned int format_width
;
746 unsigned int chan_width
;
747 snd_pcm_format_t format
;
754 chan_width
= nb_ts
* 8;
755 pcm_for_each_format(format
) {
757 * Support format other than little-endian (ie big-endian or
758 * without endianness such as 8bit formats)
760 if (snd_pcm_format_little_endian(format
) == 1)
763 /* Support physical width multiple of 8bit */
764 format_width
= snd_pcm_format_physical_width(format
);
765 if (format_width
== 0 || format_width
% 8)
769 * And support physical width that can fit N times in the
772 if (format_width
> chan_width
|| chan_width
% format_width
)
776 * In non interleaved mode, we can only support formats that
777 * can fit only 1 time in the channel
779 if (is_noninterleaved
&& format_width
!= chan_width
)
782 formats_mask
|= pcm_format_to_bits(format
);
787 static int qmc_audio_dai_parse(struct qmc_audio
*qmc_audio
, struct device_node
*np
,
788 struct qmc_dai
*qmc_dai
,
789 struct snd_soc_dai_driver
*qmc_soc_dai_driver
)
791 struct qmc_chan_info info
;
792 unsigned long rx_fs_rate
;
793 unsigned long tx_fs_rate
;
794 unsigned int nb_tx_ts
;
795 unsigned int nb_rx_ts
;
801 qmc_dai
->dev
= qmc_audio
->dev
;
803 ret
= of_property_read_u32(np
, "reg", &val
);
805 dev_err(qmc_audio
->dev
, "%pOF: failed to read reg\n", np
);
810 qmc_dai
->name
= devm_kasprintf(qmc_audio
->dev
, GFP_KERNEL
, "%s.%d",
811 np
->parent
->name
, qmc_dai
->id
);
815 count
= qmc_chan_count_phandles(np
, "fsl,qmc-chan");
817 return dev_err_probe(qmc_audio
->dev
, count
,
818 "dai %d get number of QMC channel failed\n", qmc_dai
->id
);
820 return dev_err_probe(qmc_audio
->dev
, -EINVAL
,
821 "dai %d no QMC channel defined\n", qmc_dai
->id
);
823 qmc_dai
->chans
= devm_kcalloc(qmc_audio
->dev
, count
, sizeof(*qmc_dai
->chans
), GFP_KERNEL
);
827 for (i
= 0; i
< count
; i
++) {
828 qmc_dai
->chans
[i
].qmc_chan
= devm_qmc_chan_get_byphandles_index(qmc_audio
->dev
, np
,
830 if (IS_ERR(qmc_dai
->chans
[i
].qmc_chan
)) {
831 return dev_err_probe(qmc_audio
->dev
, PTR_ERR(qmc_dai
->chans
[i
].qmc_chan
),
832 "dai %d get QMC channel %d failed\n", qmc_dai
->id
, i
);
835 ret
= qmc_chan_get_info(qmc_dai
->chans
[i
].qmc_chan
, &info
);
837 dev_err(qmc_audio
->dev
, "dai %d get QMC %d channel info failed %d\n",
838 qmc_dai
->id
, i
, ret
);
842 if (info
.mode
!= QMC_TRANSPARENT
) {
843 dev_err(qmc_audio
->dev
, "dai %d QMC chan %d mode %d is not QMC_TRANSPARENT\n",
844 qmc_dai
->id
, i
, info
.mode
);
849 * All channels must have the same number of Tx slots and the
850 * same numbers of Rx slots.
853 nb_tx_ts
= info
.nb_tx_ts
;
854 nb_rx_ts
= info
.nb_rx_ts
;
855 tx_fs_rate
= info
.tx_fs_rate
;
856 rx_fs_rate
= info
.rx_fs_rate
;
858 if (nb_tx_ts
!= info
.nb_tx_ts
) {
859 dev_err(qmc_audio
->dev
, "dai %d QMC chan %d inconsistent number of Tx timeslots (%u instead of %u)\n",
860 qmc_dai
->id
, i
, info
.nb_tx_ts
, nb_tx_ts
);
863 if (nb_rx_ts
!= info
.nb_rx_ts
) {
864 dev_err(qmc_audio
->dev
, "dai %d QMC chan %d inconsistent number of Rx timeslots (%u instead of %u)\n",
865 qmc_dai
->id
, i
, info
.nb_rx_ts
, nb_rx_ts
);
868 if (tx_fs_rate
!= info
.tx_fs_rate
) {
869 dev_err(qmc_audio
->dev
, "dai %d QMC chan %d inconsistent Tx frame sample rate (%lu instead of %lu)\n",
870 qmc_dai
->id
, i
, info
.tx_fs_rate
, tx_fs_rate
);
873 if (rx_fs_rate
!= info
.rx_fs_rate
) {
874 dev_err(qmc_audio
->dev
, "dai %d QMC chan %d inconsistent Rx frame sample rate (%lu instead of %lu)\n",
875 qmc_dai
->id
, i
, info
.rx_fs_rate
, rx_fs_rate
);
881 qmc_dai
->nb_chans_avail
= count
;
882 qmc_dai
->nb_tx_ts
= nb_tx_ts
* count
;
883 qmc_dai
->nb_rx_ts
= nb_rx_ts
* count
;
885 qmc_soc_dai_driver
->id
= qmc_dai
->id
;
886 qmc_soc_dai_driver
->name
= qmc_dai
->name
;
888 qmc_soc_dai_driver
->playback
.channels_min
= 0;
889 qmc_soc_dai_driver
->playback
.channels_max
= 0;
891 qmc_soc_dai_driver
->playback
.channels_min
= 1;
892 qmc_soc_dai_driver
->playback
.channels_max
= count
> 1 ? count
: nb_tx_ts
;
894 qmc_soc_dai_driver
->playback
.formats
= qmc_audio_formats(nb_tx_ts
,
895 count
> 1 ? true : false);
897 qmc_soc_dai_driver
->capture
.channels_min
= 0;
898 qmc_soc_dai_driver
->capture
.channels_max
= 0;
900 qmc_soc_dai_driver
->capture
.channels_min
= 1;
901 qmc_soc_dai_driver
->capture
.channels_max
= count
> 1 ? count
: nb_rx_ts
;
903 qmc_soc_dai_driver
->capture
.formats
= qmc_audio_formats(nb_rx_ts
,
904 count
> 1 ? true : false);
906 qmc_soc_dai_driver
->playback
.rates
= snd_pcm_rate_to_rate_bit(tx_fs_rate
);
907 qmc_soc_dai_driver
->playback
.rate_min
= tx_fs_rate
;
908 qmc_soc_dai_driver
->playback
.rate_max
= tx_fs_rate
;
909 qmc_soc_dai_driver
->capture
.rates
= snd_pcm_rate_to_rate_bit(rx_fs_rate
);
910 qmc_soc_dai_driver
->capture
.rate_min
= rx_fs_rate
;
911 qmc_soc_dai_driver
->capture
.rate_max
= rx_fs_rate
;
913 qmc_soc_dai_driver
->ops
= &qmc_dai_ops
;
918 static int qmc_audio_probe(struct platform_device
*pdev
)
920 struct device_node
*np
= pdev
->dev
.of_node
;
921 struct qmc_audio
*qmc_audio
;
922 struct device_node
*child
;
926 qmc_audio
= devm_kzalloc(&pdev
->dev
, sizeof(*qmc_audio
), GFP_KERNEL
);
930 qmc_audio
->dev
= &pdev
->dev
;
932 qmc_audio
->num_dais
= of_get_available_child_count(np
);
933 if (qmc_audio
->num_dais
) {
934 qmc_audio
->dais
= devm_kcalloc(&pdev
->dev
, qmc_audio
->num_dais
,
935 sizeof(*qmc_audio
->dais
),
937 if (!qmc_audio
->dais
)
940 qmc_audio
->dai_drivers
= devm_kcalloc(&pdev
->dev
, qmc_audio
->num_dais
,
941 sizeof(*qmc_audio
->dai_drivers
),
943 if (!qmc_audio
->dai_drivers
)
948 for_each_available_child_of_node(np
, child
) {
949 ret
= qmc_audio_dai_parse(qmc_audio
, child
,
951 qmc_audio
->dai_drivers
+ i
);
959 platform_set_drvdata(pdev
, qmc_audio
);
961 ret
= devm_snd_soc_register_component(qmc_audio
->dev
,
962 &qmc_audio_soc_platform
,
963 qmc_audio
->dai_drivers
,
964 qmc_audio
->num_dais
);
971 static const struct of_device_id qmc_audio_id_table
[] = {
972 { .compatible
= "fsl,qmc-audio" },
975 MODULE_DEVICE_TABLE(of
, qmc_audio_id_table
);
977 static struct platform_driver qmc_audio_driver
= {
979 .name
= "fsl-qmc-audio",
980 .of_match_table
= of_match_ptr(qmc_audio_id_table
),
982 .probe
= qmc_audio_probe
,
984 module_platform_driver(qmc_audio_driver
);
986 MODULE_AUTHOR("Herve Codina <herve.codina@bootlin.com>");
987 MODULE_DESCRIPTION("CPM/QE QMC audio driver");
988 MODULE_LICENSE("GPL");