Fallback implementation based on disabling interrupts or critical-section
December 26, 2025 · View on GitHub
This module supports two different critical section implementations:
- Built-in "disable all interrupts".
- On MSP430 and AVR, they are always single-core and has no unprivileged mode, so this is enabled by default.
- On Armv6-M (thumbv6m), pre-v6 Arm (e.g., thumbv4t, thumbv5te), RISC-V without A-extension, and Xtensa, they could be multi-core or unprivileged mode, so this is enabled when the user explicitly declares that the system is single-core and that privileged instructions are available using
unsafe-assume-single-corefeature (orportable_atomic_unsafe_assume_single_corecfg).
- Call into the
critical-sectioncrate (which allows the user to plug any implementation).- This is enabled when the user asks for it with the
critical-sectionfeature.
- This is enabled when the user asks for it with the
unsafe-assume-privileged feature (portable_atomic_unsafe_assume_privileged cfg) also uses this module's interrupt disable implementation part.
The unsafe-assume-single-core implementation uses privileged instructions to disable interrupts, so it usually doesn't work on unprivileged mode.
Enabling this feature in an environment where privileged instructions are not available, or if the instructions used are not sufficient to disable interrupts in the system, it is also usually considered unsound, although the details are system-dependent.
Consider using the critical-section feature for systems that cannot use the unsafe-assume-single-core feature (or portable_atomic_unsafe_assume_single_core cfg).
For some targets, the implementation can be changed by explicitly enabling features.
- On Arm M-Profile architectures, this disables interrupts by modifying the PRIMASK register.
- On Arm (except for M-Profile architectures), this disables interrupts by modifying the I (IRQ mask) bit of the CPSR.
- On Arm (except for M-Profile architectures) with the
disable-fiqfeature (orportable_atomic_disable_fiqcfg), this disables interrupts by modifying the I (IRQ mask) bit and F (FIQ mask) bit of the CPSR. - On RISC-V, this disables interrupts by modifying the MIE (Machine Interrupt Enable) bit of the
mstatusregister. - On RISC-V with the
s-modefeature (orportable_atomic_s_modecfg), this disables interrupts by modifying the SIE (Supervisor Interrupt Enable) bit of thesstatusregister. - On RISC-V with the
zaamotarget feature (orforce-amofeature orportable_atomic_force_amocfg), this uses AMO instructions for RMWs that have corresponding AMO instructions even if A-extension is disabled. For other RMWs, this disables interrupts as usual. - On MSP430, this disables interrupts by modifying the GIE (Global Interrupt Enable) bit of the status register (SR).
- On AVR, this disables interrupts by modifying the I (Global Interrupt Enable) bit of the status register (SREG).
- On Xtensa, this disables interrupts by modifying the PS special register.
Some operations don't require disabling interrupts:
- On architectures except for AVR: loads and stores with pointer size or smaller
- On AVR: 8-bit loads and stores
- On AVR with
rmwtarget feature additionally: 8-bitswap - On MSP430 additionally: {8,16}-bit
add,sub,and,or,xor,not - On RISC-V with the
zaamotarget feature (orportable_atomic_target_feature="zaamo"cfg orforce-amofeature orportable_atomic_force_amocfg) additionally: 32-bit(RV32)/{32,64}-bit(RV64)swap,fetch_{add,sub,and,or,xor,not,max,min},add,sub,and,or,xor,not, {8,16}-bitfetch_{and,or,xor,not},and,or,xor,not1, and all operations ofAtomicBool
However, when the critical-section feature is enabled, critical sections are taken for all atomic operations.
Feel free to submit an issue if your target is not supported yet.
Footnotes
-
With the
zabhatarget feature, {8,16}-bitswap,fetch_{add,sub,max,min},add,subtoo. ↩