This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

consistent support in sd_* wrapper functions

The documentation for S110 v7.1.0 sd_nvic_ClearPendingIRQ implies that it works with any valid IRQ.

I find that (using S110 v7.1.0 with SDK 7.1.0):

  sd_nvic_ClearPendingIRQ(UART0_IRQn);

generates a hard fault while

  NVIC_ClearPendingIRQ(UART0_IRQn);

works fine, in an application which has already started the soft device.

Am I doing something wrong, or is it not only unnecessary but actively wrong to invoke the wrapper functions with peripherals that are not restricted by the soft device? This comment suggests it's supposed to be OK.

(I'm writing code that is supposed to be independent of what soft-device it's running with, so am not trying to guess whether a particular peripheral is restricted or not.)

Parents
  • Yes you can and should use the sd_ wrappers to enable/disable/clear interrupts whether they are restricted or not. Those functions check (if the softdevice is active) the peripheral you are working with to ensure it's not restricted (and error if it is). In this case clearly you are using UART0 which isn't restricted, so that's not the problem.

    Where are you calling this from? Are you calling it from an interrupt handler? The sd_* calls all just emit a svc instruction. The priority of that interrupt (from the softdevice manual) is Upper Stack which is '2'. If you are running in Application High (which is interrupt level '1') or from one of the timeslot API callbacks which runs in 'Lower Stack', (which is '0') then the svc call will hardfault as you can't call a lower priority interrupt from a higher priority one.

    And yes I find it infinitely confusing that the lower priority user interrupt level is called 'Application Low' and the higher one 'Application High', however the highest priority in the softdevice is the 'Lower Stack' and the lower priority is the 'Upper Stack'.

    If you aren't calling this from an interrupt handler or similar, then it should work. If you are calling it from one, then switching that interrupt to priority NRF_APP_PRIORITY_LOW should work.

Reply
  • Yes you can and should use the sd_ wrappers to enable/disable/clear interrupts whether they are restricted or not. Those functions check (if the softdevice is active) the peripheral you are working with to ensure it's not restricted (and error if it is). In this case clearly you are using UART0 which isn't restricted, so that's not the problem.

    Where are you calling this from? Are you calling it from an interrupt handler? The sd_* calls all just emit a svc instruction. The priority of that interrupt (from the softdevice manual) is Upper Stack which is '2'. If you are running in Application High (which is interrupt level '1') or from one of the timeslot API callbacks which runs in 'Lower Stack', (which is '0') then the svc call will hardfault as you can't call a lower priority interrupt from a higher priority one.

    And yes I find it infinitely confusing that the lower priority user interrupt level is called 'Application Low' and the higher one 'Application High', however the highest priority in the softdevice is the 'Lower Stack' and the lower priority is the 'Upper Stack'.

    If you aren't calling this from an interrupt handler or similar, then it should work. If you are calling it from one, then switching that interrupt to priority NRF_APP_PRIORITY_LOW should work.

Children
  • the svc call will hardfault as you can't call a lower priority interrupt from a higher priority one.

    Thanks; that provided the clue. I wasn't calling from an interrupt handler, but I was calling it from an initialization sequence during which interrupts were disabled. Perfectly fine with the standard CMSIS function which just writes a register. Not fine with the svc instruction

    FWIW, I've pretty well committed to not using these wrappers for peripherals that are "open" under the SD. The overhead of the SVC interrupt compared with a single instruction is too high; worse, the SD wrappers error if the soft device is disabled and one potential application architecture involves turning off the SD completely to control the radio. I'm hoping the multiprotocol support meets the requirements of the existing application so this won't be necessary, but I can't be sure yet.

Related