2007-12-11 Till Straumann <strauman@slac.stanford.edu>

* Makefile.am, irq/irq.c, irq/irq.h, irq/irq_init.c:
	use new exception/irq support from
	libcpu/powerpc/new-exceptions/bspsupport
	rather than borrowing from ../shared/vectors ../shared/irq
This commit is contained in:
Till Straumann
2007-12-12 01:16:34 +00:00
parent 85982c6846
commit 0296f51827
6 changed files with 86 additions and 276 deletions

View File

@@ -1,3 +1,10 @@
2007-12-11 Till Straumann <strauman@slac.stanford.edu>
* Makefile.am, irq/irq.c, irq/irq.h, irq/irq_init.c:
use new exception/irq support from
libcpu/powerpc/new-exceptions/bspsupport
rather than borrowing from ../shared/vectors ../shared/irq
2007-12-11 Joel Sherrill <joel.sherrill@OARcorp.com>
* include/bsp.h, startup/bspstart.c: Eliminate copies of the

View File

@@ -69,8 +69,7 @@ pci_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += irq/irq.h
noinst_PROGRAMS += irq.rel
irq_rel_SOURCES = irq/irq_init.c irq/irq.c \
../../powerpc/shared/irq/irq_asm.S
irq_rel_SOURCES = irq/irq_init.c irq/irq.c
irq_rel_CPPFLAGS = $(AM_CPPFLAGS)
irq_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
@@ -83,12 +82,17 @@ tod_rel_CPPFLAGS = $(AM_CPPFLAGS)
tod_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
##
include_bsp_HEADERS += ../../powerpc/shared/vectors/vectors.h \
include_bsp_HEADERS += \
vectors/bspException.h
include_bsp_HEADERS += \
../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/vectors.h \
../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/irq_supp.h \
../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/ppc_exc_bspsupp.h
noinst_PROGRAMS += vectors.rel
vectors_rel_SOURCES = ../../powerpc/shared/vectors/vectors_init.c \
vectors/exceptionhandler.c ../../powerpc/shared/vectors/vectors.S \
vectors_rel_SOURCES = \
vectors/exceptionhandler.c \
../../powerpc/shared/start/vectors_entry.S
vectors_rel_CPPFLAGS = $(AM_CPPFLAGS)
vectors_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
@@ -158,6 +162,8 @@ libbsp_a_LIBADD += ../../../libcpu/@RTEMS_CPU@/shared/cpuIdent.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/rtems-cpu.rel \
../../../libcpu/@RTEMS_CPU@/mpc6xx/clock.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/raw_exception.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/exc_bspsupport.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/irq_bspsupport.rel \
../../../libcpu/@RTEMS_CPU@/mpc6xx/mmu.rel \
../../../libcpu/@RTEMS_CPU@/mpc6xx/timer.rel

View File

