Skip to main content
Graduate
November 24, 2024
Solved

Pushbutton causing multiple ISR flags (EXT-> PR) to set??

  • November 24, 2024
  • 2 replies
  • 1904 views

So I have three switches (nothing special just momentary push button) wired into the board PC2, PC3 and PA4. All are using internal pullups. PC2 and PC3 are set for rising / falling trigger IRQs and PA4 is set for falling IRQ. They all have their own ISR function and use a single callback. I am monitoring EXT -> PR register (interrupt flag) and I notice that when I push one of the buttons it will sometimes set 1, 2 or even all 3 of the flags and I never touch the other buttons. Here is an example of me pushing PC2 and 2,3,4 all went off. Sometimes only the one I want goes off as I would expect but many times multiple flags get set. There is nothing else on top of the board. It is a Nucleo-F401RE. Any ideas as to what could be going on here as I am totally confused?

SWenn1_0-1732482589937.png

 

    This topic has been closed for replies.
    Best answer by SWenn.1

    I seemed to have solved the issue.....Not completely sure but so far no false triggers have appeared. I mimicked the blue button on the nucleo board with respect to adding 100 ohm resistor between 0.1uF cap and ground.

     

    PXL_20241125_201428989.jpg

    2 replies

    Super User
    November 24, 2024

    Maybe EM (capacitive) coupling between the pins, especially if the related wires/tracks are run next to each other.

    The EXTI is asynchronous and it can react to pulses shorter than the system clock period.

    JW

    SWenn.1Author
    Graduate
    November 25, 2024

    Good thought but no....I wired 0.1uF capacitors across both switches and shortened wiring.....This should be ridiculously simple, not sure what is going on....Low level code that clears PR suggests to set register using = instead of |= ....I set breakpoints with the handlers .... _it.c file on each switch and after pushing one switch check the PR flags to find both flags getting set???

    Could it be something with the switches using both rising and falling edges?  I used CubeMX to initialize this 

     /*Configure GPIO pins : swExpand_Pin swCompress_Pin */
     GPIO_InitStruct.Pin = swExpand_Pin|swCompress_Pin;
     GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING_FALLING;
     GPIO_InitStruct.Pull = GPIO_PULLUP;
     HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);

    Here are my blocks of code if this helps  (handlers in ..._it.c file) these two pins are rising / falling edges

    void EXTI2_IRQHandler(void)
    {
     /* USER CODE BEGIN EXTI2_IRQn 0 */
    
     /* USER CODE END EXTI2_IRQn 0 */
     HAL_GPIO_EXTI_IRQHandler(swExpand_Pin);
     /* USER CODE BEGIN EXTI2_IRQn 1 */
    
     /* USER CODE END EXTI2_IRQn 1 */
    }
    
    /**
     * @brief This function handles EXTI line3 interrupt.
     */
    void EXTI3_IRQHandler(void)
    {
     /* USER CODE BEGIN EXTI3_IRQn 0 */
    
     /* USER CODE END EXTI3_IRQn 0 */
     HAL_GPIO_EXTI_IRQHandler(swCompress_Pin);
     /* USER CODE BEGIN EXTI3_IRQn 1 */
    
     /* USER CODE END EXTI3_IRQn 1 */
    }

     Actual IRQ handler ( ...._hal_gpio.c)

    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);
     }
    }

     Callback itself (main.c) ...Pushing either swCompress or swExpand switch most times causes multiple flags to go off (PC2 and PC3).  I disable the IRQ in the callback and wait for a timer to go off 100ms later (debounce) and within the timer I read the GPIO level

    void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
    {
    	if (GPIO_Pin == swCompress_Pin)
    	{
    		EXTI->IMR &= ~(swCompress_Pin); //disable further button action
    		//**********debounce routine***************
    		__HAL_TIM_SET_COMPARE(&htim1, TIM_CHANNEL_1, DEBOUNCE_TIME);
    		__HAL_TIM_CLEAR_FLAG(&htim1, TIM_FLAG_CC1);
    		__HAL_TIM_ENABLE_IT(&htim1, TIM_IT_CC1);
    		//*****************************************
    	}
    
    	if (GPIO_Pin == swExpand_Pin)
    	{
    		EXTI->IMR &= ~(swExpand_Pin); //disable further button action
    		//**********debounce routine***************
    		__HAL_TIM_SET_COMPARE(&htim1, TIM_CHANNEL_1, DEBOUNCE_TIME);
    		__HAL_TIM_CLEAR_FLAG(&htim1, TIM_FLAG_CC1);
    		__HAL_TIM_ENABLE_IT(&htim1, TIM_IT_CC1);
    		//*****************************************
    	}
    
    	if (GPIO_Pin == B1_Pin)
    	{
    		motor.upperBoundValue = 0;
    		motor.lowerBoundValue = 0;
    		ISR.program = T;
    	}
    
    	if (GPIO_Pin == flashErase_Pin)
    	{
    		EXTI->IMR &= ~(flashErase_Pin);
    		//ISR.erase = T;
    	}
    }

      Thanks

    Technical Moderator
    November 25, 2024

    Hello,

    Why are you setting for both edges: falling and rising? 

     

    Super User
    November 25, 2024

    What else do you do in that program?

    What else do you have connected to that board?

    JW

    SWenn.1Author
    Graduate
    November 25, 2024

    This will be driving a NEMA stepper motor with an IHM03A1 stacked onto the Nucleo-F401 ....HOWEVER I have removed the stack and the motor and still have the issue....  I am not running anything on the board and it LITERALLY sits there and waits for an ISR pushbutton .... One button will move motor FORWARD, the other BACKWARD.  The buttons use both edges as the falling edge triggers to advance motor and the rising edge releases the motor from running.....