xref: /linux/arch/loongarch/include/asm/irq.h (revision 3a39d672e7f48b8d6b91a09afa4b55352773b4b5)
10603839bSHuacai Chen /* SPDX-License-Identifier: GPL-2.0 */
20603839bSHuacai Chen /*
30603839bSHuacai Chen  * Copyright (C) 2020-2022 Loongson Technology Corporation Limited
40603839bSHuacai Chen  */
50603839bSHuacai Chen #ifndef _ASM_IRQ_H
60603839bSHuacai Chen #define _ASM_IRQ_H
70603839bSHuacai Chen 
80603839bSHuacai Chen #include <linux/irqdomain.h>
90603839bSHuacai Chen #include <linux/irqreturn.h>
100603839bSHuacai Chen 
110603839bSHuacai Chen #define IRQ_STACK_SIZE			THREAD_SIZE
120603839bSHuacai Chen #define IRQ_STACK_START			(IRQ_STACK_SIZE - 16)
130603839bSHuacai Chen 
140603839bSHuacai Chen DECLARE_PER_CPU(unsigned long, irq_stack);
150603839bSHuacai Chen 
160603839bSHuacai Chen /*
170603839bSHuacai Chen  * The highest address on the IRQ stack contains a dummy frame which is
180603839bSHuacai Chen  * structured as follows:
190603839bSHuacai Chen  *
200603839bSHuacai Chen  *   top ------------
210603839bSHuacai Chen  *       | task sp  | <- irq_stack[cpu] + IRQ_STACK_START
220603839bSHuacai Chen  *       ------------
230603839bSHuacai Chen  *       |          | <- First frame of IRQ context
240603839bSHuacai Chen  *       ------------
250603839bSHuacai Chen  *
260603839bSHuacai Chen  * task sp holds a copy of the task stack pointer where the struct pt_regs
270603839bSHuacai Chen  * from exception entry can be found.
280603839bSHuacai Chen  */
290603839bSHuacai Chen 
on_irq_stack(int cpu,unsigned long sp)300603839bSHuacai Chen static inline bool on_irq_stack(int cpu, unsigned long sp)
310603839bSHuacai Chen {
320603839bSHuacai Chen 	unsigned long low = per_cpu(irq_stack, cpu);
330603839bSHuacai Chen 	unsigned long high = low + IRQ_STACK_SIZE;
340603839bSHuacai Chen 
350603839bSHuacai Chen 	return (low <= sp && sp <= high);
360603839bSHuacai Chen }
370603839bSHuacai Chen 
380603839bSHuacai Chen void spurious_interrupt(void);
390603839bSHuacai Chen 
400603839bSHuacai Chen #define NR_IRQS_LEGACY 16
410603839bSHuacai Chen 
42843ed931SHuacai Chen /*
43843ed931SHuacai Chen  * 256 Vectors Mapping for AVECINTC:
44843ed931SHuacai Chen  *
45843ed931SHuacai Chen  * 0 - 15: Mapping classic IPs, e.g. IP0-12.
46843ed931SHuacai Chen  * 16 - 255: Mapping vectors for external IRQ.
47843ed931SHuacai Chen  *
48843ed931SHuacai Chen  */
49843ed931SHuacai Chen #define NR_VECTORS		256
50843ed931SHuacai Chen #define NR_LEGACY_VECTORS	16
51843ed931SHuacai Chen #define IRQ_MATRIX_BITS		NR_VECTORS
52843ed931SHuacai Chen 
530603839bSHuacai Chen #define arch_trigger_cpumask_backtrace arch_trigger_cpumask_backtrace
548d539b84SDouglas Anderson void arch_trigger_cpumask_backtrace(const struct cpumask *mask, int exclude_cpu);
550603839bSHuacai Chen 
560603839bSHuacai Chen #define MAX_IO_PICS 2
57843ed931SHuacai Chen #define NR_IRQS	(64 + NR_VECTORS * (NR_CPUS + MAX_IO_PICS))
580603839bSHuacai Chen 
592dfded47SJianmin Lv struct acpi_vector_group {
602dfded47SJianmin Lv 	int node;
612dfded47SJianmin Lv 	int pci_segment;
622dfded47SJianmin Lv 	struct irq_domain *parent;
632dfded47SJianmin Lv };
642dfded47SJianmin Lv extern struct acpi_vector_group pch_group[MAX_IO_PICS];
652dfded47SJianmin Lv extern struct acpi_vector_group msi_group[MAX_IO_PICS];
662dfded47SJianmin Lv 
670603839bSHuacai Chen #define CORES_PER_EIO_NODE	4
680603839bSHuacai Chen 
690603839bSHuacai Chen #define LOONGSON_CPU_UART0_VEC		10 /* CPU UART0 */
700603839bSHuacai Chen #define LOONGSON_CPU_THSENS_VEC		14 /* CPU Thsens */
710603839bSHuacai Chen #define LOONGSON_CPU_HT0_VEC		16 /* CPU HT0 irq vector base number */
720603839bSHuacai Chen #define LOONGSON_CPU_HT1_VEC		24 /* CPU HT1 irq vector base number */
730603839bSHuacai Chen 
740603839bSHuacai Chen /* IRQ number definitions */
750603839bSHuacai Chen #define LOONGSON_LPC_IRQ_BASE		0
760603839bSHuacai Chen #define LOONGSON_LPC_LAST_IRQ		(LOONGSON_LPC_IRQ_BASE + 15)
770603839bSHuacai Chen 
780603839bSHuacai Chen #define LOONGSON_CPU_IRQ_BASE		16
79843ed931SHuacai Chen #define LOONGSON_CPU_LAST_IRQ		(LOONGSON_CPU_IRQ_BASE + 15)
800603839bSHuacai Chen 
810603839bSHuacai Chen #define LOONGSON_PCH_IRQ_BASE		64
820603839bSHuacai Chen #define LOONGSON_PCH_ACPI_IRQ		(LOONGSON_PCH_IRQ_BASE + 47)
830603839bSHuacai Chen #define LOONGSON_PCH_LAST_IRQ		(LOONGSON_PCH_IRQ_BASE + 64 - 1)
840603839bSHuacai Chen 
850603839bSHuacai Chen #define LOONGSON_MSI_IRQ_BASE		(LOONGSON_PCH_IRQ_BASE + 64)
860603839bSHuacai Chen #define LOONGSON_MSI_LAST_IRQ		(LOONGSON_PCH_IRQ_BASE + 256 - 1)
870603839bSHuacai Chen 
880603839bSHuacai Chen #define GSI_MIN_LPC_IRQ		LOONGSON_LPC_IRQ_BASE
890603839bSHuacai Chen #define GSI_MAX_LPC_IRQ		(LOONGSON_LPC_IRQ_BASE + 16 - 1)
900603839bSHuacai Chen #define GSI_MIN_CPU_IRQ		LOONGSON_CPU_IRQ_BASE
910603839bSHuacai Chen #define GSI_MAX_CPU_IRQ		(LOONGSON_CPU_IRQ_BASE + 48 - 1)
920603839bSHuacai Chen #define GSI_MIN_PCH_IRQ		LOONGSON_PCH_IRQ_BASE
930603839bSHuacai Chen #define GSI_MAX_PCH_IRQ		(LOONGSON_PCH_IRQ_BASE + 256 - 1)
940603839bSHuacai Chen 
950603839bSHuacai Chen struct acpi_madt_lio_pic;
960603839bSHuacai Chen struct acpi_madt_eio_pic;
970603839bSHuacai Chen struct acpi_madt_ht_pic;
980603839bSHuacai Chen struct acpi_madt_bio_pic;
990603839bSHuacai Chen struct acpi_madt_msi_pic;
1000603839bSHuacai Chen struct acpi_madt_lpc_pic;
1010603839bSHuacai Chen 
102*ae16f05cSTianyang Zhang void complete_irq_moving(void);
103*ae16f05cSTianyang Zhang 
10402308732SHuacai Chen struct fwnode_handle *get_pch_msi_handle(int pci_segment);
1050603839bSHuacai Chen 
1060603839bSHuacai Chen extern struct acpi_madt_lio_pic *acpi_liointc;
1070603839bSHuacai Chen extern struct acpi_madt_eio_pic *acpi_eiointc[MAX_IO_PICS];
1080603839bSHuacai Chen 
1090603839bSHuacai Chen extern struct acpi_madt_ht_pic *acpi_htintc;
1100603839bSHuacai Chen extern struct acpi_madt_lpc_pic *acpi_pchlpc;
1110603839bSHuacai Chen extern struct acpi_madt_msi_pic *acpi_pchmsi[MAX_IO_PICS];
1120603839bSHuacai Chen extern struct acpi_madt_bio_pic *acpi_pchpic[MAX_IO_PICS];
1130603839bSHuacai Chen 
114b2d3e335SHuacai Chen extern struct fwnode_handle *cpuintc_handle;
1150858ed03SHuacai Chen extern struct fwnode_handle *liointc_handle;
116ee73f14eSHuacai Chen extern struct fwnode_handle *pch_lpc_handle;
117bcdd75c5SHuacai Chen extern struct fwnode_handle *pch_pic_handle[MAX_IO_PICS];
1180603839bSHuacai Chen 
get_percpu_irq(int vector)119316863cbSBibo Mao static inline int get_percpu_irq(int vector)
120316863cbSBibo Mao {
121316863cbSBibo Mao 	struct irq_domain *d;
122316863cbSBibo Mao 
123316863cbSBibo Mao 	d = irq_find_matching_fwnode(cpuintc_handle, DOMAIN_BUS_ANY);
124316863cbSBibo Mao 	if (d)
125316863cbSBibo Mao 		return irq_create_mapping(d, vector);
126316863cbSBibo Mao 
127316863cbSBibo Mao 	return -EINVAL;
128316863cbSBibo Mao }
12946859ac8SHuacai Chen 
1300603839bSHuacai Chen #include <asm-generic/irq.h>
1310603839bSHuacai Chen 
1320603839bSHuacai Chen #endif /* _ASM_IRQ_H */
133