cancel
Showing results for 
Search instead for 
Did you mean: 

How to use Timer6 and Timer7 at the same time?

MQi.1
Senior II

I used Timer6 and Timer7 on STM32L433CCT6, used Timer6 for tone generation and Timer7 for tone toggle generation, the ISR is:

 

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef* htim) { if(htim == &htim6) { HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_0); //TIM6->CNT = toneFreq[0]; } else if(htim == &htim7) { if(flagOnOff == SET) { if(msTone >= toneOn[toneFreqIndex]) { flagOnOff = RESET; msTone = 0; GPIOA->MODER &= ~(GPIO_MODER_MODER0); // From output to input } else { msTone++; } } else // flagOnOff == RESET { if(msTone >= toneOff[toneFreqIndex]) { flagOnOff = SET; msTone = 0; GPIOA->MODER |= GPIO_MODER_MODER0_0; // From input to output } else { msTone++; } } } else {;} }
View more

 

the related variables are:

 

extern int toneFreq[] = {130, 146, 164, 174, 196, 220, 246}; // prescale value of Timer6 is 71 extern int toneOn[] = {9000, 8000, 7000, 6000, 5000, 4000, 3000}; // miliseconds, prescale value of Timer7 is 7199 extern int toneOff[] = {1000, 2000, 3000, 4000, 5000, 6000, 7000}; // 10us = 1 tick int msTone = 0; // miliseconds volatile bool flagOnOff = SET;

 

now, the tone was OK, the toggle affection was not, did I lost anything?

5 REPLIES 5
KnarfB
Principal III

The overall pattern testting for tim6 tim7 is okay. 

How many interrupts per second does your code generate? Maybe the CPU is overrun by interrupts, which can easily happen, especially when using HAL.

Try relaxing the interrupt frequency for testing.

hth

KnarfB

Probably consequence of unrealistically high interrupt rate (1MHz of TIM6), especially in conjunction with Cube/HAL (and potentially no or low compiler optimization).

Generate the tone using PWM/Toggle on a timer which has some TIMx_CHx pin available, and then the on/off pattern using interrupt gets realistic.

JW

 

The main clock is 72M, after scale, the frequency for Timer6 is 1M, Timer7 is 10K. The tone frequency is in range:

* Notes Frequency(Hz) Cycle/Period ARR value * C4 261 1M/261=3831 65535-261/2=65405 * D4 293 1M/293=3412 65535-293/2=65389 * E4 329 1M/329=3039 65535-329/2=65371 * F4 349 1M/349=2865 65535-349/2=65361 * G4 392 1M/392=2551 65535-392/2=65339 * A4 440 1M/440=2272 65535-440/2=65315 * B4 493 1M/493=2028 65535-493/2=65289

It's impossible to handle 1M interrupts per second with HAL and almost impossible without (actually totally impossible at 72 MHz). Use PWM for frequency generation.

My STM32 stuff on github - compact USB device stack and more: https://github.com/gbm-ii/gbmUSBdevice

I found a solution - set flag in Timer7 ISR and judge it in Timer6 ISR:

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef* htim) { if(htim == &htim6) { if(flagOnOff == SET) { HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_0); //HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, SET); // PNP - SS8550 //HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, RESET); // NPN - SS8050 //TIM6->CNT = toneFreq[0]; } else { //HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, SET); // PNP - SS8550 HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, RESET); // NPN - SS8050 //HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_0); } } else if(htim == &htim7) { if(flagOnOff == SET) { if(msTone >= toneOn[toneFreqIndex]) { flagOnOff = RESET; msTone = 0; //GPIOA->MODER &= ~(GPIO_MODER_MODER0); // From output to input } else { msTone++; } } else // flagOnOff == RESET { if(msTone >= toneOff[toneFreqIndex]) { flagOnOff = SET; msTone = 0; //GPIOA->MODER |= GPIO_MODER_MODER0_0; // From input to output } else { msTone++; } } } else {;} }
View more