[En-Nut-Discussion] NutExitCritical() behaviour on ARM Cortex-M

Philipp Burch phip at hb9etc.ch
Thu Dec 5 06:21:03 CET 2019


Hi everyone,

I usually only work with critical sections that disable a specific
interrupt known to access the resource to be protected. But now I have
some code which may be accessed from different interrupts, so I would
like to have a critical section that disables interrupts globally on an
ARM Cortex-M.

For those processors, NutEnterCritical() and NutExitCritical() are
defined in arch/cm3/atom.h as follows:

#define NutEnterCritical() \
{ \
    asm volatile (  \
        "@ NutEnterCritical"    "\n\t" \
        "mrs     r0, PRIMASK"   "\n\t" \
        "cpsid   i"             "\n\t" \
        :::"r0" \
    ); \
}

#define NutExitCritical() \
    {\
        asm volatile ( \
        "@ NutExitCritical"     "\n\t" \
        "mrs     r0, PRIMASK"   "\n\t" \
        "cpsie   i"             "\n\t" \
        :::"r0" \
    ); \
}

But I really can't figure out how this is supposed to work.
NutEnterCritical() seems more or less reasonable. It moves state into r0
and then disables the interrupts. Only: What happens to the stored state
in r0? As far as I understand it, the clobber just tells the compiler
that the code modifies the contents of r0 and it needs to restore them
afterwards, but not to actually save the contents in r0 to be used
afterwards.
Now, what about NutExitCritical()? This seems to again move state *into*
r0 and then enables the interrupts. But isn't it the idea to read the
stored state and put it into PRIMASK to restore the interrupt flag to
what it was before NutEnterCritical()?
Additionally, the code disabling single interrupts required me to insert
__DSB(); __ISB(); to avoid spurious interrupts to occur at the beginning
of the critical section. Maybe these should be included.
https://electronics.stackexchange.com/a/415138 also suggests to add
"memory" and "cc" clobbers to the inline assembly code.

Am I just missing something in the current implementation?

Thank you and best regards,
Philipp


More information about the En-Nut-Discussion mailing list