GPIO edge interrupt priority and bluetooth interrupt priority

I am working on a project for the nRF52832 using nRF Connect SDK v2.2.0.

I have setup a GPIO interrupt on both edges using gpio_pin_interrupt_configure_dt, gpio_init_callback, and gpio_add_callback.

It seems to work fine : my callback function is called right after the edge interrupt occurs.

I have an issue though when I start to enable Bluetooth.

I know that when running, the Bluetooth stack can interrupt the system to handle Bluetooth events.

I would like to increase the priority of my GPIO interrupt (or decrease the priority of the Bluetooth event interrupt) so that I can reduce the latency on my GPIO interrupt callback.

My plan is to set the connection parameters so that packets can be lost without breaking the Bluetooth connection so that if the GPIO interrupt occurs and blocks / delays a Bluetooth event interrupt, the connection will stay active (probably using timeout and / or slave latency).

I have seen that the default interrupts for gpiote is configured as 'interrupts = <6 5>' in the nrf52832 device tree but I struggle to understand what 6 and 5 are and how to get the highest priority possible. I also have not found how to reduce the priority level of the Bluetooth events.

Regards

  • I would like to increase the priority of my GPIO interrupt (or decrease the priority of the Bluetooth event interrupt) so that I can reduce the latency on my GPIO interrupt callback.

    My plan is to set the connection parameters so that packets can be lost without breaking the Bluetooth connection so that if the GPIO interrupt occurs and blocks / delays a Bluetooth event interrupt, the connection will stay active (probably using timeout and / or slave latency).

    Sorry, this is not possible, you will quickly get an assert from the softdevice controller if you try to delay it's operations. The only way something like this can be done is to use the nRF5340, where there are two cores (network core and application core). In the application core you have full freedom of which interrupt have highest priority depending on the application.

    Kenneth

  • Thanks for your response. I was afraid that you would say that indeed.

    I am looking at the nRF52 datasheet and am discovering the PPI module.

    Do you think it would be possible to use PPI to configure the GPIOTE interrupt to read a timer value using Timer Capture and then do the processing when the ISR gets executed ? Is there a risk to miss any interrupt in this case ?

    Also: is there an API for using PPI with nRF Connect SDK / Zephyr ? I am only seeing a PPI trace module but I don't think that's the same thing.

  • It's not entirely clear what is the main challeng you are trying to solve here, typically it's not a problem that there is a small delay of handling a gpiote interrupt, but if you have a wakeup condition where the duration of the gpio signal is so short that you are worried that the gpio may have returned back to the default state by the time the gpiote interrupt is executed, then there is a latch register that you can read to check which pin that triggered the wakeup:
    https://infocenter.nordicsemi.com/topic/com.nordic.infocenter.nrf52832.ps.v1.1/gpio.html#register.LATCH 

    It's also possible to configure ppi channels between for instance gpiote events and timer operations (e.g start, stop, or capture), however you would need to setup this manually using the nrfx directly, something like:
    https://github.com/zephyrproject-rtos/zephyr/tree/main/samples/boards/nrf/nrfx 

    Kenneth

  • I'll clarify what I want to do : I need to measure precisely the time between GPIO edges in microseconds.

    My original implementation used a gpiote configured on both edges with an ISR (through gpio-keys module inthe device tree). In the ISR, I read the timer value and compare it to the previous execution of the ISR.

    So here when I get delayed because of the Bluetooth stack, the timing I read is wrong.

    I am looking at PPI channel and I think this is what I want. Is there any code example using the GPIOTE event to trigger a timer capture ? Most of the example I have found use the PPI in the other direction (toggle a pin from a timer value)

  • Then I can understand what you want to do, then my suggestion is to look at the example I shared, in specific I can see the example I shared created an ppi channel between an gpiote IN event and a GPIOTE out task, in your case you need to start a timer, and replace the GPIOTE out task with an TIMER capture task:
    https://github.com/zephyrproject-rtos/zephyr/blob/main/samples/boards/nrf/nrfx/src/main.c#L124 

    Kenenth

Related