CMSIS-CORE  Version 3.01
CMSIS-CORE support for Cortex-M processor-based devices
Interrupts and Exceptions (NVIC)

Describes programming of interrupts and exception functions. More...

Enumerations

enum  IRQn_Type {
  NonMaskableInt_IRQn = -14,
  HardFault_IRQn = -13,
  MemoryManagement_IRQn = -12,
  BusFault_IRQn = -11,
  UsageFault_IRQn = -10,
  SVCall_IRQn = -5,
  DebugMonitor_IRQn = -4,
  PendSV_IRQn = -2,
  SysTick_IRQn = -1,
  WWDG_STM_IRQn = 0,
  PVD_STM_IRQn = 1
}
 Definition of IRQn numbers. More...

Functions

void NVIC_SetPriorityGrouping (uint32_t PriorityGroup)
 Set priority grouping [not for Cortex-M0 variants].
uint32_t NVIC_GetPriorityGrouping (void)
 Read the priority grouping [not for Cortex-M0 variants].
void NVIC_EnableIRQ (IRQn_Type IRQn)
 Enable an external interrupt.
void NVIC_DisableIRQ (IRQn_Type IRQn)
 Disable an external interrupt.
uint32_t NVIC_GetPendingIRQ (IRQn_Type IRQn)
 Get the pending interrupt.
void NVIC_SetPendingIRQ (IRQn_Type IRQn)
 Set an interrupt to pending.
void NVIC_ClearPendingIRQ (IRQn_Type IRQn)
 Clear an interrupt from pending.
uint32_t NVIC_GetActive (IRQn_Type IRQn)
 Get the interrupt active status [not for Cortex-M0 variants].
void NVIC_SetPriority (IRQn_Type IRQn, uint32_t priority)
 Set the priority for an interrupt.
uint32_t NVIC_GetPriority (IRQn_Type IRQn)
 Get the priority of an interrupt.
uint32_t NVIC_EncodePriority (uint32_t PriorityGroup, uint32_t PreemptPriority, uint32_t SubPriority)
 Encodes Priority [not for Cortex-M0 variants].
void NVIC_DecodePriority (uint32_t Priority, uint32_t PriorityGroup, uint32_t *pPreemptPriority, uint32_t *pSubPriority)
 Decode the interrupt priority [not for Cortex-M0 variants].
void NVIC_SystemReset (void)
 Reset the system.

Description

ARM provides a template file startup_device for each supported compiler. The file must be adapted by the silicon vendor to include interrupt vectors for all device-specific interrupt handlers. Each interrupt handler is defined as a weak function to an dummy handler. These interrupt handlers can be used directly in application software without being adapted by the programmer.

The table below describes the core exception names and their availability in various Cortex-M cores.

Core Exception Name IRQn Value M0 M0p M3 M4 SC000 SC300 Description
NonMaskableInt_IRQn -14
check.png
check.png
check.png
check.png
check.png
check.png
Non Maskable Interrupt
HardFault_IRQn -13
check.png
check.png
check.png
check.png
check.png
check.png
Hard Fault Interrupt
MemoryManagement_IRQn -12    
check.png
check.png
 
check.png
Memory Management Interrupt
BusFault_IRQn -11    
check.png
check.png
 
check.png
Bus Fault Interrupt
UsageFault_IRQn -10    
check.png
check.png
 
check.png
Usage Fault Interrupt
SVCall_IRQn -5
check.png
check.png
check.png
check.png
check.png
check.png
SV Call Interrupt
DebugMonitor_IRQn -4    
check.png
check.png
 
check.png
Debug Monitor Interrupt
PendSV_IRQn -2
check.png
check.png
check.png
check.png
check.png
check.png
Pend SV Interrupt
SysTick_IRQn -1
check.png
check.png
check.png
check.png
check.png
check.png
System Tick Interrupt

For Cortex-M0 and Cortex-M0+

The following exception names are fixed and define the start of the vector table for Cortex-M0 variants:

__Vectors       DCD     __initial_sp              ; Top of Stack
                DCD     Reset_Handler             ; Reset Handler
                DCD     NMI_Handler               ; NMI Handler
                DCD     HardFault_Handler         ; Hard Fault Handler
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     SVC_Handler               ; SVCall Handler
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     PendSV_Handler            ; PendSV Handler
                DCD     SysTick_Handler           ; SysTick Handler

