bsp/leon3: Untangle interrupt controller support

Separate the probing of the interrupt controller from the
initialization.
This commit is contained in:
Sebastian Huber
2021-07-16 14:35:59 +02:00
parent 8fdecf6c55
commit a5f95cbb57
5 changed files with 97 additions and 21 deletions

View File

@@ -0,0 +1,83 @@
/* SPDX-License-Identifier: BSD-2-Clause */
/**
* @file
*
* @ingroup RTEMSBSPsSPARCLEON3
*
* @brief This header file provides interfaces used by the interrupt support
* implementation.
*/
/*
* Copyright (C) 2021 embedded brains GmbH & Co. KG
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef LIBBSP_SPARC_LEON3_BSP_IRQIMPL_H
#define LIBBSP_SPARC_LEON3_BSP_IRQIMPL_H
#include <rtems.h>
#include <grlib/grlib.h>
struct ambapp_dev;
#ifdef __cplusplus
extern "C" {
#endif
/**
* @addtogroup RTEMSBSPsSPARCLEON3
*
* @{
*/
/**
* @brief This lock serializes the interrupt controller access.
*/
extern rtems_interrupt_lock LEON3_IrqCtrl_Lock;
/**
* @brief This pointer provides the IRQ(A)MP register block address.
*/
extern volatile struct irqmp_regs *LEON3_IrqCtrl_Regs;
/**
* @brief This pointer provides the IRQ(A)MP device information block.
*/
extern struct ambapp_dev *LEON3_IrqCtrl_Adev;
/**
* @brief Initializes the interrupt controller for the boot processor.
*
* @param[in, out] regs is the IRQ(A)MP register block address.
*/
void leon3_ext_irq_init( volatile struct irqmp_regs *regs );
/** @} */
#ifdef __cplusplus
}
#endif
#endif /* LIBBSP_SPARC_LEON3_BSP_IRQIMPL_H */

View File

