Hello,
Although I already used the nrf52840 on previous projects (nrfxlib), I'm a newbie using nRF Connect and ZephyrOS (I previously used RTOS).
I'm integrating a driver which uses a GPIO interrupt to trigger read of SPI bus. The driver isn't RTOS ready (no use of semaphores for wait loop).
I got an issue when the driver try to do a SPI access when in the interrupt context of gpio and I don't understand why.
I'm using a zigbee based example app, the driver initialization is done in the main thread (before initialization of the Zboss stack).
I configured the GPIO as (the interrupt is enabled later but calling the same API) :
The SPI is initialized as :
The interrupt handler just call the driver API to handle the interrupt API (which basically check sensor status and raise a flag to notify main loop)
On the driver side the code which fails is the following:
* In the main loop we just wait for the flag to raise
* In the GPIO interrupt callback we start a register read of sensor, which finally call spi_transceive :
Which cause the error :
ASSERTION FAIL @ WEST_TOPDIR/zephyr/kernel/sem.c:136 E: r0/a1: 0x00000004 r1/a2: 0x00000088 r2/a3: 0x00000000 E: r3/a4: 0x20009755 r12/ip: 0x00000000 r14/lr: 0x00026ad3 E: xpsr: 0x61000016 E: s[ 0]: 0x20005dcc s[ 1]: 0x00025a23 s[ 2]: 0x20000448 s[ 3]: 0x2000004c E: s[ 4]: 0x2000004c s[ 5]: 0x00000000 s[ 6]: 0x20009820 s[ 7]: 0x000577e7 E: s[ 8]: 0x00000000 s[ 9]: 0x0005d7f4 s[10]: 0x20000448 s[11]: 0x0000c9f9 E: s[12]: 0x2000004c s[13]: 0x00061e08 s[14]: 0x00000023 s[15]: 0x00000000 E: fpscr: 0x20009866 E: Faulting instruction address (r15/pc): 0x000554ec E: >>> ZEPHYR FATAL ERROR 4: Kernel panic on CPU 0 E: Fault during interrupt handling E: Current thread: 0x200023f0 (main)
When I debug the issue I can see that the issue is an assert fail when trying to lock SPI connect in spi_transceive :
1. Do I use the correct API for GPIO and SPI ? I saw that I could use nrfx API
2. What could cause this context lock whereas there is no SPI bus user ? Is there a limitation between GPIOTE interrupt context and SPI access ?
If I move the SPI access to main loop, I fix the issue:
* I add a semaphore in the GPIO interrupt:
* I move the processing done in GPIO interrupt (which does the SPI access) into a dedicated function : chdrv_int_process()
* In the main loop I add a wait of semaphore, then call the process function :
It works but it changes the driver's code which I want to avoid. I don't get why I have the issue (although I'm aware doing processing in the GPIO interrupt isn't the best practice).
Best regards
Gaël