For Cortex-M3

The following exception names are fixed and define the start of the vector table for a Cortex-M3:

__Vectors       DCD     __initial_sp              ; Top of Stack
                DCD     Reset_Handler             ; Reset Handler
                DCD     NMI_Handler               ; NMI Handler
                DCD     HardFault_Handler         ; Hard Fault Handler
                DCD     MemManage_Handler         ; MPU Fault Handler
                DCD     BusFault_Handler          ; Bus Fault Handler
                DCD     UsageFault_Handler        ; Usage Fault Handler
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     0                         ; Reserved
                DCD     SVC_Handler               ; SVCall Handler
                DCD     DebugMon_Handler          ; Debug Monitor Handler
                DCD     0                         ; Reserved
                DCD     PendSV_Handler            ; PendSV Handler
                DCD     SysTick_Handler           ; SysTick Handler

Example

The following is an examples for device-specific interrupts:

; External Interrupts
                DCD     WWDG_IRQHandler           ; Window Watchdog
                DCD     PVD_IRQHandler            ; PVD through EXTI Line detect
                DCD     TAMPER_IRQHandler         ; Tamper

Device-specific interrupts must have a dummy function that can be overwritten in user code. Below is an example for this dummy function.

Default_Handler PROC
                EXPORT WWDG_IRQHandler   [WEAK]
                EXPORT PVD_IRQHandler    [WEAK]
                EXPORT TAMPER_IRQHandler [WEAK]
                :
                :
                WWDG_IRQHandler
                PVD_IRQHandler
                TAMPER_IRQHandler
                :
                :
                B .
                ENDP

The user application may simply define an interrupt handler function by using the handler name as shown below.

void WWDG_IRQHandler(void)
{
  ...
}

Code Example 1

The code below shows the usage of the CMSIS NVIC functions NVIC_SetPriorityGrouping(), NVIC_GetPriorityGrouping(), NVIC_SetPriority(), NVIC_GetPriority(), NVIC_EncodePriority(), and NVIC_DecodePriority() with an LPC1700.

#include "LPC17xx.h"

uint32_t priorityGroup;                                     /* Variables to store priority group and priority */
uint32_t priority;
uint32_t preemptPriority;
uint32_t subPriority;


int main (void)  {

  NVIC_SetPriorityGrouping(5);                              /* Set priority group to 5:
                                                               Bit[7..6] preempt priority Bits, 
                                                               Bit[5..3] subpriority Bits 
                                                               (valid for five priority bits) */
     
  priorityGroup =  NVIC_GetPriorityGrouping();              /* Get used priority grouping */

  priority = NVIC_EncodePriority(priorityGroup, 1, 6);      /* Encode priority with 6 for subpriority and 1 for preempt priority
                                                               Note: priority depends on the used priority grouping */
                                                               
  NVIC_SetPriority(UART0_IRQn, priority);                   /* Set new priority */

  priority =  NVIC_GetPriority(UART0_IRQn);                 /* Retrieve priority again */    

  NVIC_DecodePriority(priority, priorityGroup, &preemptPriority, &subPriority);

  while(1);
}

Code Example 2

The code below shows the usage of the CMSIS NVIC functions NVIC_EnableIRQ(), NVIC_GetActive() with an LPC1700.

#include "LPC17xx.h"

uint32_t active;                                            /* Variable to store interrupt active state */


void TIMER0_IRQHandler(void)  {                             /* Timer 0 interrupt handler  */

  if (LPC_TIM0->IR & (1 << 0))  {                           /* Check if interrupt for match channel 0 occured */ 
    LPC_TIM0->IR |= (1 << 0);                               /* Acknowledge interrupt for match channel 0 occured */
  }
  active = NVIC_GetActive(TIMER0_IRQn);                     /* Get interrupt active state of timer 0 */
}


int main (void) {
                                                            /* Set match channel register MR0 to 1 millisecond */
  LPC_TIM0->MR0 = (((SystemCoreClock / 1000) / 4) - 1);     /* 1 ms? */
  
  LPC_TIM0->MCR = (3 << 0);                                 /* Enable interrupt and reset for match channel MR0 */

  NVIC_EnableIRQ(TIMER0_IRQn);                              /* Enable NVIC interrupt for timer 0 */
  
  LPC_TIM0->TCR = (1 << 0);                                 /* Enable timer 0 */

  while(1);
}

Enumeration Type Documentation

