From 0d6da44029a54eafbe4fdfa1cdc64f3d52020544 Mon Sep 17 00:00:00 2001 From: Ian Rees Date: Wed, 7 May 2025 21:57:01 +1200 Subject: [PATCH] Document asm::delay() behaviour more thoroughly --- cortex-m/src/asm.rs | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/cortex-m/src/asm.rs b/cortex-m/src/asm.rs index 47b286a4..477a5f71 100644 --- a/cortex-m/src/asm.rs +++ b/cortex-m/src/asm.rs @@ -16,13 +16,18 @@ pub fn bkpt() { /// Blocks the program for *at least* `cycles` CPU cycles. /// -/// This is implemented in assembly so its execution time is independent of the optimization -/// level, however it is dependent on the specific architecture and core configuration. +/// This is implemented in assembly as a fixed number of iterations of a loop, so that execution +/// time is independent of the optimization level. /// -/// NOTE that the delay can take much longer if interrupts are serviced during its execution -/// and the execution time may vary with other factors. This delay is mainly useful for simple -/// timer-less initialization of peripherals if and only if accurate timing is not essential. In -/// any other case please use a more accurate method to produce a delay. +/// The loop code is the same for all architectures, however the number of CPU cycles required for +/// one iteration varies substantially between architectures. This means that with a 48MHz CPU +/// clock, a call to `delay(48_000_000)` is guaranteed to take at least 1 second, but for example +/// could take 2 seconds. +/// +/// NOTE that the delay can take much longer if interrupts are serviced during its execution and the +/// execution time may vary with other factors. This delay is mainly useful for simple timer-less +/// initialization of peripherals if and only if accurate timing is not essential. In any other case +/// please use a more accurate method to produce a delay. #[cfg(cortex_m)] #[inline] pub fn delay(cycles: u32) { @@ -33,9 +38,9 @@ pub fn delay(cycles: u32) { let real_cycles = 1 + cycles / 2; unsafe { asm!( - // The `bne` on some cores (eg Cortex-M4) will take a different number of instructions + // The `bne` on some cores (eg Cortex-M4) will take a different number of cycles // depending on the alignment of the branch target. Set the alignment of the top of the - // loop to prevent surprising timing changes when the alignment of the delay() changes. + // loop to prevent surprising timing changes when the alignment of `fn delay()` changes. ".p2align 3", // Use local labels to avoid R_ARM_THM_JUMP8 relocations which fail on thumbv6m. "1:",