2019-09-24 07:01 PM
I am witnessing interrupts on EXTI9_5 line which have absolutely no electrical stimulus. I'm seeing this behavior consistently on multiple chips so this isn't a one-off.
The GPIO in question (ONE_WIRE_PIN) is PA8.
GPIO initialization here:
mIRQConfig.Pin = ONE_WIRE_PIN;
mIRQConfig.Mode = GPIO_MODE_IT_FALLING;
mIRQConfig.Pull = GPIO_NOPULL;
mIRQConfig.Speed = GPIO_SPEED_FREQ_HIGH;
HAL_GPIO_Init(ONE_WIRE_PORT, &mIRQConfig);
Here is the interrupt routine:
void EXTI9_5_IRQHandler(void)
{
if ( EXTI->PR & ONE_WIRE_PIN )
{
HAL_GPIO_EXTI_IRQHandler(ONE_WIRE_PIN);
}
else if ( EXTI->PR & POWER_INT_PIN )
{
HAL_GPIO_EXTI_IRQHandler(POWER_INT_PIN);
}
else if ( EXTI->PR & TOUCH_INT_PIN )
{
HAL_GPIO_EXTI_IRQHandler(TOUCH_INT_PIN);
}
}
The HAL_GPIO_EXTI_IRQHandler is the vanilla implementation in the HAL:
void HAL_GPIO_EXTI_IRQHandler(uint16_t GPIO_Pin)
{
/* EXTI line interrupt detected */
if(__HAL_GPIO_EXTI_GET_IT(GPIO_Pin) != RESET)
{
__HAL_GPIO_EXTI_CLEAR_IT(GPIO_Pin);
HAL_GPIO_EXTI_Callback(GPIO_Pin);
}
}
And my callback is:
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
switch(GPIO_Pin)
{
case TOUCH_INT_PIN:
{
ewd1020_touch_int();
}
break;
case POWER_INT_PIN:
{
max17043_clear_alert();
}
break;
case ONE_WIRE_PIN:
{
singleWireSerialFallingEdge();
}
break;
}
}
The oscilloscope shows a constant voltage of 1.8V on that pin (VCC), with no falling edge triggering. Pullup resistor is external. Clearly, there is no electrical cause for this interrupt.
The interrupts occur as soon as USART2 becomes active. This is 100% repeatable and reproducible.
What could possibly be causing this? I've been working on this processor for 3 years now and I've seen my share of weirdness, but this takes the cake. Is there any HAL bug or misconfiguration that is even capable of exhibiting this behavior?
UPDATE:
One possible explanation for this problem might be a corruption of the interrupt vector. This is defined below. What would be a good way to validate the integrity of the vector at run time?
The OS is FreeRTOS 9.
__attribute__ ((section(".isr_vectors"), used))
void (* const g_pfnVectors[])(void) = {
(void (*)(void))((unsigned long)&__stack_end__),
ResetISR,
NMI_Handler,
HardFault_Handler,
MemManage_Handler,
BusFault_Handler,
UsageFault_Handler,
(void (*)(void))((unsigned long)&__valid_user_code_checksum),
Unexpected_Handler,
Unexpected_Handler,
Unexpected_Handler,
SVC_Handler,
DebugMon_Handler,
Unexpected_Handler,
PendSV_Handler,
SysTick_Handler,
WWDG_IRQHandler, // Window WatchDog
PVD_IRQHandler, // PVD through EXTI Line detection
TAMP_STAMP_IRQHandler, // Tamper and TimeStamps through the EXTI line
RTC_WKUP_IRQHandler, // RTC Wakeup through the EXTI line
FLASH_IRQHandler, // FLASH
RCC_IRQHandler, // RCC
EXTI0_IRQHandler, // EXTI Line0
EXTI1_IRQHandler, // EXTI Line1
EXTI2_IRQHandler, // EXTI Line2
EXTI3_IRQHandler, // EXTI Line3
EXTI4_IRQHandler, // EXTI Line4
DMA1_Stream0_IRQHandler, // DMA1 Stream 0
DMA1_Stream1_IRQHandler, // DMA1 Stream 1
DMA1_Stream2_IRQHandler, // DMA1 Stream 2
DMA1_Stream3_IRQHandler, // DMA1 Stream 3
DMA1_Stream4_IRQHandler, // DMA1 Stream 4
DMA1_Stream5_IRQHandler, // DMA1 Stream 5
DMA1_Stream6_IRQHandler, // DMA1 Stream 6
ADC_IRQHandler, // ADC1, ADC2 and ADC3s
CAN1_TX_IRQHandler, // CAN1 TX
CAN1_RX0_IRQHandler, // CAN1 RX0
CAN1_RX1_IRQHandler, // CAN1 RX1
CAN1_SCE_IRQHandler, // CAN1 SCE
EXTI9_5_IRQHandler, // External Line[9:5]s
TIM1_BRK_TIM9_IRQHandler, // TIM1 Break and TIM9
TIM1_UP_TIM10_IRQHandler, // TIM1 Update and TIM10
TIM1_TRG_COM_TIM11_IRQHandler, // TIM1 Trigger and Commutation and TIM11
TIM1_CC_IRQHandler, // TIM1 Capture Compare
TIM2_IRQHandler, // TIM2
TIM3_IRQHandler, // TIM3
TIM4_IRQHandler, // TIM4
I2C1_EV_IRQHandler, // I2C1 Event
I2C1_ER_IRQHandler, // I2C1 Error
I2C2_EV_IRQHandler, // I2C2 Event
I2C2_ER_IRQHandler, // I2C2 Error
SPI1_IRQHandler, // SPI1
SPI2_IRQHandler, // SPI2
USART1_IRQHandler, // USART1
USART2_IRQHandler, // USART2
USART3_IRQHandler, // USART3
EXTI15_10_IRQHandler, // External Line[15:10]s
RTC_Alarm_IRQHandler, // RTC Alarm (A and B) through EXTI Line
OTG_FS_WKUP_IRQHandler, // USB OTG FS Wakeup through EXTI line
TIM8_BRK_TIM12_IRQHandler, // TIM8 Break and TIM12
TIM8_UP_TIM13_IRQHandler, // TIM8 Update and TIM13
TIM8_TRG_COM_TIM14_IRQHandler, // TIM8 Trigger and Commutation and TIM14
TIM8_CC_IRQHandler, // TIM8 Capture Compare
DMA1_Stream7_IRQHandler, // DMA1 Stream7
FMC_IRQHandler, // FMC
SDIO_IRQHandler, // SDIO
TIM5_IRQHandler, // TIM5
SPI3_IRQHandler, // SPI3
UART4_IRQHandler, // UART4
UART5_IRQHandler, // UART5
TIM6_DAC_IRQHandler, // TIM6 and DAC1&2 underrun errors
TIM7_IRQHandler, // TIM7
DMA2_Stream0_IRQHandler, // DMA2 Stream 0
DMA2_Stream1_IRQHandler, // DMA2 Stream 1
DMA2_Stream2_IRQHandler, // DMA2 Stream 2
DMA2_Stream3_IRQHandler, // DMA2 Stream 3
DMA2_Stream4_IRQHandler, // DMA2 Stream 4
ETH_IRQHandler, // Ethernet
ETH_WKUP_IRQHandler, // Ethernet Wakeup through EXTI line
CAN2_TX_IRQHandler, // CAN2 TX
CAN2_RX0_IRQHandler, // CAN2 RX0
CAN2_RX1_IRQHandler, // CAN2 RX1
CAN2_SCE_IRQHandler, // CAN2 SCE
OTG_FS_IRQHandler, // USB OTG FS
DMA2_Stream5_IRQHandler, // DMA2 Stream 5
DMA2_Stream6_IRQHandler, // DMA2 Stream 6
DMA2_Stream7_IRQHandler, // DMA2 Stream 7
USART6_IRQHandler, // USART6
I2C3_EV_IRQHandler, // I2C3 event
I2C3_ER_IRQHandler, // I2C3 error
OTG_HS_EP1_OUT_IRQHandler, // USB OTG HS End Point 1 Out
OTG_HS_EP1_IN_IRQHandler, // USB OTG HS End Point 1 In
OTG_HS_WKUP_IRQHandler, // USB OTG HS Wakeup through EXTI
OTG_HS_IRQHandler, // USB OTG HS
DCMI_IRQHandler, // DCMI
CRYP_IRQHandler, // CRYP crypto
HASH_RNG_IRQHandler, // Hash and Rng
FPU_IRQHandler, // FPU
UART7_IRQHandler, // UART7
UART8_IRQHandler, // UART8
SPI4_IRQHandler, // SPI4
SPI5_IRQHandler, // SPI5
SPI6_IRQHandler, // SPI6
SAI1_IRQHandler, // SAI1
LTDC_IRQHandler, // LTDC
LTDC_ER_IRQHandler, // LTDC error
DMA2D_IRQHandler, // DMA2D
QUADSPI_IRQHandler, // QUADSPI
DSI_IRQHandler, // DSI
};
2019-09-24 10:59 PM
> absolutely no electrical stimulus
Connect it directly to GND to be sure.
JW
2019-09-25 10:54 AM
Grounding defeats it. But it's supposed to be a falling edge and the scope doesn't detect anything. I've set the threshold to 1.72V with a VCC of 1.8V and it's not triggering on the scope, so why would it trigger inside the GPIO?
2019-09-27 02:28 AM
Maybe because your scope+probe+grounding arrangement is not fast enough to capture short spikes the EXTI pin sees.
JW
2019-09-27 08:29 AM
Switching from PA8 to PB14 resolved the issue. This will remain a mystery for now.