@@ -44,6 +44,7 @@
#include <rtems.h> #include <rtems.h>
#include <amba.h> #include <amba.h>
#include <bsp/irqimpl.h>
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
@@ -146,10 +147,6 @@ extern "C" {
#define LEON3_REG_CACHE_CTRL_FI 0x00200000 /* Flush instruction cache */ #define LEON3_REG_CACHE_CTRL_FI 0x00200000 /* Flush instruction cache */
#define LEON3_REG_CACHE_CTRL_DS 0x00800000 /* Data cache snooping */ #define LEON3_REG_CACHE_CTRL_DS 0x00800000 /* Data cache snooping */
/* LEON3 Interrupt Controller */
extern volatile struct irqmp_regs *LEON3_IrqCtrl_Regs;
extern struct ambapp_dev *LEON3_IrqCtrl_Adev;
/* LEON3 GP Timer */ /* LEON3 GP Timer */
extern volatile struct gptimer_regs *LEON3_Timer_Regs; extern volatile struct gptimer_regs *LEON3_Timer_Regs;
extern struct ambapp_dev *LEON3_Timer_Adev; extern struct ambapp_dev *LEON3_Timer_Adev;
@@ -193,8 +190,6 @@ static __inline__ int bsp_irq_fixup(int irq)
* store the result back are vulnerable. * store the result back are vulnerable.
*/ */
extern rtems_interrupt_lock LEON3_IrqCtrl_Lock;
#define LEON3_IRQCTRL_ACQUIRE( _lock_context ) \ #define LEON3_IRQCTRL_ACQUIRE( _lock_context ) \
rtems_interrupt_lock_acquire( &LEON3_IrqCtrl_Lock, _lock_context ) rtems_interrupt_lock_acquire( &LEON3_IrqCtrl_Lock, _lock_context )
@@ -410,9 +405,6 @@ extern int leon3_timer_core_index;
*/ */
extern unsigned int leon3_timer_prescaler; extern unsigned int leon3_timer_prescaler;
/* GRLIB extended IRQ controller register */
void leon3_ext_irq_init(void);
RTEMS_NO_RETURN void leon3_power_down_loop(void); RTEMS_NO_RETURN void leon3_power_down_loop(void);
static inline uint32_t leon3_get_cpu_count( static inline uint32_t leon3_get_cpu_count(

View File

@@ -115,9 +115,6 @@ RTEMS_SYSINIT_ITEM(
); );
#endif #endif
rtems_interrupt_lock LEON3_IrqCtrl_Lock =
RTEMS_INTERRUPT_LOCK_INITIALIZER("LEON3 IrqCtrl");
/* Pointers to Interrupt Controller configuration registers */ /* Pointers to Interrupt Controller configuration registers */
volatile struct irqmp_regs *LEON3_IrqCtrl_Regs; volatile struct irqmp_regs *LEON3_IrqCtrl_Regs;
struct ambapp_dev *LEON3_IrqCtrl_Adev; struct ambapp_dev *LEON3_IrqCtrl_Adev;
@@ -166,12 +163,6 @@ static void amba_initialize(void)
icsel = (icsel >> ((7 - (LEON3_Cpu_Index & 0x7)) * 4)) & 0xf; icsel = (icsel >> ((7 - (LEON3_Cpu_Index & 0x7)) * 4)) & 0xf;
LEON3_IrqCtrl_Regs += icsel; LEON3_IrqCtrl_Regs += icsel;
} }
LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] = 0;
LEON3_IrqCtrl_Regs->force[LEON3_Cpu_Index] = 0;
LEON3_IrqCtrl_Regs->iclear = 0xffffffff;
/* Init Extended IRQ controller if available */
leon3_ext_irq_init();
/* find GP Timer */ /* find GP Timer */
adev = (void *)ambapp_for_each(plb, (OPTIONS_ALL|OPTIONS_APB_SLVS), adev = (void *)ambapp_for_each(plb, (OPTIONS_ALL|OPTIONS_APB_SLVS),

View File

@@ -38,12 +38,19 @@
/* GRLIB extended IRQ controller IRQ number */ /* GRLIB extended IRQ controller IRQ number */
int LEON3_IrqCtrl_EIrq = -1; int LEON3_IrqCtrl_EIrq = -1;
rtems_interrupt_lock LEON3_IrqCtrl_Lock =
RTEMS_INTERRUPT_LOCK_INITIALIZER("LEON3 IrqCtrl");
/* Initialize Extended Interrupt controller */ /* Initialize Extended Interrupt controller */
void leon3_ext_irq_init(void) void leon3_ext_irq_init(volatile struct irqmp_regs *regs)
{ {
if ( (LEON3_IrqCtrl_Regs->mpstat >> 16) & 0xf ) { regs->mask[LEON3_Cpu_Index] = 0;
regs->force[LEON3_Cpu_Index] = 0;
regs->iclear = 0xffffffff;
if ( (regs->mpstat >> 16) & 0xf ) {
/* Extended IRQ controller available */ /* Extended IRQ controller available */
LEON3_IrqCtrl_EIrq = (LEON3_IrqCtrl_Regs->mpstat >> 16) & 0xf; LEON3_IrqCtrl_EIrq = (regs->mpstat >> 16) & 0xf;
} }
} }
@@ -76,6 +83,8 @@ void bsp_interrupt_facility_initialize(void)
leon3_interrupt_affinities[i] = affinity; leon3_interrupt_affinities[i] = affinity;
} }
#endif #endif
leon3_ext_irq_init(LEON3_IrqCtrl_Regs);
} }
rtems_status_code bsp_interrupt_get_attributes( rtems_status_code bsp_interrupt_get_attributes(

View File

@@ -16,6 +16,7 @@ install:
- destination: ${BSP_INCLUDEDIR}/bsp - destination: ${BSP_INCLUDEDIR}/bsp
source: source:
- bsps/sparc/leon3/include/bsp/irq.h - bsps/sparc/leon3/include/bsp/irq.h
- bsps/sparc/leon3/include/bsp/irqimpl.h
- bsps/sparc/leon3/include/bsp/watchdog.h - bsps/sparc/leon3/include/bsp/watchdog.h
- destination: ${BSP_LIBDIR} - destination: ${BSP_LIBDIR}
source: source: