summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSebastian Huber <sebastian.huber@embedded-brains.de>2014-02-18 12:42:58 +0100
committerSebastian Huber <sebastian.huber@embedded-brains.de>2014-02-19 10:25:47 +0100
commit2cb0877f3a90693b60a8e2b1576c29a0ce91b112 (patch)
tree7a4da096ad6ef725462a1ab5a98920d9b1bfa51e
parentscore: _SMP_Inter_processor_interrupt_handler() (diff)
downloadrtems-2cb0877f3a90693b60a8e2b1576c29a0ce91b112.tar.bz2
bsp/leon3: Add and use LEON3_IrqCtrl_Lock
Disabling of interrupts is not enough to ensure mutual exclusion on SMP configurations.
-rw-r--r--c/src/lib/libbsp/sparc/leon3/amba/amba.c2
-rw-r--r--c/src/lib/libbsp/sparc/leon3/include/leon.h34
2 files changed, 23 insertions, 13 deletions
diff --git a/c/src/lib/libbsp/sparc/leon3/amba/amba.c b/c/src/lib/libbsp/sparc/leon3/amba/amba.c
index 8873ae9ee0..5cb1880ac5 100644
--- a/c/src/lib/libbsp/sparc/leon3/amba/amba.c
+++ b/c/src/lib/libbsp/sparc/leon3/amba/amba.c
@@ -23,6 +23,8 @@
*/
struct ambapp_bus ambapp_plb;
+rtems_interrupt_lock LEON3_IrqCtrl_Lock = RTEMS_INTERRUPT_LOCK_INITIALIZER;
+
/* Pointers to Interrupt Controller configuration registers */
volatile struct irqmp_regs *LEON3_IrqCtrl_Regs;
diff --git a/c/src/lib/libbsp/sparc/leon3/include/leon.h b/c/src/lib/libbsp/sparc/leon3/include/leon.h
index 4ebb043455..ebd0f907e2 100644
--- a/c/src/lib/libbsp/sparc/leon3/include/leon.h
+++ b/c/src/lib/libbsp/sparc/leon3/include/leon.h
@@ -23,7 +23,7 @@
#ifndef _INCLUDE_LEON_h
#define _INCLUDE_LEON_h
-#include <rtems/score/sparc.h>
+#include <rtems.h>
#include <amba.h>
#ifdef __cplusplus
@@ -167,6 +167,14 @@ static __inline__ int bsp_irq_fixup(int irq)
* store the result back are vulnerable.
*/
+extern rtems_interrupt_lock LEON3_IrqCtrl_Lock;
+
+#define LEON3_IRQCTRL_ACQUIRE(_level ) \
+ rtems_interrupt_lock_acquire( &LEON3_IrqCtrl_Lock, _level )
+
+#define LEON3_IRQCTRL_RELEASE(_level ) \
+ rtems_interrupt_lock_release( &LEON3_IrqCtrl_Lock, _level )
+
#define LEON_Clear_interrupt( _source ) \
do { \
LEON3_IrqCtrl_Regs->iclear = (1 << (_source)); \
@@ -187,39 +195,39 @@ static __inline__ int bsp_irq_fixup(int irq)
#define LEON_Mask_interrupt( _source ) \
do { \
- uint32_t _level; \
- _level = sparc_disable_interrupts(); \
+ rtems_interrupt_level _level; \
+ LEON3_IRQCTRL_ACQUIRE( _level ); \
LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] &= ~(1 << (_source)); \
- sparc_enable_interrupts( _level ); \
+ LEON3_IRQCTRL_RELEASE( _level ); \
} while (0)
#define LEON_Unmask_interrupt( _source ) \
do { \
- uint32_t _level; \
- _level = sparc_disable_interrupts(); \
+ rtems_interrupt_level _level; \
+ LEON3_IRQCTRL_ACQUIRE( _level ); \
LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] |= (1 << (_source)); \
- sparc_enable_interrupts( _level ); \
+ LEON3_IRQCTRL_RELEASE( _level ); \
} while (0)
#define LEON_Disable_interrupt( _source, _previous ) \
do { \
- uint32_t _level; \
+ rtems_interrupt_level _level; \
uint32_t _mask = 1 << (_source); \
- _level = sparc_disable_interrupts(); \
+ LEON3_IRQCTRL_ACQUIRE( _level ); \
(_previous) = LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index]; \
LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] = _previous & ~_mask; \
- sparc_enable_interrupts( _level ); \
+ LEON3_IRQCTRL_RELEASE( _level ); \
(_previous) &= _mask; \
} while (0)
#define LEON_Restore_interrupt( _source, _previous ) \
do { \
- uint32_t _level; \
+ rtems_interrupt_level _level; \
uint32_t _mask = 1 << (_source); \
- _level = sparc_disable_interrupts(); \
+ LEON3_IRQCTRL_ACQUIRE( _level ); \
LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] = \
(LEON3_IrqCtrl_Regs->mask[LEON3_Cpu_Index] & ~_mask) | (_previous); \
- sparc_enable_interrupts( _level ); \
+ LEON3_IRQCTRL_RELEASE( _level ); \
} while (0)
/* Make all SPARC BSPs have common macros for interrupt handling */