@@ -43,20 +43,6 @@
#define EDGE_TRIGGER
#define _MSR_GET( _mask) \
do { \
RTEMS_COMPILER_MEMORY_BARRIER(); \
_CPU_MSR_GET( _mask); \
RTEMS_COMPILER_MEMORY_BARRIER(); \
} while (0);
#define _MSR_SET( _mask) \
do { \
RTEMS_COMPILER_MEMORY_BARRIER(); \
_CPU_MSR_SET( _mask); \
RTEMS_COMPILER_MEMORY_BARRIER(); \
} while (0);
/* #define DEBUG_IRQ*/
/*
@@ -69,17 +55,19 @@
*/
static unsigned int BSP_irq_prio_mask_tbl[3][BSP_PIC_IRQ_NUMBER];
/*
* default handler connected on each irq after bsp initialization
*/
static rtems_irq_connect_data default_rtems_entry;
/*
* location used to store initial tables used for interrupt
* management.
*/
static rtems_irq_global_settings* internal_config;
/* handler table (cached copy ) */
static rtems_irq_connect_data* rtems_hdl_tbl;
/*
* default handler connected on each irq after bsp initialization
* (locally cached copy)
*/
void (*default_rtems_hdl)(rtems_irq_hdl_param) = (void(*)(rtems_irq_hdl_param)) -1;
static volatile unsigned *BSP_irqMask_reg[3];
static volatile unsigned *BSP_irqCause_reg[3];
@@ -162,7 +150,7 @@ static inline unsigned int modIrq32(unsigned irq)
* is already set and that the tables it contains are still valid
* and accessible.
*/
static void compute_pic_masks_from_prio()
static void compute_pic_masks_from_prio(rtems_irq_global_settings *config)
{
int i,j, k;
unsigned long long irq_prio_mask=0;
@@ -192,7 +180,7 @@ static void compute_pic_masks_from_prio()
* Mask interrupts at PIC level that have a lower priority
* or <Till Straumann> a equal priority.
*/
if (internal_config->irqPrioTbl [i] >= internal_config->irqPrioTbl [j])
if (config->irqPrioTbl [i] >= config->irqPrioTbl [j])
irq_prio_mask |= (unsigned long long)(1LLU << j);
}
@@ -207,7 +195,7 @@ static void compute_pic_masks_from_prio()
BSP_irq_prio_mask_tbl[2][i] = 1<<i;
/* Compute for the GPP priority interrupt mask */
for (j=BSP_GPP_IRQ_LOWEST_OFFSET; j <BSP_PROCESSOR_IRQ_LOWEST_OFFSET; j++) {
if (internal_config->irqPrioTbl [i] >= internal_config->irqPrioTbl [j])
if (config->irqPrioTbl [i] >= config->irqPrioTbl [j])
BSP_irq_prio_mask_tbl[2][i] |= 1 << (j-BSP_GPP_IRQ_LOWEST_OFFSET);
}
}
@@ -303,6 +291,9 @@ void BSP_enable_pic_irq(const rtems_irq_number irqNum)
unsigned bitNum, regNum;
unsigned int level;
if ( !is_pic_irq(irqNum) )
return;
bitNum = modIrq32(((unsigned int)irqNum) - BSP_MICL_IRQ_LOWEST_OFFSET);
regNum = divIrq32(((unsigned int)irqNum) - BSP_MICL_IRQ_LOWEST_OFFSET);
@@ -317,29 +308,52 @@ void BSP_enable_pic_irq(const rtems_irq_number irqNum)
rtems_interrupt_enable(level);
}
void BSP_disable_pic_irq(const rtems_irq_number irqNum)
void BSP_enable_irq_at_pic(const rtems_irq_number irqNum)
{
BSP_enable_pic_irq(irqNum);
}
int BSP_disable_irq_at_pic(const rtems_irq_number irqNum)
{
int rval;
unsigned bitNum, regNum;
unsigned int level;
if ( ! is_pic_irq(irqNum) )
return -1;
bitNum = modIrq32(((unsigned int)irqNum) - BSP_MICL_IRQ_LOWEST_OFFSET);
regNum = divIrq32(((unsigned int)irqNum) - BSP_MICL_IRQ_LOWEST_OFFSET);
rtems_interrupt_disable(level);
CleanMainIrqTbl((int) irqNum);
rval = BSP_irqMask_cache[regNum] & (1<<bitNum);
BSP_irqMask_cache[regNum] &= ~(1 << bitNum);
out_le32(BSP_irqMask_reg[regNum], BSP_irqMask_cache[regNum]);
while (in_le32(BSP_irqMask_reg[regNum]) != BSP_irqMask_cache[regNum]);
rtems_interrupt_enable(level);
return rval ? 1 : 0;
}
int BSP_setup_the_pic() /* adapt the same name as shared/irq */
void BSP_disable_pic_irq(const rtems_irq_number irqNum)
{
(void)BSP_disable_irq_at_pic(irqNum);
}
int BSP_setup_the_pic(rtems_irq_global_settings *config) /* adapt the same name as shared/irq */
{
int i;
internal_config = config;
default_rtems_hdl = config->defaultEntry.hdl;
rtems_hdl_tbl = config->irqHdlTbl;
/* Get ready for discovery BSP */
BSP_irqMask_reg[0]= (volatile unsigned int *) (GT64260_REG_BASE + GT_CPU_INT_MASK_LO);
BSP_irqMask_reg[1]= (volatile unsigned int *) (GT64260_REG_BASE + GT_CPU_INT_MASK_HI);
@@ -380,7 +394,7 @@ int BSP_setup_the_pic() /* adapt the same name as shared/irq */
out_le32(BSP_irqMask_reg[i], 0);
}
in_le32(BSP_irqMask_reg[2]);
compute_pic_masks_from_prio();
compute_pic_masks_from_prio(config);
#if 0
printk("BSP_irqMask_reg[0] = 0x%x, BSP_irqCause_reg[0] 0x%x\n",
@@ -394,22 +408,6 @@ int BSP_setup_the_pic() /* adapt the same name as shared/irq */
in_le32(BSP_irqCause_reg[2]));
#endif
/*
*
*/
for (i=BSP_MICL_IRQ_LOWEST_OFFSET; i < BSP_PROCESSOR_IRQ_LOWEST_OFFSET ; i++) {
if (rtems_hdl_tbl[i].hdl != default_rtems_entry.hdl) {
BSP_enable_pic_irq(i);
if (rtems_hdl_tbl[i].on)
rtems_hdl_tbl[i].on(&rtems_hdl_tbl[i]);
}
else {
if (rtems_hdl_tbl[i].off)
rtems_hdl_tbl[i].off(&rtems_hdl_tbl[i]);
BSP_disable_pic_irq(i);
}
}
return(1);
}
@@ -418,190 +416,21 @@ int BSP_setup_the_pic() /* adapt the same name as shared/irq */
* is valid.
*/
static int isValidInterrupt(int irq)
{
if ( (irq < BSP_LOWEST_OFFSET) || (irq > BSP_MAX_OFFSET))
return 0;
return 1;
}
/*
* ------------------------ RTEMS Single Irq Handler Mngt Routines ----------------
*/
int BSP_install_rtems_irq_handler (const rtems_irq_connect_data* irq)
{
unsigned int level;
if (!isValidInterrupt(irq->name)) {
printk("Invalid interrupt vector %d\n",irq->name);
return 0;
}
/*
* Check if default handler is actually connected. If not issue an error.
* You must first get the current handler via i386_get_current_idt_entry
* and then disconnect it using i386_delete_idt_entry.
* RATIONALE : to always have the same transition by forcing the user
* to get the previous handler before accepting to disconnect.
*/
rtems_interrupt_disable(level);
if (rtems_hdl_tbl[irq->name].hdl != default_rtems_entry.hdl) {
rtems_interrupt_enable(level);
printk("IRQ vector %d already connected\n",irq->name);
return 0;
}
/*
* store the data provided by user
*/
rtems_hdl_tbl[irq->name] = *irq;
#ifdef BSP_SHARED_HANDLER_SUPPORT
rtems_hdl_tbl[irq->name].next_handler = (void *)-1;
#endif
if (is_pic_irq(irq->name)) {
/*
* Enable PIC irq : Main Interrupt Cause Low and High & GPP external
*/
#ifdef DEBUG_IRQ
printk("PIC irq %d\n",irq->name);
#endif
BSP_enable_pic_irq(irq->name);
}
else {
if (is_processor_irq(irq->name)) {
/*
* Enable exception at processor level
*/
}
}
/*
* Enable interrupt on device
*/
if (irq->on)
irq->on(irq);
rtems_interrupt_enable(level);
return 1;
}
int BSP_get_current_rtems_irq_handler (rtems_irq_connect_data* irq)
{
if (!isValidInterrupt(irq->name)) {
return 0;
}
*irq = rtems_hdl_tbl[irq->name];
return 1;
}
int BSP_remove_rtems_irq_handler (const rtems_irq_connect_data* irq)
{
unsigned int level;
if (!isValidInterrupt(irq->name)) {
return 0;
}
/*
* Check if default handler is actually connected. If not issue an error.
* You must first get the current handler via i386_get_current_idt_entry
* and then disconnect it using i386_delete_idt_entry.
* RATIONALE : to always have the same transition by forcing the user
* to get the previous handler before accepting to disconnect.
*/
if (rtems_hdl_tbl[irq->name].hdl != irq->hdl) {
return 0;
}
rtems_interrupt_disable(level);
/*
* disable PIC interrupt
*/
if (is_pic_irq(irq->name))
BSP_disable_pic_irq(irq->name);
else {
if (is_processor_irq(irq->name)) {
/*
* disable exception at processor level
*/
}
}
/*
* Disable interrupt on device
*/
if (irq->off)
irq->off(irq);
/*
* restore the default irq value
*/
rtems_hdl_tbl[irq->name] = default_rtems_entry;
rtems_interrupt_enable(level);
return 1;
}
/*
* ------------------------ RTEMS Global Irq Handler Mngt Routines ----------------
*/
int BSP_rtems_irq_mngt_set(rtems_irq_global_settings* config)
{
unsigned int level;
int i;
/*
* Store various code accelerators
*/
internal_config = config;
default_rtems_entry = config->defaultEntry;
rtems_hdl_tbl = config->irqHdlTbl;
rtems_interrupt_disable(level);
if ( !BSP_setup_the_pic() ) {
printk("PIC setup failed; leaving IRQs OFF\n");
return 0;
}
for (i= BSP_MAIN_GPP7_0_IRQ; i <= BSP_MAIN_GPP31_24_IRQ; i++)
BSP_enable_pic_irq(i);
rtems_interrupt_enable(level);
return 1;
}
int BSP_rtems_irq_mngt_get(rtems_irq_global_settings** config)
{
*config = internal_config;
return 0;
}
/*
* High level IRQ handler called from shared_raw_irq_code_entry
*/
int C_dispatch_irq_handler (CPU_Interrupt_frame *frame, unsigned int excNum)
int C_dispatch_irq_handler (BSP_Exception_frame *frame, unsigned int excNum)
{
register unsigned msr, new_msr;
unsigned long irqCause[3]={0, 0,0};
register unsigned long selectCause;
unsigned oldMask[3]={0,0,0};
register unsigned i=0, j, irq=0, bitmask=0, group=0;
if (excNum == ASM_DEC_VECTOR) {
_MSR_GET(msr);
new_msr = msr | MSR_EE;
_MSR_SET(new_msr);
rtems_hdl_tbl[BSP_DECREMENTER].hdl(rtems_hdl_tbl[BSP_DECREMENTER].handle);
_MSR_SET(msr);
bsp_irq_dispatch_list( rtems_hdl_tbl, BSP_DECREMENTER, default_rtems_hdl);
return 0;
}
@@ -635,11 +464,7 @@ int C_dispatch_irq_handler (CPU_Interrupt_frame *frame, unsigned int excNum)
out_le32(BSP_irqCause_reg[2], ~bitmask);/* Till Straumann: Ack the edge triggered GPP IRQ */
#endif
_MSR_GET(msr);
new_msr = msr | MSR_EE;
_MSR_SET(new_msr);
rtems_hdl_tbl[irq].hdl(rtems_hdl_tbl[irq].handle);
_MSR_SET(msr);
bsp_irq_dispatch_list( rtems_hdl_tbl, irq, default_rtems_hdl);
for (j=0; j<3; j++ ) BSP_irqMask_cache[j] = oldMask[j];
break;
@@ -654,25 +479,6 @@ int C_dispatch_irq_handler (CPU_Interrupt_frame *frame, unsigned int excNum)
return 0;
}
void _ThreadProcessSignalsFromIrq (BSP_Exception_frame* ctx)
{
/*
* Process pending signals that have not already been
* processed by _Thread_Displatch. This happens quite
* unfrequently : the ISR must have posted an action
* to the current running thread.
*/
if ( _Thread_Do_post_task_switch_extension ||
_Thread_Executing->do_post_task_switch_extension ) {
_Thread_Executing->do_post_task_switch_extension = FALSE;
_API_extensions_Run_postswitch();
}
/*
* I plan to process other thread related events here.
* This will include DEBUG session requested from keyboard...
*/
}
/* Only print part of the entries for now */
void BSP_printPicIsrTbl()
{

View File

@@ -29,7 +29,7 @@
#ifndef LIBBSP_POWERPC_MVME5500_IRQ_IRQ_H
#define LIBBSP_POWERPC_MVME5500_IRQ_IRQ_H
/*#define BSP_SHARED_HANDLER_SUPPORT 1*/
#define BSP_SHARED_HANDLER_SUPPORT 1
#include <rtems/irq.h>
#ifndef ASM
@@ -133,5 +133,7 @@
extern void BSP_rtems_irq_mng_init(unsigned cpuId);
#include <bsp/irq_supp.h>
#endif
#endif

View File

@@ -21,11 +21,6 @@
#include <libcpu/raw_exception.h> /* ASM_EXT_VECTOR, ASM_DEC_VECTOR ... */
/*#define TRACE_IRQ_INIT*/
extern unsigned int external_exception_vector_prolog_code_size[];
extern void external_exception_vector_prolog_code();
extern unsigned int decrementer_exception_vector_prolog_code_size[];
extern void decrementer_exception_vector_prolog_code();
/*
* default on/off function
*/
@@ -93,8 +88,8 @@ rtems_irq_prio BSPirqPrioTable[BSP_PIC_IRQ_NUMBER]={
*/
void BSP_rtems_irq_mng_init(unsigned cpuId)
{
rtems_raw_except_connect_data vectorDesc;
int i;
int i;
rtems_interrupt_level l;
/*
* First initialize the Interrupt management hardware
@@ -130,6 +125,7 @@ void BSP_rtems_irq_mng_init(unsigned cpuId)
printk("Going to setup irq mngt configuration\n");
#endif
rtems_interrupt_disable(l);
if (!BSP_rtems_irq_mngt_set(&initial_config)) {
/*
* put something here that will show the failure...
@@ -138,29 +134,14 @@ void BSP_rtems_irq_mng_init(unsigned cpuId)
}
#ifdef TRACE_IRQ_INIT
printk("Done setup irq mngt configuration\n");
#endif
#endif
/* I don't really understand why all sources are enable here... (T.S) */
for (i= BSP_MAIN_GPP7_0_IRQ; i <= BSP_MAIN_GPP31_24_IRQ; i++)
BSP_enable_pic_irq(i);
rtems_interrupt_enable(l);
/*
* We must connect the raw irq handler for the two
* expected interrupt sources : decrementer and external interrupts.
*/
vectorDesc.exceptIndex = ASM_DEC_VECTOR;
vectorDesc.hdl.vector = ASM_DEC_VECTOR;
vectorDesc.hdl.raw_hdl = decrementer_exception_vector_prolog_code;
vectorDesc.hdl.raw_hdl_size = (unsigned) decrementer_exception_vector_prolog_code_size;
vectorDesc.on = nop_func;
vectorDesc.off = nop_func;
vectorDesc.isOn = connected;
if (!ppc_set_exception (&vectorDesc)) {
BSP_panic("Unable to initialize RTEMS decrementer raw exception\n");
}
vectorDesc.exceptIndex = ASM_EXT_VECTOR;
vectorDesc.hdl.vector = ASM_EXT_VECTOR;
vectorDesc.hdl.raw_hdl = external_exception_vector_prolog_code;
vectorDesc.hdl.raw_hdl_size = (unsigned) external_exception_vector_prolog_code_size;
if (!ppc_set_exception (&vectorDesc)) {
BSP_panic("Unable to initialize RTEMS external raw exception\n");
}
#ifdef TRACE_IRQ_INIT
printk("RTEMS IRQ management is now operationnal\n");
#endif

View File

@@ -81,14 +81,22 @@ $(PROJECT_INCLUDE)/tod.h: ../../shared/tod.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/tod.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/tod.h
$(PROJECT_INCLUDE)/bsp/vectors.h: ../../powerpc/shared/vectors/vectors.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vectors.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vectors.h
$(PROJECT_INCLUDE)/bsp/bspException.h: vectors/bspException.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/bspException.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/bspException.h
$(PROJECT_INCLUDE)/bsp/vectors.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/vectors.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vectors.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vectors.h
$(PROJECT_INCLUDE)/bsp/irq_supp.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/irq_supp.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq_supp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq_supp.h
$(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/ppc_exc_bspsupp.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
$(PROJECT_INCLUDE)/bsp/bspMvme5500.h: GT64260/bspMvme5500.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/bspMvme5500.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/bspMvme5500.h