Measuring time in #[no_std] - cortex-m3 microcontroller

Hello dear Rustaceans :crab:,

I'm trying to port a Rust program to be run on QEMU with the configuration for LM3S6965, a Cortex-M3 microcontroller. (I've been following the Embedded Rust book :smile: )

The Rust program uses the duration_since function provided by std::time::SystemTime to measure time.

pub fn duration_since(
    &self,
    earlier: SystemTime
) -> Result<Duration, SystemTimeError>

I see that in the #[no_std] setting, there is no such convenient API provided by rust core library. So far, I couldn't find a helpful crate that provides an API for measuring time in embedded devices.

What would be an ergonomic way to measure time in #[no_std] code??
Would I need to write Rust code by myself that is specific to LM3S6965 ??

Any helpful pointers would be greatly appreciated! :heart_decoration: Thank you!

Do you only want to measure the complete length executed in qemu? Then I don't know, since I don't know which capability qemu has.

If you want to measure the time, also valid on the controller itself or only of a part of the program, then you have to initialize a timer (perioheral on the microcontroller), f.e. the Systick timer, start and evaluate it. The Systick timer is implemented in all Cortex-M processors. You can find online a lot C tutorial, which you can transform to rust and your specific controller (f.e. https://iotality.com/armcm-systick-timer/)

1 Like

That is what I want to do right now :smile: Your response is really helpful!
Thank you!

1 Like

I apparently saw that there is also a chapter of the embedded book about it:
https://docs.rust-embedded.org/book/peripherals/a-first-attempt.html

1 Like

Thanks for pointing that out!
I really should've posted this question after skimming through the whole book...

On cortex-m , I've often found the cycle-counter handy.

extern crate cortex_m;

use cortex_m::peripheral::{DWT, Peripherals};

fn main() {
    {
        let mut peripherals = Peripherals::take().unwrap();
        peripherals.DWT.enable_cycle_counter();
    } // all the peripheral singletons are destroyed here

    // but this method can be called without a DWT instance
    let cyccnt = DWT::get_cycle_count();
}
1 Like

Thanks for the suggestion :smiley:
I just tried using cycle-counter with the above code-sniipet on QEMU (target cortex-m3), but the cyccnt is always 0 regardless of how many times I call DWT::get_cycle_count() in code.. Could be a QEMU issue I guess :confused:

Oh ... Iā€™m brand new to Rust and qemu, but have used it in the C-World on the IAR compiler + simulator.