mirror of
https://github.com/xen-project/xen.git
synced 2026-10-28 02:01:24 +01:00
xen/riscv: introduce intc_init() and helpers
Introduce intc_init() to initialize the interrupt controller using the registered hardware ops. Also add intc_route_irq_to_xen() to route IRQs to Xen, with support for setting IRQ type and priority via new internal helpers intc_set_irq_type() and intc_set_irq_priority(). Call intc_init() to do basic initialization steps for APLIC and IMSIC. Co-developed-by: Romain Caritey <Romain.Caritey@microchip.com> Signed-off-by: Oleksii Kurochko <oleksii.kurochko@gmail.com> Acked-by: Jan Beulich <jbeulich@suse.com>
This commit is contained in:
1 parent
028e41d1f3
commit
8b5887d8cd
3 files changed
+47
No files matched your search
@@ -43,4 +43,8 @@ void intc_preinit(void);
|
||||
|
||||
void register_intc_ops(const struct intc_hw_operations *ops);
|
||||
|
||||
void intc_init(void);
|
||||
|
||||
void intc_route_irq_to_xen(struct irq_desc *desc, unsigned int priority);
|
||||
|
||||
#endif /* ASM__RISCV__INTERRUPT_CONTOLLER_H */
|
||||
@@ -1,9 +1,12 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
|
||||
#include <xen/acpi.h>
|
||||
#include <xen/bug.h>
|
||||
#include <xen/device_tree.h>
|
||||
#include <xen/init.h>
|
||||
#include <xen/irq.h>
|
||||
#include <xen/lib.h>
|
||||
#include <xen/spinlock.h>
|
||||
|
||||
#include <asm/intc.h>
|
||||
|
||||
@@ -21,3 +24,41 @@ void __init intc_preinit(void)
|
||||
else
|
||||
panic("ACPI interrupt controller preinit() isn't implemented\n");
|
||||
}
|
||||
|
||||
void __init intc_init(void)
|
||||
{
|
||||
if ( intc_hw_ops->init() )
|
||||
panic("Failed to initialize the interrupt controller drivers\n");
|
||||
}
|
||||
|
||||
/* desc->irq needs to be disabled before calling this function */
|
||||
static void intc_set_irq_type(struct irq_desc *desc, unsigned int type)
|
||||
{
|
||||
ASSERT(desc->status & IRQ_DISABLED);
|
||||
ASSERT(spin_is_locked(&desc->lock));
|
||||
ASSERT(type != IRQ_TYPE_INVALID);
|
||||
|
||||
if ( intc_hw_ops->set_irq_type )
|
||||
intc_hw_ops->set_irq_type(desc, type);
|
||||
}
|
||||
|
||||
static void intc_set_irq_priority(struct irq_desc *desc, unsigned int priority)
|
||||
{
|
||||
ASSERT(spin_is_locked(&desc->lock));
|
||||
|
||||
if ( intc_hw_ops->set_irq_priority )
|
||||
intc_hw_ops->set_irq_priority(desc, priority);
|
||||
}
|
||||
|
||||
void intc_route_irq_to_xen(struct irq_desc *desc, unsigned int priority)
|
||||
{
|
||||
ASSERT(desc->status & IRQ_DISABLED);
|
||||
ASSERT(spin_is_locked(&desc->lock));
|
||||
/* Can't route interrupts that don't exist */
|
||||
ASSERT(intc_hw_ops && desc->irq < intc_hw_ops->info->num_irqs);
|
||||
|
||||
desc->handler = intc_hw_ops->host_irq_type;
|
||||
|
||||
intc_set_irq_type(desc, desc->arch.type);
|
||||
intc_set_irq_priority(desc, priority);
|
||||
}
|
||||
@@ -134,6 +134,8 @@ void __init noreturn start_xen(unsigned long bootcpu_id,
|
||||
|
||||
intc_preinit();
|
||||
|
||||
intc_init();
|
||||
|
||||
printk("All set up\n");
|
||||
|
||||
machine_halt();
|
||||
|
||||