6767#define OFFSET_ADR_INT_CONFIG 0x1580UL /* PINTC version >= 2 */
6868#define OFFSET_DEVINTWK_INTEN 0x1600UL
6969
70- #define SW_PINTC_MCU_GSI_BASE 64
70+ #define PINTC_GSI_BASE ( node ) (64 + 512 * (node))
7171
7272#define INTPU_BASE_V1 0x802a00000000
7373#define INTPU_SIZE_V1 0x1680
7474
7575#define MCU_BASE_V1 0x803000000000
7676#define MCU_SIZE_V1 0x8f00
7777
78+ #define SUNWAY_MAX_NODES 8
79+
7880DECLARE_PER_CPU (unsigned long, hard_node_id );
7981
8082struct pintc_chip_data {
@@ -89,13 +91,13 @@ struct pintc_chip_data {
8991 raw_spinlock_t mcu_lock ;
9092};
9193
92- static struct pintc_chip_data * chip_datas [MAX_NUMNODES ];
94+ static struct pintc_chip_data * chip_datas [SUNWAY_MAX_NODES ];
9395
9496static struct pintc_chip_data * pintc_alloc_chip_data (u32 node )
9597{
9698 struct pintc_chip_data * chip_data ;
9799
98- if (WARN_ON (node >= MAX_NUMNODES ))
100+ if (WARN_ON (node >= SUNWAY_MAX_NODES ))
99101 return NULL ;
100102
101103 chip_data = kzalloc_node (sizeof (struct pintc_chip_data ),
@@ -111,7 +113,7 @@ static void pintc_free_chip_data(struct pintc_chip_data *chip_data)
111113 if (!chip_data )
112114 return ;
113115
114- if (WARN_ON ((chip_data -> node >= MAX_NUMNODES ) ||
116+ if (WARN_ON ((chip_data -> node >= SUNWAY_MAX_NODES ) ||
115117 (chip_datas [chip_data -> node ] != chip_data )))
116118 return ;
117119
@@ -285,13 +287,14 @@ static int mcu_irq_set_affinity(struct irq_data *irq_data,
285287 return assign_mcu_irq_config (chip_data , & targets );
286288}
287289
288- static struct irq_chip pintc_mcu_chip = {
289- .name = "MCU-INT" ,
290- .irq_enable = mcu_irq_enable ,
291- .irq_disable = mcu_irq_disable ,
292- .irq_mask = mcu_irq_disable ,
293- .irq_unmask = mcu_irq_enable ,
294- .irq_set_affinity = mcu_irq_set_affinity ,
290+ static struct irq_chip pintc_mcu_chips [SUNWAY_MAX_NODES ] = {
291+ [0 ... SUNWAY_MAX_NODES - 1 ] = {
292+ .irq_enable = mcu_irq_enable ,
293+ .irq_disable = mcu_irq_disable ,
294+ .irq_mask = mcu_irq_disable ,
295+ .irq_unmask = mcu_irq_enable ,
296+ .irq_set_affinity = mcu_irq_set_affinity ,
297+ }
295298};
296299
297300static struct irq_chip pintc_mcu_vt_chip = {
@@ -303,6 +306,9 @@ static int pintc_mcu_translate(struct irq_domain *domain,
303306 unsigned long * hwirq ,
304307 unsigned int * type )
305308{
309+ struct pintc_chip_data * chip_data = domain -> host_data ;
310+ u32 node = chip_data -> node ;
311+
306312 if (WARN_ON (fwspec -> param_count < 1 ))
307313 return - EINVAL ;
308314
@@ -315,9 +321,9 @@ static int pintc_mcu_translate(struct irq_domain *domain,
315321
316322 /* ACPI */
317323 if (is_fwnode_irqchip (fwspec -> fwnode )) {
318- if (WARN_ON (fwspec -> param [0 ] < SW_PINTC_MCU_GSI_BASE ))
324+ if (WARN_ON (fwspec -> param [0 ] < PINTC_GSI_BASE ( node ) ))
319325 return - EINVAL ;
320- * hwirq = fwspec -> param [0 ] - SW_PINTC_MCU_GSI_BASE ;
326+ * hwirq = fwspec -> param [0 ] - PINTC_GSI_BASE ( node ) ;
321327 * type = IRQ_TYPE_NONE ;
322328 return 0 ;
323329 }
@@ -376,13 +382,14 @@ static const struct irq_domain_ops pintc_mcu_domain_ops = {
376382 .free = pintc_mcu_free_irqs ,
377383};
378384
379- struct irq_domain * mcu_irq_domain ;
380- EXPORT_SYMBOL (mcu_irq_domain );
385+ static struct irq_domain * mcu_domains [SUNWAY_MAX_NODES ];
381386
382387static int __init pintc_init_mcu (struct pintc_chip_data * chip_data ,
383388 struct fwnode_handle * handle )
384389{
385390 unsigned int mcu_irq_num = chip_data -> mcu_irq_num ;
391+ u32 node = chip_data -> node ;
392+ char * chip_name ;
386393
387394 if (chip_data -> vt ) {
388395 chip_data -> mcu_chip = & pintc_mcu_vt_chip ;
@@ -392,25 +399,37 @@ static int __init pintc_init_mcu(struct pintc_chip_data *chip_data,
392399 * "irq_domain_create_legacy", we have to call
393400 * "__irq_domain_add" directly.
394401 */
395- mcu_irq_domain = __irq_domain_add (handle , mcu_irq_num ,
402+ mcu_domains [ node ] = __irq_domain_add (handle , mcu_irq_num ,
396403 mcu_irq_num , 0 , & pintc_mcu_domain_ops ,
397404 chip_data );
398- if (mcu_irq_domain )
399- irq_domain_associate_many (mcu_irq_domain ,
405+ if (mcu_domains [ node ] )
406+ irq_domain_associate_many (mcu_domains [ node ] ,
400407 0 , 0 , mcu_irq_num );
401408 } else {
402- chip_data -> mcu_chip = & pintc_mcu_chip ;
403- mcu_irq_domain = irq_domain_create_linear (handle , mcu_irq_num ,
409+ chip_data -> mcu_chip = & pintc_mcu_chips [node ];
410+
411+ chip_name = kzalloc_node (sizeof ("MCUX-INT" ), GFP_KERNEL , node );
412+ if (!chip_name )
413+ return - ENOMEM ;
414+
415+ snprintf (chip_name , sizeof ("MCUX-INT" ), "MCU%u-INT" , node );
416+ chip_data -> mcu_chip -> name = chip_name ;
417+
418+ mcu_domains [node ] = irq_domain_create_linear (handle , mcu_irq_num ,
404419 & pintc_mcu_domain_ops , chip_data );
420+
405421 /* Mask all interrupts for now */
406422 writeq (0x0 , chip_data -> mcu_base + OFFSET_MCU_DVC_INT_EN );
407423
408- /* When building the root domain, move it to a better location */
409- if (mcu_irq_domain )
424+ if (mcu_domains [node ])
410425 pintc_mcu_enable (chip_data -> pintc_base );
426+ else {
427+ chip_data -> mcu_chip -> name = NULL ;
428+ kfree (chip_name );
429+ }
411430 }
412431
413- if (!mcu_irq_domain ) {
432+ if (!mcu_domains [ node ] ) {
414433 pr_err ("failed to create MCU irq domain\n" );
415434 return - ENOMEM ;
416435 }
@@ -424,24 +443,24 @@ static int __init pintc_init_mcu(struct pintc_chip_data *chip_data,
424443 return 0 ;
425444}
426445
427- /* Currently, only MCU controller on node 0 is supported */
428446void handle_dev_int (struct pt_regs * regs )
429447{
430448 unsigned long stat , val ;
431449 unsigned int hwirq ;
450+ u32 node = __this_cpu_read (hard_node_id );
432451
433452 /* Disable global irq of MCU due to some hardware reasons */
434- val = pintc_mcu_disable_and_save (chip_datas [0 ]);
453+ val = pintc_mcu_disable_and_save (chip_datas [node ]);
435454
436- stat = readq (chip_datas [0 ]-> mcu_base + OFFSET_MCU_DVC_INT );
455+ stat = readq (chip_datas [node ]-> mcu_base + OFFSET_MCU_DVC_INT );
437456
438457 while (stat ) {
439458 hwirq = ffs (stat ) - 1 ;
440- generic_handle_domain_irq (mcu_irq_domain , hwirq );
459+ generic_handle_domain_irq (mcu_domains [ node ] , hwirq );
441460 stat &= ~(1UL << hwirq );
442461 }
443462
444- pintc_mcu_restore (chip_datas [0 ], val );
463+ pintc_mcu_restore (chip_datas [node ], val );
445464}
446465
447466void handle_fault_int (void )
@@ -487,13 +506,6 @@ void handle_fault_int(void)
487506static int __init pintc_of_init_mcu (struct pintc_chip_data * chip_data ,
488507 struct device_node * pintc )
489508{
490- /* Not yet supported */
491- if (chip_data -> node > 0 ) {
492- pr_info ("MCU version [%u] on node [%u] skipped\n" ,
493- chip_data -> version , chip_data -> node );
494- return 0 ;
495- }
496-
497509 return pintc_init_mcu (chip_data , of_node_to_fwnode (pintc ));
498510}
499511
@@ -608,6 +620,7 @@ enum sw_pintc_sub_type {
608620static int __init lpc_intc_parse_madt (union acpi_subtable_headers * header ,
609621 const unsigned long end )
610622{
623+ static bool initialized [SUNWAY_MAX_NODES ];
611624 struct acpi_madt_sw_lpc_intc * lpc_intc ;
612625
613626 lpc_intc = (struct acpi_madt_sw_lpc_intc * )header ;
@@ -616,13 +629,22 @@ static int __init lpc_intc_parse_madt(union acpi_subtable_headers *header,
616629 if (lpc_intc -> node > 0 )
617630 return 0 ;
618631
632+ if (initialized [lpc_intc -> node ])
633+ return 0 ;
634+
635+ /* LPC controller is the child of MCU controller */
636+ if (!mcu_domains [lpc_intc -> node ])
637+ return 0 ;
638+
619639 if ((lpc_intc -> version == ACPI_MADT_SW_LPC_INTC_VERSION_NONE ) ||
620640 (lpc_intc -> version >= ACPI_MADT_SW_LPC_INTC_VERSION_RESERVED )) {
621641 pr_err ("invalid LPC-INTC version\n" );
622642 return - EINVAL ;
623643 }
624644
625- return lpc_intc_acpi_init (mcu_irq_domain , lpc_intc );
645+ initialized [lpc_intc -> node ] = true;
646+
647+ return lpc_intc_acpi_init (mcu_domains [lpc_intc -> node ], lpc_intc );
626648}
627649
628650static bool __init
@@ -642,22 +664,16 @@ static int __init pintc_acpi_init_mcu(struct pintc_chip_data *chip_data,
642664 struct acpi_madt_sw_sub_pintc * mcu )
643665{
644666 struct fwnode_handle * handle ;
667+ u32 node = chip_data -> node ;
645668 int ret ;
646669
647- /* Not yet supported */
648- if (chip_data -> node > 0 ) {
649- pr_info ("MCU version [%u] on node [%u] skipped\n" ,
650- chip_data -> version , chip_data -> node );
651- return 0 ;
652- }
653-
654670 if (!mcu -> status ) {
655671 pr_info ("MCU version [%u] on node [%u] disabled\n" ,
656672 chip_data -> version , chip_data -> node );
657673 return 0 ;
658674 }
659675
660- if (mcu -> gsi_base != SW_PINTC_MCU_GSI_BASE ) {
676+ if (mcu -> gsi_base != PINTC_GSI_BASE ( node ) ) {
661677 pr_err ("invalid MCU GSI\n" );
662678 return - EINVAL ;
663679 }
@@ -694,7 +710,7 @@ static int __init pintc_acpi_init_mcu(struct pintc_chip_data *chip_data,
694710 return 0 ;
695711
696712out_acpi_free_mcu_domain :
697- irq_domain_remove (mcu_irq_domain );
713+ irq_domain_remove (mcu_domains [ node ] );
698714out_acpi_unmap_mcu :
699715 iounmap (chip_data -> mcu_base );
700716out_acpi_free_fwnode :
0 commit comments