1
1
// SPDX-License-Identifier: GPL-2.0
2
2
/*
3
3
* Copyright (c) 2018 Pengutronix, Oleksij Rempel <o.rempel@pengutronix.de>
4
+ * Copyright 2022 NXP, Peng Fan <peng.fan@nxp.com>
4
5
*/
5
6
6
7
#include <linux/clk.h>
28
29
#define IMX_MU_SECO_TX_TOUT (msecs_to_jiffies(3000))
29
30
#define IMX_MU_SECO_RX_TOUT (msecs_to_jiffies(3000))
30
31
32
+ /* Please not change TX & RX */
31
33
enum imx_mu_chan_type {
32
- IMX_MU_TYPE_TX , /* Tx */
33
- IMX_MU_TYPE_RX , /* Rx */
34
- IMX_MU_TYPE_TXDB , /* Tx doorbell */
35
- IMX_MU_TYPE_RXDB , /* Rx doorbell */
34
+ IMX_MU_TYPE_TX = 0 , /* Tx */
35
+ IMX_MU_TYPE_RX = 1 , /* Rx */
36
+ IMX_MU_TYPE_TXDB = 2 , /* Tx doorbell */
37
+ IMX_MU_TYPE_RXDB = 3 , /* Rx doorbell */
36
38
};
37
39
38
40
enum imx_mu_xcr {
@@ -92,6 +94,7 @@ enum imx_mu_type {
92
94
IMX_MU_V1 ,
93
95
IMX_MU_V2 = BIT (1 ),
94
96
IMX_MU_V2_S4 = BIT (15 ),
97
+ IMX_MU_V2_IRQ = BIT (16 ),
95
98
};
96
99
97
100
struct imx_mu_dcfg {
@@ -536,7 +539,7 @@ static int imx_mu_startup(struct mbox_chan *chan)
536
539
{
537
540
struct imx_mu_priv * priv = to_imx_mu_priv (chan -> mbox );
538
541
struct imx_mu_con_priv * cp = chan -> con_priv ;
539
- unsigned long irq_flag = IRQF_SHARED ;
542
+ unsigned long irq_flag = 0 ;
540
543
int ret ;
541
544
542
545
pm_runtime_get_sync (priv -> dev );
@@ -551,11 +554,12 @@ static int imx_mu_startup(struct mbox_chan *chan)
551
554
if (!priv -> dev -> pm_domain )
552
555
irq_flag |= IRQF_NO_SUSPEND ;
553
556
554
- ret = request_irq (priv -> irq [0 ], imx_mu_isr , irq_flag ,
555
- cp -> irq_desc , chan );
557
+ if (!(priv -> dcfg -> type & IMX_MU_V2_IRQ ))
558
+ irq_flag |= IRQF_SHARED ;
559
+
560
+ ret = request_irq (priv -> irq [cp -> type ], imx_mu_isr , irq_flag , cp -> irq_desc , chan );
556
561
if (ret ) {
557
- dev_err (priv -> dev ,
558
- "Unable to acquire IRQ %d\n" , priv -> irq [0 ]);
562
+ dev_err (priv -> dev , "Unable to acquire IRQ %d\n" , priv -> irq [cp -> type ]);
559
563
return ret ;
560
564
}
561
565
@@ -598,7 +602,7 @@ static void imx_mu_shutdown(struct mbox_chan *chan)
598
602
break ;
599
603
}
600
604
601
- free_irq (priv -> irq [0 ], chan );
605
+ free_irq (priv -> irq [cp -> type ], chan );
602
606
pm_runtime_put_sync (priv -> dev );
603
607
}
604
608
@@ -749,7 +753,7 @@ static int imx_mu_probe(struct platform_device *pdev)
749
753
struct device_node * np = dev -> of_node ;
750
754
struct imx_mu_priv * priv ;
751
755
const struct imx_mu_dcfg * dcfg ;
752
- int ret ;
756
+ int i , ret ;
753
757
u32 size ;
754
758
755
759
priv = devm_kzalloc (dev , sizeof (* priv ), GFP_KERNEL );
@@ -762,14 +766,25 @@ static int imx_mu_probe(struct platform_device *pdev)
762
766
if (IS_ERR (priv -> base ))
763
767
return PTR_ERR (priv -> base );
764
768
765
- priv -> irq [0 ] = platform_get_irq (pdev , 0 );
766
- if (priv -> irq [0 ] < 0 )
767
- return priv -> irq [0 ];
768
-
769
769
dcfg = of_device_get_match_data (dev );
770
770
if (!dcfg )
771
771
return - EINVAL ;
772
772
priv -> dcfg = dcfg ;
773
+ if (priv -> dcfg -> type & IMX_MU_V2_IRQ ) {
774
+ priv -> irq [IMX_MU_TYPE_TX ] = platform_get_irq_byname (pdev , "tx" );
775
+ if (priv -> irq [IMX_MU_TYPE_TX ] < 0 )
776
+ return priv -> irq [IMX_MU_TYPE_TX ];
777
+ priv -> irq [IMX_MU_TYPE_RX ] = platform_get_irq_byname (pdev , "rx" );
778
+ if (priv -> irq [IMX_MU_TYPE_RX ] < 0 )
779
+ return priv -> irq [IMX_MU_TYPE_RX ];
780
+ } else {
781
+ ret = platform_get_irq (pdev , 0 );
782
+ if (ret < 0 )
783
+ return ret ;
784
+
785
+ for (i = 0 ; i < IMX_MU_CHANS ; i ++ )
786
+ priv -> irq [i ] = ret ;
787
+ }
773
788
774
789
if (priv -> dcfg -> type & IMX_MU_V2_S4 )
775
790
size = sizeof (struct imx_s4_rpc_msg_max );
0 commit comments