MarkP
MarkP

Reputation: 4288

Counting cycles on Cortex M0+

I have a Cortex M0+ (SAML21) board that I'm using for performance testing. I'd like to measure how many cycles a given piece of code takes. I tried using DWT (DWT_CONTROL), but it never produced a result; it returned 0 cycles regardless of what code ran.

  // enable the use DWT
  *DEMCR = *DEMCR | 0x01000000;

  // Reset cycle counter
  *DWT_CYCCNT = 0;

  // enable cycle counter
  *DWT_CONTROL = *DWT_CONTROL | 1 ;
  // some code here
  // .....

  // number of cycles stored in count variable
  count = *DWT_CYCCNT;

Is there a way to count cycles (perhaps with an interrupt and counter?) much like I can query for milliseconds (eg. millis() on Arduino)?

Upvotes: 2

Views: 3258

Answers (2)

Arsenal
Arsenal

Reputation: 362

I cannot find any mention of the cycle counter register in the ARMv6-M Architecture Reference Manual.

So I'd say, this is not possible with an internal counter like it is in the bigger siblings like the M3, M4 and so on.

This is also stated in this knowledge base article:

This article was written for Cortex-M3 and Cortex-M4, but the same points apply to Cortex-M7, Cortex-M33 and Cortex-M55. Newer Cortex-M processors at the higher end of performance, such as Cortex-M55, may include an extended Performance Motnioring Unit that provides additional preformance measuring capabilities, but these are outside the scope of this article. The smaller Cortex-M processors such as Cortex-M0, Cortex-M0+ and Cortex-M23 do not include the DWT capabilities described here, and, other than the Cortex-M23, do not include ETM instruction trace, but all Cortex-M processors provide the "tarmac" capability for the chip designers.

(Emphasis mine)

So other means have to be used:

  • some debuggers can measure the time between hitting two breakpoints (or between two stops), the accuracy of this is usually limited by interacting with the OS, so can easily be in the order of 20 ms
  • use an internal timer with high enough clock frequency to give reasonable results and start / stop it before and after the interesting region
  • toggle a pin and measure the time with a logic analyzer / oscilloscope

Upvotes: 4

andy mango
andy mango

Reputation: 1551

According to the CMSIS header file for the M0+ (core_cm0plus.h), the Core Debug Registers are only accessible over the Debug Access Port and not via the processor. I can only suggest using some free running timer (maybe SysTick) or perhaps your debugger can be of some help to get access to the required registers.

Upvotes: 1

Related Questions