2013-09-30 04:14 AM
hello all and thanks for your help,
I'm working with stm32f4 discovery board and I will like to use two different timers. For the timer TIM3 after a long work I set certain parameters so I can have my desired behavior (generate a periodic signal with a properly dutycycle and frequence ). Because I saw on the datasheet that TIM2, TIM3, TIM4 and TIM5 have the same characteristic I though that the same settings that I used for TIM3 will work also for TIM4 for example but unfortunately is not. Probably I miss something, I would like to understand the reason of this. Here in the bottom is the simple code that I used.#include ''stm32f4xx_gpio.h''
#include ''stm32f4xx_rcc.h''
#include ''stm32f4xx_tim.h''
GPIO_InitTypeDef GPIO_InitStructure;
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
void TIM_Config(void);
void PWM_Config(int period);
int main(void)
{
/* TIM Configuration */
TIM_Config();
/* PWM Configuration */
PWM_Config(800);
TIM3->CCR1=100;
TIM3->CCR2=100;
TIM3->CCR3=100;
TIM3->CCR4=100;
while (1)
{
}
}
void TIM_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
/* TIM3 clock enable */
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
/* GPIOC and GPIOB clock enable */
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC | RCC_AHB1Periph_GPIOB, ENABLE);
/* GPIOC Configuration: TIM3 CH1 (PC6) and TIM3 CH2 (PC7) */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7 ;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP ;
GPIO_Init(GPIOC, &GPIO_InitStructure);
/* GPIOB Configuration: TIM3 CH3 (PB0) and TIM3 CH4 (PB1) */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP ;
GPIO_Init(GPIOB, &GPIO_InitStructure);
/* Connect TIM3 pins to AF2 */
GPIO_PinAFConfig(GPIOC, GPIO_PinSource6, GPIO_AF_TIM3);
GPIO_PinAFConfig(GPIOC, GPIO_PinSource7, GPIO_AF_TIM3);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource0, GPIO_AF_TIM3);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource1, GPIO_AF_TIM3);
}
void PWM_Config(int period)
{
uint16_t PrescalerValue = 0;
/* Compute the prescaler value */
PrescalerValue = (uint16_t) ((SystemCoreClock /2) / 28000000) - 1;
/* Time base configuration */
TIM_TimeBaseStructure.TIM_Period = period;
TIM_TimeBaseStructure.TIM_Prescaler = PrescalerValue;
TIM_TimeBaseStructure.TIM_ClockDivision = 0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);
/* PWM1 Mode configuration: Channel1 */
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OC1Init(TIM3, &TIM_OCInitStructure);
TIM_OC1PreloadConfig(TIM3, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel2 */
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;
TIM_OC2Init(TIM3, &TIM_OCInitStructure);
TIM_OC2PreloadConfig(TIM3, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel3 */
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;
TIM_OC3Init(TIM3, &TIM_OCInitStructure);
TIM_OC3PreloadConfig(TIM3, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel4 */
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;
TIM_OC4Init(TIM3, &TIM_OCInitStructure);
TIM_OC4PreloadConfig(TIM3, TIM_OCPreload_Enable);
TIM_ARRPreloadConfig(TIM3, ENABLE);
/* TIM3 enable counter */
TIM_Cmd(TIM3, ENABLE);
}
Thank you for your help.
Pablo
#tim3-stm32f4-discovery
2013-09-30 06:35 AM
From a quick scan the code doesn't appear unreasonable, what exactly is the nature of the problem? Is the frequency not what you expected? What exactly?
2013-09-30 07:35 AM
Thanks clive,
let's say for example that with TIM3 I am able to have in one pin a trigger signal at 1Hz. just by chaining the timer name, TIM4, I am not able to see anything, my oscilloscope is flat, in particular:TIM5, TIM2: high level (~3V)TIM4: low level (~0V)TIM3: correct trigger signal Does the timers TIM2, TIM3, TIM4 and TIM5 are suppose to have the same behavior isn't it?2013-09-30 08:31 AM
Ok, so you're showing me code that does work, and asking me a question about some other code that doesn't? It would be easier for me if you showed me examples of what doesn't work, and I could suggestion reasons why, or how the configuration is wrong.
The timers should function in a materially similar ways, TIM1 & 8 will need the PWM Outputs Enabled. Other TIM you'll need to be sure a) You've enable the right APBx clock source, b) selected the right pin associations, and AHB clocks. Some timers do not have PWM, some have 1 or 2 channels, some just have a time base. The data sheet and reference manual should provide a comprehensive breakdown. TIM4 on the STM32F4-Discovery is connected to the colour LEDs, it's certainly possible to drive these in PWM or TOGGLE modes.2013-10-01 04:18 AM
The code that doesn't work is the one above but with the Timer = TIM4 (or 2,5)
As you said I check if there are some inconsistencies but seems all ok. Anyway there is something that I miss, I sawhttp://myembeddedtutorial.blogspot.ie/2013/06/working-with-stm32f4-timers.html
, for leds toggels, and this actually work with all the TIMs above, so my problem seems connect the timer to the pin and generate the trigger signal on it. Because those TIMs are suppose to have the same behavior ( datasheet says that) I was wondering why in my case is not like this.Thanks for your help.Pablo2013-10-01 05:07 AM
#include ''stm32f401_discovery.h''
void TIM_Config(void);
void PWM_Config(int period);
#define WIDTH 20000
int main(void)
{
/* TIM Configuration */
TIM_Config();
/* PWM Configuration */
PWM_Config(WIDTH);
TIM4->CCR1=WIDTH/8;
TIM4->CCR2=WIDTH/8;
TIM4->CCR3=WIDTH/8;
TIM4->CCR4=WIDTH/8;
while(1);
}
void TIM_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
/* TIM4 clock enable */
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);
/* GPIOD clock enable */
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOD, ENABLE);
/* GPIOD Configuration: TIM4 CH1..4 (PD.15) */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP ;
GPIO_Init(GPIOD, &GPIO_InitStructure);
/* Connect AF to TIM4 pins */
GPIO_PinAFConfig(GPIOD, GPIO_PinSource12, GPIO_AF_TIM4); // Green
GPIO_PinAFConfig(GPIOD, GPIO_PinSource13, GPIO_AF_TIM4); // Orange
GPIO_PinAFConfig(GPIOD, GPIO_PinSource14, GPIO_AF_TIM4); // Red
GPIO_PinAFConfig(GPIOD, GPIO_PinSource15, GPIO_AF_TIM4); // Blue
}
void PWM_Config(int period)
{
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
uint16_t PrescalerValue = 0;
/* Compute the prescaler value */
PrescalerValue = (uint16_t) ((SystemCoreClock / 2) / 20000) - 1; // 20 KHz
/* Time base configuration */
TIM_TimeBaseStructure.TIM_Period = period - 1;
TIM_TimeBaseStructure.TIM_Prescaler = PrescalerValue;
TIM_TimeBaseStructure.TIM_ClockDivision = 0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure);
/* PWM1 Mode configuration: Channel1 */
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0; // OFF
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
// Other TIM have CHx/CHxN fields
TIM_OC1Init(TIM4, &TIM_OCInitStructure);
TIM_OC1PreloadConfig(TIM4, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel2 */
TIM_OC2Init(TIM4, &TIM_OCInitStructure);
TIM_OC2PreloadConfig(TIM4, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel3 */
TIM_OC3Init(TIM4, &TIM_OCInitStructure);
TIM_OC3PreloadConfig(TIM4, TIM_OCPreload_Enable);
/* PWM1 Mode configuration: Channel4 */
TIM_OC4Init(TIM4, &TIM_OCInitStructure);
TIM_OC4PreloadConfig(TIM4, TIM_OCPreload_Enable);
TIM_ARRPreloadConfig(TIM4, ENABLE);
/* TIM4 enable counter */
TIM_Cmd(TIM4, ENABLE);
}
2013-10-02 07:14 AM
Thanks clive for the code.
I need to ask you one more thing to understand how the things work. If I make these edits:GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP ;
GPIO_Init(GPIOD, &GPIO_InitStructure);
/* Connect AF to TIM4 pins */
GPIO_PinAFConfig(GPIOD, GPIO_PinSource11, GPIO_AF_TIM4); // Green
GPIO_PinAFConfig(GPIOD, GPIO_PinSource13, GPIO_AF_TIM4); // Orange
GPIO_PinAFConfig(GPIOD, GPIO_PinSource14, GPIO_AF_TIM4); // Red
GPIO_PinAFConfig(GPIOD, GPIO_PinSource15, GPIO_AF_TIM4); // Blue
using the
GPIO_PinSource11
rather than
GPIO_PinSource12
on PD11 I am not able to see anything. What is the reason?
Thank you for your help. Pablo2013-10-02 07:50 AM
on PD11 I am not able to see anything. What is the reason?
The problem is that you're inventing connectivity that doesn't exist. From the Data Manual for the STM32F40x devices2013-10-03 08:49 AM
Thanks a lot clive,
that's exactly what I was looking for.Regards,Pablo