enum IRQn_Type

The core exception enumeration names for IRQn values are defined in the file device.h.

Negative IRQn values represent processor core exceptions (internal interrupts). Positive IRQn values represent device-specific exceptions (external interrupts). The first device-specific interrupt has the IRQn value 0.

The table below describes the core exception names and their availability in various Cortex-M cores.

Enumerator:
NonMaskableInt_IRQn 

Exception 2: Non Maskable Interrupt.

HardFault_IRQn 

Exception 3: Hard Fault Interrupt.

MemoryManagement_IRQn 

Exception 4: Memory Management Interrupt [not on Cortex-M0 variants].

BusFault_IRQn 

Exception 5: Bus Fault Interrupt [not on Cortex-M0 variants].

UsageFault_IRQn 

Exception 6: Usage Fault Interrupt [not on Cortex-M0 variants].

SVCall_IRQn 

Exception 11: SV Call Interrupt.

DebugMonitor_IRQn 

Exception 12: Debug Monitor Interrupt [not on Cortex-M0 variants].

PendSV_IRQn 

Exception 14: Pend SV Interrupt [not on Cortex-M0 variants].

SysTick_IRQn 

Exception 15: System Tick Interrupt.

WWDG_STM_IRQn 

Device Interrupt 0: Window WatchDog Interrupt.

PVD_STM_IRQn 

Device Interrupt 1: PVD through EXTI Line detection Interrupt.


Function Documentation

void NVIC_ClearPendingIRQ ( IRQn_Type  IRQn)

This function removes the pending state of the specified interrupt IRQn. IRQn cannot be a negative number.

Parameters:
[in]IRQnInterrupt number
Remarks:
  • The registers that control the status of interrupts are called SETPEND and CLRPEND.
  • An interrupt can have the status pending though it is not active.
See also:
void NVIC_DecodePriority ( uint32_t  Priority,
uint32_t  PriorityGroup,
uint32_t *  pPreemptPriority,
uint32_t *  pSubPriority 
)

This function decodes an interrupt priority value with the priority group PriorityGroup to preemptive priority value pPreemptPriority and subpriority value pSubPriority. In case of a conflict between priority grouping and available priority bits (__NVIC_PRIO_BITS) the smallest possible priority group is set.

Parameters:
[in]PriorityPriority
[in]PriorityGroupPriority group
[out]*pPreemptPriorityPreemptive priority value (starting from 0)
[out]*pSubPrioritySubpriority value (starting from 0)
Remarks:
  • not for Cortex-M0 variants.
See also:
void NVIC_DisableIRQ ( IRQn_Type  IRQn)

This function disables the specified device-specific interrupt IRQn. IRQn cannot be a negative value.

Parameters:
[in]IRQnNumber of the external interrupt to disable
Remarks:
  • The registers that control the enabling and disabling of interrupts are called SETENA and CLRENA.
See also:
void NVIC_EnableIRQ ( IRQn_Type  IRQn)

This function enables the specified device-specific interrupt IRQn. IRQn cannot be a negative value.

Parameters:
[in]IRQnInterrupt number
Remarks:
  • The registers that control the enabling and disabling of interrupts are called SETENA and CLRENA.
  • The number of supported interrupts depends on the implementation of the chip designer and can be read form the Interrupt Controller Type Register (ICTR) in granularities of 32:
    ICTR[4:0]
    • =0 - 32 interrupts supported
    • =1 - 64 interrupts supported
    • ...
See also:
uint32_t NVIC_EncodePriority ( uint32_t  PriorityGroup,
uint32_t  PreemptPriority,
uint32_t  SubPriority 
)

This function encodes the priority for an interrupt with the priority group PriorityGroup, preemptive priority value PreemptPriority, and subpriority value SubPriority. In case of a conflict between priority grouping and available priority bits (__NVIC_PRIO_BITS) the smallest possible priority group is set.

Parameters:
[in]PriorityGroupPriority group
[in]PreemptPriorityPreemptive priority value (starting from 0)
[in]SubPrioritySubpriority value (starting from 0)
Returns:
Encoded priority for the interrupt
Remarks:
  • not for Cortex-M0 variants.
See also:
uint32_t NVIC_GetActive ( IRQn_Type  IRQn)

This function reads the Interrupt Active Register (NVIC_IABR0-NVIC_IABR7) in NVIC and returns the active bit of the interrupt IRQn.

