Super detailed! A must-see for newbies! STM32–EXTI external interrupt

1. What is an external interrupt?

External interrupts are interrupts triggered by external events on pins external to the microprocessor or microcontroller, usually GPIO pins. These external events can be triggers from external devices, sensors, or other external sources.

2. Details of external interrupt

The registers managed by the AFIO clock include AFIO_EVCR (time control register), AFIO_MAPR (alternative function remapping and debugging IO configuration register), AFIO_EXTICRX (external interrupt configuration register), so when configuring EXTI, you need to turn on the AFIO clock first.

1. EXTI bus distribution

Configuring external interrupts/events on the GPIO line through AFIO_EXTICRx, the AFIO clock must be enabled first.
The EXTI line 0~EXIT line 15 bus controls the GPIO port mapping.

● EXTI line 16 is connected to the PVD output.
● EXTI line 17 is connected to the RTC alarm event.
● EXTI line 18 is connected to the USB wake event.
● EXTI line 19 is connected to the Wake-on-Ethernet event (only applicable to connected products).

2. EXTI register


(1) Interrupt Mask Register (EXTI_IMR): Mask (set to 0) or enable (set to 1) the interrupt request from line x. Enable/disable interrupts.

(2) Suspend register (EXTI_PR): No trigger request occurs (set to 0) / occurs (set to 1).
This bit is set to ‘1’ when a selected edge event occurs on the external interrupt line. It can be cleared by writing a ‘1’ to this bit, or by changing the polarity of the edge detection.

(3) Event mask register (EXTI_EMR): Mask (set to 0) or open (set to 1) the event request from line x. Enable/disable events.

(4) Rising edge trigger selection register (EXTI_RTSR): Disable (set to 0) or enable (set to 1) the rising edge trigger (interrupt and event) on input line x.

(5) Falling edge trigger selection register (EXTI_FTSR): Disable (set to 0) or enable (set to 1) the falling edge trigger (interrupt and event) on input line x.

(6) Software Interrupt Event Register (EXTI_SWIER): When this bit is ‘0’, writing ‘1’ will set the corresponding suspend bit in EXTI_PR. If the interrupt is enabled in EXTI_IMR and EXTI_EMR, an interrupt will be generated at this time.
Note: This bit can be cleared to ‘0’ by clearing the corresponding bit of EXTI_PR (writing ‘1’).

3. EXTI framework diagram analysis


(1) If a peripheral (input line) is used to generate an interrupt, you can choose rising/falling/dual edge trigger interrupts. At this time, the software interrupt event register must be written with 0. Because the software interrupt event register and edge detection circuit are connected through an “OR gate”. If the software interrupt register is set to 1, an interrupt signal will be generated directly, and it will have no effect whether the peripheral generates an interrupt or not. An interrupt/event request can also be generated by writing 1 to the software interrupt/event register in software.
(2) EXTI can be divided into two major functions, one is to generate interrupts and the other is to generate events. These two functions are derived from hardware It’s different.
●The purpose of generating an interrupt line: is to input the input signal to the NVIC, and then run the interrupt service function to realize the function. This is software level.
●The purpose of generating an event line: is to transmit a pulse signal to other peripherals for use, and it is a circuit-level signal transmission, belonging to the hardware level.
●Steps to generate an interrupt: Set the trigger register according to the edge detection required by the input line peripheral circuit, and set the “Software Interrupt Event Register” to 0 (for the reasons mentioned above), and at the same time, set the “Interrupt Mask Register” in Writing 1 to the corresponding bit enables the interrupt request. When the selected signal edge appears on the external interrupt line, an interrupt request will be generated and the corresponding suspend bit of the “Request Suspend Register” will be set to 1. Writing 1 to the corresponding bit in the “request pending register” will clear the interrupt request.
●Steps to generate an event: Set the trigger register according to the edge detection required by the input line peripheral circuit, and write 1 in the corresponding bit of the “event mask register” to allow the event request. An event pulse is generated when a selected signal edge occurs on the event line.
(3) “Pulse generator” is used to trigger event responses. It is mainly connected to other peripherals. When an interrupt signal comes, it activates the pulse generator and sends a pulse signal to other peripherals it is connected to.
(4) Two “mask registers”. They are all connected to an “AND gate” with our signal, which means that if some bits of this mask register are set to 0, the incoming interrupt signal will never pass through this AND gate, reaching a “shield” Effect. For example, if you do not want an interrupt channel to work, then set the bit in the interrupt mask register to 0, so that the interrupt signal from here will never reach the NVIC; for another example, if you do not need the event response function, then set the event mask register If all are set to 0, the event response will be invalid.

