原子哥:
你好:
我在咱们专栏看到过这样一个程序,如下:
函数名:void  WM_Init_test(u16 psc)
功 能:用一个定时器TIM3输出四路【频率可调】【占空比可调】的PWM脉冲
原 理:利用STM32定时器的输出比较模式,再使能比较中断
定时器的计数频率为 72M Hz
===============================================================*/
void  WM_Init_test(u16 psc)
{
RCC->APB1ENR|=1<<1; //TIM3时钟使能
RCC->APB2ENR|=1<<2; //使能PORTA时钟
RCC->APB2ENR|=1<<3; //使能PORTB时钟
GPIOA->CRL&=0XF0FFFFFF;//PA6输出
GPIOA->CRL|=0X0B000000;//复用功能输出
GPIOA->ODR|=1<<6; //PA6上拉
GPIOA->CRL&=0X0FFFFFFF;//PA7输出
GPIOA->CRL|=0XB0000000;//复用功能输出
GPIOA->ODR|=1<<7; //PA7上拉
GPIOB->CRL&=0XFFFFFFF0;//PB0输出
GPIOB->CRL|=0X0000000B;//复用功能输出
GPIOB->ODR|=1<<0; //PB0上拉
GPIOB->CRL&=0XFFFFFF0F;//PB1输出
GPIOB->CRL|=0X000000B0;//复用功能输出
GPIOB->ODR|=1<<1; //PB1上拉
TIM3->ARR=0xffff;
TIM3-> SC=psc;//预分频
TIM3->CCR1=100;
TIM3->CCR2=200;
TIM3->CCR3=300;
TIM3->CCR4=400;
TIM3->CCMR1|=3<<4; //CH1 输出比较模式 OC1M=011
TIM3->CCMR1|=3<<12; //CH2 输出比较模式 OC2M=011
TIM3->CCMR2|=3<<4; //CH3 输出比较模式 OC3M=011
TIM3->CCMR2|=3<<12; //CH4 输出比较模式 OC4M=011
TIM3->CCMR1&=~(1<<3); //CH1预装载禁止 OC1PE=0
TIM3->CCMR1&=~(1<<11); //CH2预装载禁止 OC2PE=0
TIM3->CCMR2&=~(1<<3); //CH1预装载禁止 OC3PE=0
TIM3->CCMR2&=~(1<<11); //CH2预装载禁止 OC4PE=0
TIM3->DIER|=1<<1; //CC1IE 允许捕获比较中断1
TIM3->DIER|=1<<2; //CC2IE 允许捕获比较中断2
TIM3->DIER|=1<<3; //CC3IE 允许捕获比较中断3
TIM3->DIER|=1<<4; //CC4IE 允许捕获比较中断4
TIM3->CCER|=1<<0; //OC1 输出使能 CC1E=1
TIM3->CCER|=1<<4; //OC2 输出使能 CC2E=1
TIM3->CCER|=1<<8; //OC3 输出使能 CC3E=1
TIM3->CCER|=1<<12; //OC4 输出使能 CC4E=1
TIM3->CR1|=0x01; //使能定时器3
MY_NVIC_Init(1,3,TIM3_IRQChannel,1);//抢占1,子优先级3,组2
}
void TIM3_IRQHandler(void)
{
u16 cap;
static u8 n1=0;
static u8 n2=0;
static u8 n3=0;
static u8 n4=0;
if(TIM3->SR&0X0002) //查看CC1IF标记
{
if(n1==0)
{
n1=1;
cap=TIM3->CNT;
TIM3->CCR1=cap+100;
}
else
{
n1=0;
cap=TIM3->CNT;
TIM3->CCR1=cap+100;
}
}
if(TIM3->SR&0X0004) //查看CC2IF标记
{
if(n2==0)
{
n2=1;
cap=TIM3->CNT;
TIM3->CCR2=cap+250;
}
else
{
n2=0;
cap=TIM3->CNT;
TIM3->CCR2=cap+150;
}
}
if(TIM3->SR&0X0008) //查看CC3IF标记
{
if(n3==0)
{
n3=1;
cap=TIM3->CNT;
TIM3->CCR3=cap+450;
}
else
{
n3=0;
cap=TIM3->CNT;
TIM3->CCR3=cap+150;
}
}
if(TIM3->SR&0X0010) //查看CC4IF标记
{
if(n4==0)
{
n4=1;
cap=TIM3->CNT;
TIM3->CCR4=cap+400;
}
else
{
n4=0;
cap=TIM3->CNT;
TIM3->CCR4=cap+400;
}
}
TIM3->SR&=~(1<<1); //清标记位
TIM3->SR&=~(1<<2); //清标记位
TIM3->SR&=~(1<<3); //清标记位
TIM3->SR&=~(1<<4); //清标记位
}
我想问一下,
if(TIM3->SR&0X0002) //查看CC1IF标记
{
if(n1==0)
{
n1=1;
cap=TIM3->CNT;
TIM3->CCR1=cap+100;
}
else
{
n1=0;
cap=TIM3->CNT;
TIM3->CCR1=cap+100;
}
程序经过示波器测量波形。类似上述语句中红色数字的数值改变,会改变一个周期内高,低电平的维持长度。同时频率也就发生改变。请问一下,它的频率如何计算,每路输出的占空比又怎么计算?如果实现变频,变占空比。数值是通过哪个计算公式算出来的?谢谢!
|