lkml.org 
[lkml]   [2022]   [Jul]   [15]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH V15 12/15] LoongArch: prepare to support multiple pch-pic and pch-msi irqdomain
    Date
    For systems with two chipsets, there are two related pch-pic and
    pch-msi irqdomains, each of which has the same node id as its
    parent irqdomain. So we use a structure to mantain the relation
    of node and it's parent irqdomain as pch irqdomin, the 'pci_segment'
    field is only used to match the pci segment of a pci device when
    setting msi irqdomain for the device.

    struct acpi_vector_group {
    int node;
    int pci_segment;
    struct irq_domain *parent;
    };

    The field 'pci_segment' and 'node' are initialized from MCFG, and
    the parent irqdomain driver will set field 'parent' by matching same
    'node'.

    Signed-off-by: Jianmin Lv <lvjianmin@loongson.cn>
    ---
    arch/loongarch/include/asm/irq.h | 8 ++++++++
    arch/loongarch/kernel/irq.c | 38 ++++++++++++++++++++++++++++++++++++++
    2 files changed, 46 insertions(+)

    diff --git a/arch/loongarch/include/asm/irq.h b/arch/loongarch/include/asm/irq.h
    index b4c7956..a07315a 100644
    --- a/arch/loongarch/include/asm/irq.h
    +++ b/arch/loongarch/include/asm/irq.h
    @@ -48,6 +48,14 @@ static inline bool on_irq_stack(int cpu, unsigned long sp)
    #define MAX_IO_PICS 2
    #define NR_IRQS (64 + (256 * MAX_IO_PICS))

    +struct acpi_vector_group {
    + int node;
    + int pci_segment;
    + struct irq_domain *parent;
    +};
    +extern struct acpi_vector_group pch_group[MAX_IO_PICS];
    +extern struct acpi_vector_group msi_group[MAX_IO_PICS];
    +
    #define CORES_PER_EIO_NODE 4

    #define LOONGSON_CPU_UART0_VEC 10 /* CPU UART0 */
    diff --git a/arch/loongarch/kernel/irq.c b/arch/loongarch/kernel/irq.c
    index b04201c..06f2a15 100644
    --- a/arch/loongarch/kernel/irq.c
    +++ b/arch/loongarch/kernel/irq.c
    @@ -26,6 +26,8 @@
    EXPORT_PER_CPU_SYMBOL(irq_stat);

    struct irq_domain *cpu_domain;
    +struct acpi_vector_group pch_group[MAX_IO_PICS];
    +struct acpi_vector_group msi_group[MAX_IO_PICS];

    /*
    * 'what should we do if we get a hw irq event on an illegal vector'.
    @@ -52,6 +54,41 @@ int arch_show_interrupts(struct seq_file *p, int prec)
    return 0;
    }

    +static int __init early_pci_mcfg_parse(struct acpi_table_header *header)
    +{
    + struct acpi_table_mcfg *mcfg;
    + struct acpi_mcfg_allocation *mptr;
    + int i, n;
    +
    + if (header->length < sizeof(struct acpi_table_mcfg))
    + return -EINVAL;
    +
    + n = (header->length - sizeof(struct acpi_table_mcfg)) /
    + sizeof(struct acpi_mcfg_allocation);
    + mcfg = (struct acpi_table_mcfg *)header;
    + mptr = (struct acpi_mcfg_allocation *) &mcfg[1];
    +
    + for (i = 0; i < n; i++, mptr++) {
    + msi_group[i].pci_segment = mptr->pci_segment;
    + pch_group[i].node = msi_group[i].node = (mptr->address >> 44) & 0xf;
    + }
    +
    + return 0;
    +}
    +
    +static void __init init_vec_parent_group(void)
    +{
    + int i;
    +
    + for (i = 0; i < MAX_IO_PICS; i++) {
    + msi_group[i].pci_segment = -1;
    + msi_group[i].node = -1;
    + pch_group[i].node = -1;
    + }
    +
    + acpi_table_parse(ACPI_SIG_MCFG, early_pci_mcfg_parse);
    +}
    +
    void __init init_IRQ(void)
    {
    int i;
    @@ -65,6 +102,7 @@ void __init init_IRQ(void)
    clear_csr_ecfg(ECFG0_IM);
    clear_csr_estat(ESTATF_IP);

    + init_vec_parent_group();
    irqchip_init();
    #ifdef CONFIG_SMP
    ipi_irq = EXCCODE_IPI - EXCCODE_INT_START;
    --
    1.8.3.1
    \
     
     \ /
      Last update: 2022-07-15 09:07    [W:3.811 / U:0.004 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site