4. EXTI related configuration

(1) EXTI mode:

typedef enum
{<!-- -->
EXTI_Mode_Interrupt = 0x00, //Generate an interrupt
EXTI_Mode_Event = 0x04 //Generate event
}EXTIMode_TypeDef;

(2) EXTI trigger type:

typedef enum
{<!-- -->
EXTI_Trigger_Rising = 0x08, //rising edge
EXTI_Trigger_Falling = 0x0C, //Falling edge
EXTI_Trigger_Rising_Falling = 0x10 //Trigger on both rising and falling edges
}EXTITrigger_TypeDef;

5.EXTI example: (Take PA10 as an example)

(1) Enable the clock (because GPIO maps external interrupts, the AFIO clock needs to be turned on)

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); // GPIOA clock
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); // AFIO clock

(2) Configure GPIO pins

GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; // Take pull-up input mode as an example
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, & amp;GPIO_InitStructure);

(3) Configure the mapping relationship between the GPIO port and the external interrupt line. (PA10 is hung on the EXTI10 bus)

GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource10); //External interrupt line 10 is mapped to PA10.

(4) Configure EXTI

EXTI_InitTypeDef EXTI_InitStructure;
EXTI_InitStructure.EXTI_Line = EXTI_Line10; // Select interrupt line
EXTI_InitStructure.EXTI_LineCmd = ENABLE; // Enable interrupt line
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; //Interrupt mode
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising; // Take rising edge trigger as an example
EXTI_Init( & amp;EXTI_InitStructure);

(5) Configure interrupt priority group

NVIC_PriorityGroupConfig(NVIC_Priority_Group_2);

(6) Configure NVIC

NVIC_InitTypeDef NVIC_InitStructure;
NVIC_InitStructure.NVIC_IRQChannel = EXTI15_10_IRQn; // PA10 selects EXTI15_10
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; // Enable interrupt channel
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; // Preemption priority, the value range must comply with the specifications of the previous grouping
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; // Response priority, the value range must comply with the specifications of the previous grouping
NVIC_Init( & amp;NVIC_InitStructure);

(7) Write an interrupt service function

void EXTI15_10_IRQHandler(void)
{<!-- -->
if (EXTI_GetITStatus(EXTI_Line10) == SET) {<!-- --> // Determine whether the pending register corresponding to PX10 is set. If it is set, an interrupt has occurred.
EXTI_ClearITPendingBit(EXTI_Line10); // Clear the interrupt flag bit
// Handle your interrupts ...
}
}

Why do we need to clear the interrupt flag bit in the interrupt service function?
Answer: After STM32 generates an interrupt signal, the interrupt flag bit will be set to 1 by hardware. Therefore, when processing the external interrupt signal, the interrupt service routine should reset the interrupt flag bit to “0” in the final clearing operation to ensure that the system normal operation. If the interrupt flag bit is not cleared, even if the interrupt signal has been processed, the processor will still think that the interrupt signal has not been processed, and will remain in the interrupt state and cannot handle the next interrupt.

6.Appendix

(1) Library function for software-triggered interrupts.

void EXTI_GenerateSWInterrupt(uint32_t EXTI_Line);