cancel
Showing results for 
Search instead for 
Did you mean: 

Variable frequency pulse train for pulse transformer application

arre24
Associate II
Posted on August 22, 2012 at 17:22

Hi

The objective is to create a

variable frequency

pulse train with as little CPU intervention as possible.

This was quite straightforward with the TMS320 TI MCU. It had a feature called ''PWM chopper'' where it was possible to configure frequency, pulse width, duty cycle and number of pulses.

To achieve the same kind of functionality with the STM32F4, the idea that first came to mind was to use the Advanced Control Timer & DMA peripheral.

A table which consists of the timer periods that define the pulse train characteristics is setup in RAM. The have the DMA transfer these values to the timer compare register using memory increment mode. The timer output pin is configured to toggle at every compare match. 

Also, it is desired to have control of the time interval between each consecutive pulse train. Therefore a timer capture/compare interrupt is enabled. In the interrupt, the pulse train starting time (first positive flank) is defined as:

Current time (time when the interrupt occurs) + A settable delay

The time when the next interrupt occurs is also settable.

The questions are:

1) Is the method described above possible with the STM32F4?

2) Are there any other ways to get the same result?
53 REPLIES 53
Posted on March 24, 2015 at 17:57

Is there a reason to configure the timer as maximal, rather than at 5000, or 10000? At 5000 you'd keep getting an interrupt every 5ms and the counter would wrap automatically.

The purpose of HT/TC would be to keep a streaming DMA operation to be sustained.

If there is adequate time between the 19th sample being loaded, and subsequently firing, you couple perhaps just service the TC

With a 38 sample buffer, HT/TC would fire at 19 sample intervals, allowing you to update the after-next portion of the table.

How many of the 19 forward, vs 19 backward, sequences do you normally expect to send?

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
webmaster
Associate II
Posted on March 24, 2015 at 20:32

I've also tried this.

void DMA2_Stream1_IRQHandler(void)
{
if (DMA_GetITStatus(DMA2_Stream1, DMA_IT_TCIF1))
{
// Transfer complete.
DMA_ClearITPendingBit(DMA2_Stream1, DMA_IT_TCIF1);
if (semiciclo)
{
TIM1->CCR1 = SRC_Buffer[0] = 233;//Tabla_Buffer [0];
SRC_Buffer[1] Tabla_Buffer [1];
SRC_Buffer[2] Tabla_Buffer [2];
SRC_Buffer[3] Tabla_Buffer [3];
SRC_Buffer[4] Tabla_Buffer [4];
SRC_Buffer[5] Tabla_Buffer [5];
SRC_Buffer[6] Tabla_Buffer [6];
SRC_Buffer[7] Tabla_Buffer [7];
SRC_Buffer[8] Tabla_Buffer [8];
SRC_Buffer[9] Tabla_Buffer [9];
SRC_Buffer[10] Tabla_Buffer [10];
SRC_Buffer[11] Tabla_Buffer [11];
SRC_Buffer[12] Tabla_Buffer [12];
SRC_Buffer[13] Tabla_Buffer [13];
SRC_Buffer[14] Tabla_Buffer [14];
SRC_Buffer[15] Tabla_Buffer [15];
SRC_Buffer[16] Tabla_Buffer [16];
SRC_Buffer[17] Tabla_Buffer [17];
SRC_Buffer[18] Tabla_Buffer [18];
}
else
{
TIM1->CCR1 = SRC_Buffer[0] = 1756;//(5000 - Tabla_Buffer [18]);
SRC_Buffer[1] (5000 - Tabla_Buffer [17]);
SRC_Buffer[2] (5000 - Tabla_Buffer [16]);
SRC_Buffer[3] (5000 - Tabla_Buffer [15]);
SRC_Buffer[4] (5000 - Tabla_Buffer [14]);
SRC_Buffer[5] (5000 - Tabla_Buffer [13]);
SRC_Buffer[6] (5000 - Tabla_Buffer [12]);
SRC_Buffer[7] (5000 - Tabla_Buffer [11]);
SRC_Buffer[8] (5000 - Tabla_Buffer [10]);
SRC_Buffer[9] (5000 - Tabla_Buffer [9]);
SRC_Buffer[10] (5000 - Tabla_Buffer [8]);
SRC_Buffer[11] (5000 - Tabla_Buffer [7]);
SRC_Buffer[12] (5000 - Tabla_Buffer [6]);
SRC_Buffer[13] (5000 - Tabla_Buffer [5]);
SRC_Buffer[14] (5000 - Tabla_Buffer [4]);
SRC_Buffer[15] (5000 - Tabla_Buffer [3]);
SRC_Buffer[16] (5000 - Tabla_Buffer [2]);
SRC_Buffer[17] (5000 - Tabla_Buffer [1]);
SRC_Buffer[18] (5000 - Tabla_Buffer [0]);
}
}
else if (DMA_GetITStatus(DMA2_Stream1, DMA_IT_HTIF1))
{
// Half transfer.
DMA_ClearITPendingBit(DMA2_Stream1, DMA_IT_HTIF1);
}
else if (DMA_GetITStatus(DMA2_Stream1, DMA_IT_TEIF1))
{
// Transfer error.
DMA_ClearITPendingBit(DMA2_Stream1, DMA_IT_TEIF1);
}
}

and does not work!!!
webmaster
Associate II
Posted on March 24, 2015 at 20:41

I need to recharge every 5000msg because I have to update the table. In the example there is only one but really are 500 tables.

You can change each TC table on DMA? How?

webmaster
Associate II
Posted on March 24, 2015 at 20:48

That is. Instead of reloading the table just move the pointer ...

DMA2_Strem1 -> ????? = (uint32_t) SRC_Buffer [0] [SPWM_ELEMENTS];

Posted on March 24, 2015 at 21:14

I believe you'd have to stop the DMA to change the address, you could also look at the double buffering options.

What's the minimum time delta between the last sample and the 5ms window?

I don't think setting the TIMx->CCRx is a good plan in the TC interrupt, the timer may not have gotten to 5ms at that point. It's the point where it's delivered the last sample, but the compare point may not have been hit yet either.
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
webmaster
Associate II
Posted on March 24, 2015 at 21:20

233usg

So I thought it could be a good idea. Load the table before starting again.

Posted on March 24, 2015 at 21:28

I think you can get the first sample into the table in that time.

Sample point 18 hits on the timer, sample 19 loads into the compare register. TC fires. Load the first 16 samples for the next period (5ms / 5000 of the timer), when HT fires load samples 17, 18, 19 for the now current period

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
webmaster
Associate II
Posted on March 25, 2015 at 08:09

I really need something more robust. Sometime I would  put more shots on the table and would return to having to touch this code. I thought this would have more defined micro utilities for these tasks.

Posivilidad you were saying the double buffer options. Would this be a more robust and configurable way for this problem?

I sincerely appreciate the help that they provide me.

webmaster
Associate II
Posted on March 25, 2015 at 14:45

Definitely after reading about double buffer I think is the solution. Could you tell me the steps to configure the program in this way?

Posted on March 25, 2015 at 15:51

I don't have any examples for the case. You'll need to review the docs and the library source.

I'm not sure how the method is less robust than the ones you've already presented, it uses less interrupts, and doesn't meddle with the timer phase or compares. You could make the pattern buffer much bigger, and the wrap of the counter much longer (multiples of 5ms, or whatever).

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..