ctr_firmware/trunk/bootrom/build/libraries/os/common/os_interrupt.c
nakasima a458bc04a7 os_interrupt_common.cをos_interrupt.cへマージ。
ARM11のosHalt修正。

git-svn-id: file:///Volumes/Transfer/gigaleak_20231201/2020-09-30%20-%20paladin.7z/paladin/ctr_firmware@134 b871894f-2f95-9b40-918c-086798483c85
2008-12-19 09:16:29 +00:00

1018 lines
29 KiB
C

/*---------------------------------------------------------------------------*
Project: CtrBrom - libraries - OS
File: os_interrupt.c
Copyright 2008 Nintendo. All rights reserved.
These coded instructions, statements, and computer programs contain
proprietary information of Nintendo of America Inc. and/or Nintendo
Company Ltd., and are protected by Federal copyright law. They may
not be disclosed to third parties or copied or duplicated in any form,
in whole or in part, without the prior written consent of Nintendo.
$Date:: $
$Rev$
$Author$
*---------------------------------------------------------------------------*/
#include <brom/os.h>
#ifdef SDK_ARM11
OSIntrFunction osIntrTable[OS_INTR_ID_NUM];
#else // SDK_ARM9
OSIntrFunction osIntrTable[OS_INTR_ID_NUM] ATTRIBUTE_SECTION(.dtcm);
#endif // SDK_ARM9
asm void i_osIrqVeneer( void );
/*---------------------------------------------------------------------------*
Name: osInitInterrupt
Description: Initialize Interrupts
Arguments: None
Returns: None
*---------------------------------------------------------------------------*/
void osInitInterrupt( void )
{
static BOOL isInit;
if ( isInit == FALSE )
{
isInit = TRUE;
(void)osDisableIrqAndFiq();
i_osInitInterruptTable();
((u32*)HW_INTR_VENEER_BUF)[0] = ((u32*)i_osIrqVeneer)[0];
((u32*)HW_INTR_VENEER_BUF)[1] = ((u32*)i_osIrqVeneer)[1];
#ifdef SDK_ARM11
{
u32 num = OS_INTR_ID_NUM;
u32 conf = 0;
int i;
for ( i=0; i<MATH_ROUNDUP(num, 32)/32; i++ )
{
reg_OS_IDR_CLR_IE[i] = HW_IDR_WORD_MASK;
reg_OS_IDR_CLR_PND[i] = HW_IDR_WORD_MASK;
}
for ( i=0; i<num; i++ )
{
reg_OS_IDR_TGT[i] = REG_OS_IDR_TGT0_C0_MASK;
reg_OS_IDR_PRIO[i] = OS_IDR_INTR_PRIO_DEFAULT << 4;
}
for ( i=0; i<32; i+=2 )
{
conf |= (HW_IDR_INTR_RISE_EDGE | HW_IDR_INTR_1_N_MODEL) << i;
}
for ( i=0; i<MATH_ROUNDUP(num, 16)/16; i++ )
{
reg_OS_IDR_CFG[i] = conf;
}
}
reg_OS_IDR_CNT = REG_OS_IDR_CNT_E_MASK;
reg_OS_CPUI_PRIO = 15 << REG_OS_CPUI_PRIO_THLD_SHIFT;
reg_OS_CPUI_BP = HW_CPUIBP_CMP_PRIO_ALL_BITS;
reg_OS_CPUI_CNT = REG_OS_CPUI_CNT_E_MASK;
#else // SDK_ARM9
reg_OS_IE = 0;
reg_OS_IF = 0xffffffff;
#endif // SDK_ARM9
(void)osEnableInterrupts();
}
}
/*---------------------------------------------------------------------------*
Name: i_osIrqVeneer
Description: Interrupt Vevver
Arguments: None
Returns: None
*---------------------------------------------------------------------------*/
#include <brom/code32.h>
asm void i_osIrqVeneer( void )
{
INASM_EXTERN( osIrqHandler )
ldr pc, =osIrqHandler
LTORG
}
#include <brom/codereset.h>
/*---------------------------------------------------------------------------*
Name: i_osInitInterruptTable
Description: Initialize InterruptTable
Arguments: None
Returns: None
*---------------------------------------------------------------------------*/
void i_osInitInterruptTable( void )
{
int i;
for (i=0; i<OS_INTR_ID_NUM; i++)
{
osIntrTable[i] = NULL;
}
}
/*---------------------------------------------------------------------------*
Name: osSetInterruptHandler
Description: Set interrupt handler
Arguments: interrupt ID
interrupt handler
Returns: None
*---------------------------------------------------------------------------*/
void osSetInterruptHandler( OSIntrID id, OSIntrFunction handler )
{
osIntrTable[id] = handler;
}
/*---------------------------------------------------------------------------*
Name: osGetInterruptHandler
Description: Get interrupt handler
Arguments: interrupt ID
interrupt handler
Returns: None
*---------------------------------------------------------------------------*/
OSIntrFunction osGetInterruptHandler( OSIntrID id )
{
return osIntrTable[id];
}
//============================================================================
// Control the master of all interrupts
//============================================================================
/*---------------------------------------------------------------------------*
Name: osEnableInterrupts
Description: Set CPSR to enable irq and fiq interrupts
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
OSIntrMode osEnableInterrupts( void )
{
return osEnableIrq();
}
/*---------------------------------------------------------------------------*
Name: osDisableInterrupts
Description: Set CPSR to disable irq and fiq interrupts
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
OSIntrMode osDisableInterrupts( void )
{
return osDisableIrq();
}
/*---------------------------------------------------------------------------*
Name: osRestoreInterrupts
Description: Restore CPSR irq and fiq interrupts
Arguments: state of irq interrupt bit
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
OSIntrMode osRestoreInterrupts( OSIntrMode state )
{
return osRestoreIrq( state );
}
#include <brom/code32.h>
/*---------------------------------------------------------------------------*
Name: osEnableIrq
Description: Set CPSR to enable irq interrupt
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osEnableIrq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsie i
#else
bic r1, r0, #HW_PSR_IRQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_IRQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osDisableIrq
Description: Set CPSR to disable irq interrupt
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osDisableIrq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsid i
#else
orr r1, r0, #HW_PSR_IRQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_IRQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osRestoreIrq
Description: Restore CPSR irq interrupt
Arguments: state of irq and fiq interrupt bit
Returns: last state of HW_PSR_IRQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osRestoreIrq( OSIntrMode state )
{
mrs r1, cpsr
bic r2, r1, #HW_PSR_IRQ_DISABLE
orr r2, r2, r0
msr cpsr_c, r2
and r0, r1, #HW_PSR_IRQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osEnableFiq
Description: Set CPSR to enable fiq interrupt
Arguments: None.
Returns: last state of HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osEnableFiq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsie f
#else
bic r1, r0, #HW_PSR_FIQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_FIQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osDisableFiq
Description: Set CPSR to disable fiq interrupt
Arguments: None.
Returns: last state of HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osDisableFiq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsid f
#else
orr r1, r0, #HW_PSR_FIQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_FIQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osRestoreFiq
Description: Restore CPSR fiq interrupt
Arguments: state of fiq interrupt bit
Returns: last state of HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osRestoreFiq( OSIntrMode state )
{
mrs r1, cpsr
bic r2, r1, #HW_PSR_FIQ_DISABLE
orr r2, r2, r0
msr cpsr_c, r2
and r0, r1, #HW_PSR_FIQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osEnableIrqAndFiq
Description: Set CPSR to enable irq and fiq interrupts
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osEnableIrqAndFiq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsie if
#else
bic r1, r0, #HW_PSR_IRQ_FIQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_IRQ_FIQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osDisableIrqAndFiq
Description: Set CPSR to disable irq and fiq interrupts
Arguments: None.
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osDisableIrqAndFiq( void )
{
mrs r0, cpsr
#ifdef SDK_USE_MPCORE_EXTEND_OP
cpsid if
#else
orr r1, r0, #HW_PSR_IRQ_FIQ_DISABLE
msr cpsr_c, r1
#endif
and r0, r0, #HW_PSR_IRQ_FIQ_DISABLE
bx lr
}
/*---------------------------------------------------------------------------*
Name: osRestoreIrqAndFiq
Description: Restore CPSR irq and fiq interrupts
Arguments: state of irq and fiq interrupt bit
Returns: last state of HW_PSR_IRQ_DISABLE & HW_PSR_FIQ_DISABLE
*---------------------------------------------------------------------------*/
ASM OSIntrMode osRestoreIrqAndFiq( OSIntrMode state )
{
mrs r1, cpsr
bic r2, r1, #HW_PSR_IRQ_FIQ_DISABLE
orr r2, r2, r0
msr cpsr_c, r2
and r0, r1, #HW_PSR_IRQ_FIQ_DISABLE
bx lr
}
#include <brom/codereset.h>
//================================================================================
// InterruptMask
//================================================================================
/*---------------------------------------------------------------------------*
Name: osEnableInterruptID
Description: set Interrupt Set Enable Register
Arguments: Interrupt Distributor ID
Returns: TRUE if last state is enabled
*---------------------------------------------------------------------------*/
BOOL osEnableInterruptID( OSIntrID id )
{
BOOL retval;
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
retval = TRUE & (reg_OS_IDR_SET_IE[ofs] >> sft);
reg_OS_IDR_SET_IE[ofs] = 1 << sft;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
retval = TRUE & (BOOL)(prep >> id);
reg_OS_IE = prep | (1 << id);
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osEnableInterruptMask
Description: set specified interrupt factor
Arguments: mask interrupt factor
Returns: previous factors
*---------------------------------------------------------------------------*/
OSIntrMask osEnableInterruptMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
OSIntrMask prep = reg_OS_IDR_SET_IE_ALL;
reg_OS_IDR_SET_IE_ALL = mask;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
reg_OS_IE = prep | mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return prep;
}
/*---------------------------------------------------------------------------*
Name: osDisableInterruptID
Description: set Interrupt Clear Enable Register
Arguments: Interrupt Distributor ID
Returns: TRUE if last state is enabled
*---------------------------------------------------------------------------*/
BOOL osDisableInterruptID( OSIntrID id )
{
BOOL retval;
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
retval = TRUE & (reg_OS_IDR_SET_IE[ofs] >> sft);
reg_OS_IDR_CLR_IE[ofs] = 1 << sft;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
retval = TRUE & (BOOL)(prep >> id);
reg_OS_IE = prep & ~(1 << id);
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osDisableInterruptMask
Description: unset specified interrupt factor
Arguments: mask interrupt factor
Returns: previous factors
*---------------------------------------------------------------------------*/
OSIntrMask osDisableInterruptMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
OSIntrMask prep = reg_OS_IDR_SET_IE_ALL;
reg_OS_IDR_CLR_IE_ALL = mask;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
reg_OS_IE = prep & ~mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return prep;
}
/*---------------------------------------------------------------------------*
Name: osRestoreInterruptID
Description: set Interrupt Clear Enable Register
Arguments: id : Interrupt Distributor ID
state : state whether interrupt is enabled
Returns: TRUE if last state is enabled
*---------------------------------------------------------------------------*/
BOOL osRestoreInterruptID( OSIntrID id, BOOL state )
{
BOOL retval;
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
retval = TRUE & (reg_OS_IDR_SET_IE[ofs] >> sft);
if ( state == TRUE )
{
reg_OS_IDR_SET_IE[ofs] = 1 << sft;
}
else
{
reg_OS_IDR_CLR_IE[ofs] = 1 << sft;
}
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
retval = TRUE & (BOOL)(prep >> id);
if ( state == TRUE )
{
reg_OS_IE = prep | (state << id);
}
else
{
reg_OS_IE = prep & ~(state << id);
}
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osSetInterruptMask
Description: set interrupt factor
Arguments: mask interrupt factor
Returns: previous factors
*---------------------------------------------------------------------------*/
OSIntrMask osSetInterruptMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
OSIntrMask prep = reg_OS_IDR_SET_IE_ALL;
reg_OS_IDR_CLR_IE[0] = HW_IDR_WORD_MASK;
reg_OS_IDR_CLR_IE[1] = HW_IDR_WORD_MASK;
reg_OS_IDR_CLR_IE[2] = HW_IDR_WORD_MASK;
reg_OS_IDR_CLR_IE[3] = HW_IDR_WORD_MASK;
reg_OS_IDR_SET_IE_ALL = mask;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IE;
reg_OS_IE = mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return prep;
}
//================================================================================
// INTERRUPT PENDING
//================================================================================
/*---------------------------------------------------------------------------*
Name: osClearInterruptPendingID
Description: set Interrupt Clear Pending Register
Arguments: Interrupt Distributor ID
Returns: TRUE if last state is pending
*---------------------------------------------------------------------------*/
BOOL osClearInterruptPendingID( OSIntrID id )
{
OSIntrMode enabled = osDisableInterrupts();
BOOL retval;
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
retval = TRUE & (reg_OS_IDR_SET_PND[ofs] >> sft);
reg_OS_IDR_CLR_PND[ofs] = 1 << sft;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IF;
retval = TRUE & (BOOL)(prep >> id);
reg_OS_IF = (u32)(1 << id);
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osClearInterruptPendingMask
Description: reset IF bit
(setting bit causes to clear bit for interrupt)
Arguments: mask interrupt factor
Returns: previous factors
*---------------------------------------------------------------------------*/
OSIntrMask osClearInterruptPendingMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
OSIntrMask prep = reg_OS_IDR_SET_PND_ALL;
reg_OS_IDR_CLR_PND_ALL = mask;
#else // SDK_ARM9
OSIntrMask prep = reg_OS_IF;
reg_OS_IF = mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
return prep;
}
#ifdef SDK_ARM11
/*---------------------------------------------------------------------------*
Name: osSetInterruptPendingID
Description: set Interrupt Set Pending Register
Arguments: Interrupt Distributor ID
Returns: TRUE if last state is pending
*---------------------------------------------------------------------------*/
BOOL osSetInterruptPendingID( OSIntrID id )
{
u32 ofs = id/32;
u32 sft = id%32;
BOOL retval;
retval = TRUE & (reg_OS_IDR_SET_PND[ofs] >> sft);
reg_OS_IDR_SET_PND[ofs] = 1 << sft;
return retval;
}
/*---------------------------------------------------------------------------*
Name: osRestoreInterruptPendingID
Description: restore Interrupt Pending
Arguments: id : Interrupt Distributor ID
state : state whether interrupt is enabled
Returns: TRUE if last state is pending
*---------------------------------------------------------------------------*/
BOOL osRestoreInterruptPendingID( OSIntrID id, BOOL state )
{
u32 ofs = id/32;
u32 sft = id%32;
BOOL retval;
retval = TRUE & (reg_OS_IDR_SET_PND[ofs] >> sft);
if ( state == TRUE )
{
reg_OS_IDR_SET_PND[ofs] = 1 << sft;
}
else
{
reg_OS_IDR_CLR_PND[ofs] = 1 << sft;
}
return retval;
}
/*---------------------------------------------------------------------------*
Name: osSetEndOfInterruptRegister
Description: set ID to End of Interrupt Register
change state to Inactive.
Arguments: Interrupt Distributor ID
Returns: None
*---------------------------------------------------------------------------*/
void osSetEndOfInterruptRegister( OSIntrID id )
{
reg_OS_CPUI_EOI = id;
}
/*---------------------------------------------------------------------------*
Name: i_osReadHighestPendingInterruptRegister
Description: read ID from Highest Pending Interrupt Register
Arguments: None
Returns: Interrupt Distributor ID
*---------------------------------------------------------------------------*/
OSIntrID i_osReadHighestPendingInterruptRegister( void )
{
return (OSIntrID)(reg_OS_CPUI_HI_PND & REG_OS_CPUI_HI_PND_ID_MASK);
}
/*---------------------------------------------------------------------------*
Name: i_osReadInterruptAcknowledgeRegister
Description: read ID from Interrupt Acknowledge Register
get interrupt ID and change state to NotPending and Active.
Arguments: None
Returns: Interrupt Distributor ID
*---------------------------------------------------------------------------*/
OSIntrID i_osReadInterruptAcknowledgeRegister( void )
{
return (OSIntrID)(reg_OS_CPUI_ACK & REG_OS_CPUI_ACK_ID_MASK);
}
#endif // SDK_ARM11
/*---------------------------------------------------------------------------*
Name: osIsInterruptPendingID
Description: set Interrupt Clear Pending Register
Arguments: Interrupt Distributor ID
Returns: TRUE if last state is pending
*---------------------------------------------------------------------------*/
BOOL osIsInterruptPendingID( OSIntrID id )
{
BOOL retval;
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
retval = TRUE & (reg_OS_IDR_SET_PND[ofs] >> sft);
#else // SDK_ARM9
retval = TRUE & (BOOL)(reg_OS_IF >> id);
#endif // SDK_ARM9
return retval;
}
//================================================================================
// IRQ CHEKE BUFFER
//================================================================================
/*---------------------------------------------------------------------------*
Name: osSetInterruptCheckID
Description: set irq flag to check being called
Arguments: irq factors to be set
Returns: None
*---------------------------------------------------------------------------*/
BOOL osSetInterruptCheckID( OSIntrID id )
{
BOOL retval;
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
u32 *buf = &((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[ofs];
#else // SDK_ARM9
u32 sft = id;
u32 *buf = (OSIntrMask *)HW_INTR_CHECK_BUF;
#endif // SDK_ARM9
retval = TRUE & (*buf >> sft);
*buf |= 1 << sft;
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osClearInterruptCheckID
Description: clear irq flag stored in HW_INTR_CHECK_BUF
Arguments: irq factors to be set
Returns: None
*---------------------------------------------------------------------------*/
BOOL osClearInterruptCheckID( OSIntrID id )
{
BOOL retval;
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
u32 *buf = &((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[ofs];
#else // SDK_ARM9
u32 sft = id;
u32 *buf = (OSIntrMask *)HW_INTR_CHECK_BUF;
#endif // SDK_ARM9
retval = TRUE & (*buf >> sft);
*buf &= ~(1 << sft);
(void)osRestoreInterrupts( enabled );
return retval;
}
/*---------------------------------------------------------------------------*
Name: osIsInterruptCheckID
Description: check irq flag stored in HW_INTR_CHECK_BUF
Arguments: irq factors to be set
Returns: None
*---------------------------------------------------------------------------*/
BOOL osIsInterruptCheckID( OSIntrID id )
{
BOOL retval;
#ifdef SDK_ARM11
u32 ofs = id/32;
u32 sft = id%32;
u32 *buf = &((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[ofs];
#else // SDK_ARM9
u32 sft = id;
u32 *buf = (OSIntrMask *)HW_INTR_CHECK_BUF;
#endif // SDK_ARM9
retval = TRUE & (*buf >> sft);
return retval;
}
/*---------------------------------------------------------------------------*
Name: osSetInterruptCheckMask
Description: set irq flag to check being called
Arguments: irq factors to be set
Returns: None
*---------------------------------------------------------------------------*/
void osSetInterruptCheckMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[0] |= mask.w[0];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[1] |= mask.w[1];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[2] |= mask.w[2];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[3] |= mask.w[3];
#else // SDK_ARM9
*(OSIntrMask *)HW_INTR_CHECK_BUF |= mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
}
/*---------------------------------------------------------------------------*
Name: osClearInterruptCheckMask
Description: clear irq flag stored in HW_INTR_CHECK_BUF
Arguments: irq factors to be cleared
Returns: None
*---------------------------------------------------------------------------*/
void osClearInterruptCheckMask( OSIntrMask mask )
{
OSIntrMode enabled = osDisableInterrupts();
#ifdef SDK_ARM11
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[0] &= ~mask.w[0];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[1] &= ~mask.w[1];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[2] &= ~mask.w[2];
((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[3] &= ~mask.w[3];
#else // SDK_ARM9
*(OSIntrMask *)HW_INTR_CHECK_BUF &= ~mask;
#endif // SDK_ARM9
(void)osRestoreInterrupts( enabled );
}
/*---------------------------------------------------------------------------*
Name: osIsInterruptCheckMask
Description: check irq flag stored in HW_INTR_CHECK_BUF
Arguments: irq factors to be cleared
Returns: TRUE if irq flag exists
*---------------------------------------------------------------------------*/
BOOL osIsInterruptCheckMask( OSIntrMask mask )
{
u32 tmp;
#ifdef SDK_ARM11
OSIntrMode enabled = osDisableInterrupts();
tmp = ((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[0] & mask.w[0];
tmp |= ((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[1] & mask.w[1];
tmp |= ((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[2] & mask.w[2];
tmp |= ((OSIntrMask *)HW_INTR_CHECK0_BUF)->w[3] & mask.w[3];
(void)osRestoreInterrupts( enabled );
#else // SDK_ARM9
tmp = osGetInterruptCheckMask() & mask;
#endif // SDK_ARM9
return tmp ? TRUE : FALSE;
}
//============================================================================
// WAIT
//============================================================================
/*---------------------------------------------------------------------------*
Name: osWaitInterruptID
Description: wait specifiled interrupt.
OS_WaitInterrupt doesn't switch thread.
OS_WaitInterrupt wait by using OS_Halt().
Arguments: clear TRUE if want to clear interrupt flag before wait.
FALSE if not.
irqFlags bit of interrupts to wait for
Returns: None
*---------------------------------------------------------------------------*/
void osWaitInterruptID( BOOL clear, OSIntrID id )
{
OSIntrMode cpsrIrq = osDisableInterrupts();
if (clear)
{
(void)osClearInterruptCheckID( id );
}
while (! osIsInterruptCheckID(id) )
{
osHalt();
(void)osEnableInterrupts();
(void)osDisableInterrupts();
}
(void)osClearInterruptCheckID( id );
(void)osRestoreInterrupts( cpsrIrq );
}
/*---------------------------------------------------------------------------*
Name: osWaitInterruptMask
Description: wait specifiled interrupt.
OS_WaitInterrupt doesn't switch thread.
OS_WaitInterrupt wait by using OS_Halt().
Arguments: clear TRUE if want to clear interrupt flag before wait.
FALSE if not.
irqFlags bit of interrupts to wait for
Returns: None
*---------------------------------------------------------------------------*/
void osWaitInterruptMask( BOOL clear, OSIntrMask irqFlags )
{
OSIntrMode cpsrIrq = osDisableInterrupts();
if (clear)
{
(void)osClearInterruptCheckMask( irqFlags );
}
while (! osIsInterruptCheckMask(irqFlags) )
{
osHalt();
(void)osEnableInterrupts();
(void)osDisableInterrupts();
}
(void)osClearInterruptCheckMask( irqFlags );
(void)osRestoreInterrupts( cpsrIrq );
}