3
3
* drivers/dma/fsl-edma.c
4
4
*
5
5
* Copyright 2013-2014 Freescale Semiconductor, Inc.
6
+ * Copyright 2024 NXP
6
7
*
7
8
* Driver for the Freescale eDMA engine with flexible channel multiplexing
8
9
* capability for DMA request sources. The eDMA block can be found on some
9
- * Vybrid and Layerscape SoCs.
10
+ * Vybrid, Layerscape and S32G SoCs.
10
11
*/
11
12
12
13
#include <dt-bindings/dma/fsl-edma.h>
@@ -72,6 +73,60 @@ static irqreturn_t fsl_edma2_tx_handler(int irq, void *devi_id)
72
73
return fsl_edma_tx_handler (irq , fsl_chan -> edma );
73
74
}
74
75
76
+ static irqreturn_t fsl_edma3_or_tx_handler (int irq , void * dev_id ,
77
+ u8 start , u8 end )
78
+ {
79
+ struct fsl_edma_engine * fsl_edma = dev_id ;
80
+ struct fsl_edma_chan * chan ;
81
+ int i ;
82
+
83
+ end = min (end , fsl_edma -> n_chans );
84
+
85
+ for (i = start ; i < end ; i ++ ) {
86
+ chan = & fsl_edma -> chans [i ];
87
+
88
+ fsl_edma3_tx_handler (irq , chan );
89
+ }
90
+
91
+ return IRQ_HANDLED ;
92
+ }
93
+
94
+ static irqreturn_t fsl_edma3_tx_0_15_handler (int irq , void * dev_id )
95
+ {
96
+ return fsl_edma3_or_tx_handler (irq , dev_id , 0 , 16 );
97
+ }
98
+
99
+ static irqreturn_t fsl_edma3_tx_16_31_handler (int irq , void * dev_id )
100
+ {
101
+ return fsl_edma3_or_tx_handler (irq , dev_id , 16 , 32 );
102
+ }
103
+
104
+ static irqreturn_t fsl_edma3_or_err_handler (int irq , void * dev_id )
105
+ {
106
+ struct fsl_edma_engine * fsl_edma = dev_id ;
107
+ struct edma_regs * regs = & fsl_edma -> regs ;
108
+ unsigned int err , ch , ch_es ;
109
+ struct fsl_edma_chan * chan ;
110
+
111
+ err = edma_readl (fsl_edma , regs -> es );
112
+ if (!(err & EDMA_V3_MP_ES_VLD ))
113
+ return IRQ_NONE ;
114
+
115
+ for (ch = 0 ; ch < fsl_edma -> n_chans ; ch ++ ) {
116
+ chan = & fsl_edma -> chans [ch ];
117
+
118
+ ch_es = edma_readl_chreg (chan , ch_es );
119
+ if (!(ch_es & EDMA_V3_CH_ES_ERR ))
120
+ continue ;
121
+
122
+ edma_writel_chreg (chan , EDMA_V3_CH_ES_ERR , ch_es );
123
+ fsl_edma_disable_request (chan );
124
+ fsl_edma -> chans [ch ].status = DMA_ERROR ;
125
+ }
126
+
127
+ return IRQ_HANDLED ;
128
+ }
129
+
75
130
static irqreturn_t fsl_edma_err_handler (int irq , void * dev_id )
76
131
{
77
132
struct fsl_edma_engine * fsl_edma = dev_id ;
@@ -274,6 +329,49 @@ static int fsl_edma3_irq_init(struct platform_device *pdev, struct fsl_edma_engi
274
329
return 0 ;
275
330
}
276
331
332
+ static int fsl_edma3_or_irq_init (struct platform_device * pdev ,
333
+ struct fsl_edma_engine * fsl_edma )
334
+ {
335
+ int ret ;
336
+
337
+ fsl_edma -> txirq = platform_get_irq_byname (pdev , "tx-0-15" );
338
+ if (fsl_edma -> txirq < 0 )
339
+ return fsl_edma -> txirq ;
340
+
341
+ fsl_edma -> txirq_16_31 = platform_get_irq_byname (pdev , "tx-16-31" );
342
+ if (fsl_edma -> txirq_16_31 < 0 )
343
+ return fsl_edma -> txirq_16_31 ;
344
+
345
+ fsl_edma -> errirq = platform_get_irq_byname (pdev , "err" );
346
+ if (fsl_edma -> errirq < 0 )
347
+ return fsl_edma -> errirq ;
348
+
349
+ ret = devm_request_irq (& pdev -> dev , fsl_edma -> txirq ,
350
+ fsl_edma3_tx_0_15_handler , 0 , "eDMA tx0_15" ,
351
+ fsl_edma );
352
+ if (ret )
353
+ return dev_err_probe (& pdev -> dev , ret ,
354
+ "Can't register eDMA tx0_15 IRQ.\n" );
355
+
356
+ if (fsl_edma -> n_chans > 16 ) {
357
+ ret = devm_request_irq (& pdev -> dev , fsl_edma -> txirq_16_31 ,
358
+ fsl_edma3_tx_16_31_handler , 0 ,
359
+ "eDMA tx16_31" , fsl_edma );
360
+ if (ret )
361
+ return dev_err_probe (& pdev -> dev , ret ,
362
+ "Can't register eDMA tx16_31 IRQ.\n" );
363
+ }
364
+
365
+ ret = devm_request_irq (& pdev -> dev , fsl_edma -> errirq ,
366
+ fsl_edma3_or_err_handler , 0 , "eDMA err" ,
367
+ fsl_edma );
368
+ if (ret )
369
+ return dev_err_probe (& pdev -> dev , ret ,
370
+ "Can't register eDMA err IRQ.\n" );
371
+
372
+ return 0 ;
373
+ }
374
+
277
375
static int
278
376
fsl_edma2_irq_init (struct platform_device * pdev ,
279
377
struct fsl_edma_engine * fsl_edma )
@@ -404,6 +502,14 @@ static struct fsl_edma_drvdata imx95_data5 = {
404
502
.setup_irq = fsl_edma3_irq_init ,
405
503
};
406
504
505
+ static const struct fsl_edma_drvdata s32g2_data = {
506
+ .dmamuxs = DMAMUX_NR ,
507
+ .chreg_space_sz = EDMA_TCD ,
508
+ .chreg_off = 0x4000 ,
509
+ .flags = FSL_EDMA_DRV_EDMA3 | FSL_EDMA_DRV_MUX_SWAP ,
510
+ .setup_irq = fsl_edma3_or_irq_init ,
511
+ };
512
+
407
513
static const struct of_device_id fsl_edma_dt_ids [] = {
408
514
{ .compatible = "fsl,vf610-edma" , .data = & vf610_data },
409
515
{ .compatible = "fsl,ls1028a-edma" , .data = & ls1028a_data },
@@ -413,6 +519,7 @@ static const struct of_device_id fsl_edma_dt_ids[] = {
413
519
{ .compatible = "fsl,imx93-edma3" , .data = & imx93_data3 },
414
520
{ .compatible = "fsl,imx93-edma4" , .data = & imx93_data4 },
415
521
{ .compatible = "fsl,imx95-edma5" , .data = & imx95_data5 },
522
+ { .compatible = "nxp,s32g2-edma" , .data = & s32g2_data },
416
523
{ /* sentinel */ }
417
524
};
418
525
MODULE_DEVICE_TABLE (of , fsl_edma_dt_ids );
0 commit comments