Author Topic: Most Efficient and Low-Power way to store ADC samples of STM32 to external Flash  (Read 2486 times)

0 Members and 1 Guest are viewing this topic.

Offline syntax333Topic starter

  • Regular Contributor
  • *
  • Posts: 158
  • Country: 00
Hi, I am currently working on a project which requires me to store ADC samples (Sampled by internal ADC of STM32) to an external SPI Flash.

I was thinking using DMA for connecting ADC peripheral to certain buffer to SPI peripheral (ADC->Buffer->SPI).

First DMA stream (ADC->Buffer) is set as double buffering. Second DMA stream (Buffer->SPI) is set as Normal Mode.

Process is described below.
  • Sleep while waiting until Buffer is full with ADC samples
  • Transmission complete flag is set by DMA and interrupt is occured
  • Inside ADC DMA interrupt, enable second DMA stream (which connects buffer and SPI) Note: No need to enable DMA interrupt for connection between buffer and SPI since SPI is guaranteed to have high speed thus transmission will finished before another interrupt by ADC DMA
  • Process repeats

While this process happens I want the STM32 to sleep as much as possible for low power consumption. Due to interrupt of first DMA stream Transmission complete , process described above causes STM32 to wakeup from sleep, clear TC flag, start second stream and sleep again.

My question: Is this the most efficient way to use DMA for this kind of transmission? or is there a way that eliminates the need for wakeup from sleep for enabling second DMA stream (Buffer->SPI)? Maybe "hidden" DMA capability which eliminates the need for wakeup from sleep and does the second DMA transmission without waking up CPU?

I have little experience with DMA so any information will be appreciated.

 
 

Offline ajb

  • Super Contributor
  • ***
  • Posts: 2820
  • Country: us
What is your sampling pattern? How many total bytes at what interval?
 

Offline bugnate

  • Regular Contributor
  • *
  • Posts: 58
  • Country: us
Is it really the case that you need no CPU intervention for the external SPI flash write, for instance to set addresses or other command formatting? I suppose you could have steered the SPI flash into a streaming write mode. I don't disbelieve you, just curious.

You should be able to find a list of DMA request triggers for your particular chip in the reference manual. Off hand, I could imagine setting a timer (synchronized with your ADC) that generates a DMA request at an appropriate interval to do your second transfer. However, I wouldn't do this. As someone who has spent a lot of time stressing over low power sampling at his day job as well as some uncomfortable dreams, I would humbly suggest you are overthinking the importance of the DMA angle. I don't claim you are wrong, rather that the optimization is small, DMA is prickly, and there is usually better and lower hanging fruit.

IMO, the CPU waking up (from Sleep) for a handful of microseconds to do a little house keeping every now and then isn't going to move the power needle. Sleep is lower power than Run mode, but often only something like 50% less power. Check your datasheet. This is decent, but only applies maybe 0.01% of the time. Anything you can do to attack the other 99.99% is what will count. You should either be looking at trying to use Stop mode OR taking steps to cut your base power. Using Stop mode requires some strategizing and may not be reasonable beyond low rates. For the latter, look into disabling un-needed clocks/peripherals and cut everything else to the bone at least when Sleeping. IIRC, I have a STM32F103 based product which cuts HCLK as low 125 kHz when sleeping for this reason. More recent or advanced devices will have more tricks available to help you here, especially I'd assume on the L-series.
 
The following users thanked this post: thm_w, syntax333

Offline syntax333Topic starter

  • Regular Contributor
  • *
  • Posts: 158
  • Country: 00
Thank you for your suggestions. I am now interested in what you said "product which cuts HCLK as low 125 kHz when sleeping". Am I understanding it wrong or do you mean lowering main clock speed before entering sleep mode? Is this possible or logical thing to do considering changing clock frequency while CPU is running may be slow for time critical applications? Doesn't it take too long to change clock frequency?
 

Offline bugnate

  • Regular Contributor
  • *
  • Posts: 58
  • Country: us
Thank you for your suggestions. I am now interested in what you said "product which cuts HCLK as low 125 kHz when sleeping". Am I understanding it wrong or do you mean lowering main clock speed before entering sleep mode? Is this possible or logical thing to do considering changing clock frequency while CPU is running may be slow for time critical applications? Doesn't it take too long to change clock frequency?

There are lots of details, but you basically have the idea. For instance, in your case you presumably need a consistent sample timer and (while sampling) a sampling clock, but apart from that you should be free to change the CPU clock. I'd suggest finding an architecture diagram in the datasheet or reference manual and running some experiments.

As to how long it takes, the worst case is starting up a crystal and locking a PLL which may be order of milliseconds. On the other hand, if you are for example using the HSI directly (no PLL) and only changing a clock divider, this should be far faster, I'd expect microseconds. If you are only doing light housekeeping at intervals, the latter should be closer to your needs. You absolutely should measure and reflect on whatever you implement of course.
 


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf