@@ -72,6 +72,10 @@ struct zynqmp_ipi_mchan {
72
72
unsigned int chan_type ;
73
73
};
74
74
75
+ struct zynqmp_ipi_mbox ;
76
+
77
+ typedef int (* setup_ipi_fn )(struct zynqmp_ipi_mbox * ipi_mbox , struct device_node * node );
78
+
75
79
/**
76
80
* struct zynqmp_ipi_mbox - Description of a ZynqMP IPI mailbox
77
81
* platform data.
@@ -81,13 +85,15 @@ struct zynqmp_ipi_mchan {
81
85
* @remote_id: remote IPI agent ID
82
86
* @mbox: mailbox Controller
83
87
* @mchans: array for channels, tx channel and rx channel.
88
+ * @setup_ipi_fn: Function Pointer to set up IPI Channels
84
89
*/
85
90
struct zynqmp_ipi_mbox {
86
91
struct zynqmp_ipi_pdata * pdata ;
87
92
struct device dev ;
88
93
u32 remote_id ;
89
94
struct mbox_controller mbox ;
90
95
struct zynqmp_ipi_mchan mchans [2 ];
96
+ setup_ipi_fn setup_ipi_fn ;
91
97
};
92
98
93
99
/**
@@ -464,12 +470,9 @@ static void zynqmp_ipi_mbox_dev_release(struct device *dev)
464
470
static int zynqmp_ipi_mbox_probe (struct zynqmp_ipi_mbox * ipi_mbox ,
465
471
struct device_node * node )
466
472
{
467
- struct zynqmp_ipi_mchan * mchan ;
468
473
struct mbox_chan * chans ;
469
474
struct mbox_controller * mbox ;
470
- struct resource res ;
471
475
struct device * dev , * mdev ;
472
- const char * name ;
473
476
int ret ;
474
477
475
478
dev = ipi_mbox -> pdata -> dev ;
@@ -489,6 +492,73 @@ static int zynqmp_ipi_mbox_probe(struct zynqmp_ipi_mbox *ipi_mbox,
489
492
}
490
493
mdev = & ipi_mbox -> dev ;
491
494
495
+ /* Get the IPI remote agent ID */
496
+ ret = of_property_read_u32 (node , "xlnx,ipi-id" , & ipi_mbox -> remote_id );
497
+ if (ret < 0 ) {
498
+ dev_err (dev , "No IPI remote ID is specified.\n" );
499
+ return ret ;
500
+ }
501
+
502
+ ret = ipi_mbox -> setup_ipi_fn (ipi_mbox , node );
503
+ if (ret ) {
504
+ dev_err (dev , "Failed to set up IPI Buffers.\n" );
505
+ return ret ;
506
+ }
507
+
508
+ mbox = & ipi_mbox -> mbox ;
509
+ mbox -> dev = mdev ;
510
+ mbox -> ops = & zynqmp_ipi_chan_ops ;
511
+ mbox -> num_chans = 2 ;
512
+ mbox -> txdone_irq = false;
513
+ mbox -> txdone_poll = true;
514
+ mbox -> txpoll_period = 5 ;
515
+ mbox -> of_xlate = zynqmp_ipi_of_xlate ;
516
+ chans = devm_kzalloc (mdev , 2 * sizeof (* chans ), GFP_KERNEL );
517
+ if (!chans )
518
+ return - ENOMEM ;
519
+ mbox -> chans = chans ;
520
+ chans [IPI_MB_CHNL_TX ].con_priv = & ipi_mbox -> mchans [IPI_MB_CHNL_TX ];
521
+ chans [IPI_MB_CHNL_RX ].con_priv = & ipi_mbox -> mchans [IPI_MB_CHNL_RX ];
522
+ ipi_mbox -> mchans [IPI_MB_CHNL_TX ].chan_type = IPI_MB_CHNL_TX ;
523
+ ipi_mbox -> mchans [IPI_MB_CHNL_RX ].chan_type = IPI_MB_CHNL_RX ;
524
+ ret = devm_mbox_controller_register (mdev , mbox );
525
+ if (ret )
526
+ dev_err (mdev ,
527
+ "Failed to register mbox_controller(%d)\n" , ret );
528
+ else
529
+ dev_info (mdev ,
530
+ "Registered ZynqMP IPI mbox with TX/RX channels.\n" );
531
+ return ret ;
532
+ }
533
+
534
+ /**
535
+ * zynqmp_ipi_setup - set up IPI Buffers for classic flow
536
+ *
537
+ * @ipi_mbox: pointer to IPI mailbox private data structure
538
+ * @node: IPI mailbox device node
539
+ *
540
+ * This will be used to set up IPI Buffers for ZynqMP SOC if user
541
+ * wishes to use classic driver usage model on new SOC's with only
542
+ * buffered IPIs.
543
+ *
544
+ * Note that bufferless IPIs and mixed usage of buffered and bufferless
545
+ * IPIs are not supported with this flow.
546
+ *
547
+ * This will be invoked with compatible string "xlnx,zynqmp-ipi-mailbox".
548
+ *
549
+ * Return: 0 for success, negative value for failure
550
+ */
551
+ static int zynqmp_ipi_setup (struct zynqmp_ipi_mbox * ipi_mbox ,
552
+ struct device_node * node )
553
+ {
554
+ struct zynqmp_ipi_mchan * mchan ;
555
+ struct device * mdev ;
556
+ struct resource res ;
557
+ const char * name ;
558
+ int ret ;
559
+
560
+ mdev = & ipi_mbox -> dev ;
561
+
492
562
mchan = & ipi_mbox -> mchans [IPI_MB_CHNL_TX ];
493
563
name = "local_request_region" ;
494
564
ret = zynqmp_ipi_mbox_get_buf_res (node , name , & res );
@@ -563,37 +633,7 @@ static int zynqmp_ipi_mbox_probe(struct zynqmp_ipi_mbox *ipi_mbox,
563
633
if (!mchan -> rx_buf )
564
634
return - ENOMEM ;
565
635
566
- /* Get the IPI remote agent ID */
567
- ret = of_property_read_u32 (node , "xlnx,ipi-id" , & ipi_mbox -> remote_id );
568
- if (ret < 0 ) {
569
- dev_err (dev , "No IPI remote ID is specified.\n" );
570
- return ret ;
571
- }
572
-
573
- mbox = & ipi_mbox -> mbox ;
574
- mbox -> dev = mdev ;
575
- mbox -> ops = & zynqmp_ipi_chan_ops ;
576
- mbox -> num_chans = 2 ;
577
- mbox -> txdone_irq = false;
578
- mbox -> txdone_poll = true;
579
- mbox -> txpoll_period = 5 ;
580
- mbox -> of_xlate = zynqmp_ipi_of_xlate ;
581
- chans = devm_kzalloc (mdev , 2 * sizeof (* chans ), GFP_KERNEL );
582
- if (!chans )
583
- return - ENOMEM ;
584
- mbox -> chans = chans ;
585
- chans [IPI_MB_CHNL_TX ].con_priv = & ipi_mbox -> mchans [IPI_MB_CHNL_TX ];
586
- chans [IPI_MB_CHNL_RX ].con_priv = & ipi_mbox -> mchans [IPI_MB_CHNL_RX ];
587
- ipi_mbox -> mchans [IPI_MB_CHNL_TX ].chan_type = IPI_MB_CHNL_TX ;
588
- ipi_mbox -> mchans [IPI_MB_CHNL_RX ].chan_type = IPI_MB_CHNL_RX ;
589
- ret = devm_mbox_controller_register (mdev , mbox );
590
- if (ret )
591
- dev_err (mdev ,
592
- "Failed to register mbox_controller(%d)\n" , ret );
593
- else
594
- dev_info (mdev ,
595
- "Registered ZynqMP IPI mbox with TX/RX channels.\n" );
596
- return ret ;
636
+ return 0 ;
597
637
}
598
638
599
639
/**
@@ -624,6 +664,7 @@ static int zynqmp_ipi_probe(struct platform_device *pdev)
624
664
struct zynqmp_ipi_pdata * pdata ;
625
665
struct zynqmp_ipi_mbox * mbox ;
626
666
int num_mboxes , ret = - EINVAL ;
667
+ setup_ipi_fn ipi_fn ;
627
668
628
669
num_mboxes = of_get_available_child_count (np );
629
670
if (num_mboxes == 0 ) {
@@ -644,9 +685,18 @@ static int zynqmp_ipi_probe(struct platform_device *pdev)
644
685
return ret ;
645
686
}
646
687
688
+ ipi_fn = (setup_ipi_fn )device_get_match_data (& pdev -> dev );
689
+ if (!ipi_fn ) {
690
+ dev_err (dev ,
691
+ "Mbox Compatible String is missing IPI Setup fn.\n" );
692
+ return - ENODEV ;
693
+ }
694
+
647
695
pdata -> num_mboxes = num_mboxes ;
648
696
649
697
mbox = pdata -> ipi_mboxes ;
698
+ mbox -> setup_ipi_fn = ipi_fn ;
699
+
650
700
for_each_available_child_of_node (np , nc ) {
651
701
mbox -> pdata = pdata ;
652
702
ret = zynqmp_ipi_mbox_probe (mbox , nc );
@@ -690,7 +740,9 @@ static void zynqmp_ipi_remove(struct platform_device *pdev)
690
740
}
691
741
692
742
static const struct of_device_id zynqmp_ipi_of_match [] = {
693
- { .compatible = "xlnx,zynqmp-ipi-mailbox" },
743
+ { .compatible = "xlnx,zynqmp-ipi-mailbox" ,
744
+ .data = & zynqmp_ipi_setup ,
745
+ },
694
746
{},
695
747
};
696
748
MODULE_DEVICE_TABLE (of , zynqmp_ipi_of_match );
0 commit comments