Parameters:
[in]IRQnInterrupt number
Returns:
  • =0 Interrupt is not active
  • =1 Interrupt is active, or active and pending
Remarks:
  • not for Cortex-M0 variants.
  • Each external interrupt has an active status bit. When the processor starts the interrupt handler the bit is set to 1 and cleared when the interrupt return is executed.
  • When an ISR is preempted and the processor executes anohter interrupt handler, the previous interrupt is still defined as active.
See also:
uint32_t NVIC_GetPendingIRQ ( IRQn_Type  IRQn)

This function returns the pending status of the specified interrupt IRQn.

Parameters:
[in]IRQnInterrupt number
Returns:
  • =0 Interrupt is not pending
  • =1 Interrupt is pending
Remarks:
  • The registers that control the status of interrupts are called SETPEND and CLRPEND.
See also:
uint32_t NVIC_GetPriority ( IRQn_Type  IRQn)

This function reads the priority for the specified interrupt IRQn. IRQn can can specify any device-specific (external) interrupt, or core (internal) interrupt.

The returned priority value is automatically aligned to the implemented priority bits of the microcontroller.

Parameters:
[in]IRQnInterrupt number
Returns:
Interrupt priority
Remarks:
  • Each external interrupt has an associated priority-level register.
  • Unimplemented bits are read as zero.
See also:
uint32_t NVIC_GetPriorityGrouping ( void  )

This functuion returns the priority grouping (flag PRIGROUP in AIRCR[10:8]).

Returns:
Priority grouping field
Remarks:
  • not for Cortex-M0 variants.
  • By default, priority group setting is zero.
See also:
void NVIC_SetPendingIRQ ( IRQn_Type  IRQn)

This function sets the pending bit for the specified interrupt IRQn. IRQn cannot be a negative value.

Parameters:
[in]IRQnInterrupt number
Remarks:
  • The registers that control the status of interrupts are called SETPEND and CLRPEND.
See also:
void NVIC_SetPriority ( IRQn_Type  IRQn,
uint32_t  priority 
)

Sets the priority for the interrupt specified by IRQn.IRQn can can specify any device-specific (external) interrupt, or core (internal) interrupt. The priority specifies the interrupt priority value, whereby lower values indicate a higher priority. The default priority is 0 for every interrupt. This is the highest possible priority.

The priority cannot be set for every core interrupt. HardFault and NMI have a fixed (negative) priority that is higher than any configurable exception or interrupt.

Parameters:
[in]IRQnInterrupt Number
[in]priorityPriority to set
Remarks:
  • The number of priority levels is configurable and depends on the implementation of the chip designer. To determine the number of bits implemented for interrupt priority-level registers, write 0xFF to one of the priority-level register, then read back the value. For example, if the minimum number of 3 bits have been implemented, the read-back value is 0xE0.
  • Writes to unimplemented bits are ignored.
  • For Cortex-M0:
    • Dynamic switching of interrupt priority levels is not supported. The priority level of an interrupt should not be changed after it has been enabled.
    • Supports 0 to 192 priority levels.
    • Priority-level registers are 2 bit wide, occupying the two MSBs. Each Interrupt Priority Level Register is 1-byte wide.
  • For Cortex-M3 and Cortex-M4:
    • Dynamic switching of interrupt priority levels is supported.
    • Supports 0 to 255 priority levels.
    • Priority-level registers have a maximum width of 8 bits and a minumum of 3 bits. Each register can be further devided into preempt priority level and subpriority level.
See also:
void NVIC_SetPriorityGrouping ( uint32_t  PriorityGroup)

The function sets the priority grouping PriorityGroup using the required unlock sequence. PriorityGroup is assigned to the field PRIGROUP (register AIRCR[10:8]). This field determines the split of group priority from subpriority. Only values from 0..7 are used. In case of a conflict between priority grouping and available priority bits (__NVIC_PRIO_BITS), the smallest possible priority group is set.

Parameters:
[in]PriorityGroupPriority group
Remarks:
  • not for Cortex-M0 variants.
  • By default, priority group setting is zero.
See also:
void NVIC_SystemReset ( void  )

This function requests a system reset by setting the SYSRESETREQ flag in the AIRCR register.

Remarks:
  • In most microcontroller designs, setting the SYSRESETREQ flag resets the processor and most parts of the system, but should not affect the debug system.
See also: