打印
[STM32F1]

TIM4 PWM输出波形不正常

[复制链接]
1303|8
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
wape271|  楼主 | 2019-11-26 15:30 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
PWM周期为20us,间隔两个周期再打开,
在间隔周期内将PWM脉宽设为0(TIM4->CCR1=0;)
关键的几条PWM配置为:
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_ARRPreloadConfig(TIM4,ENABLE);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OC1PreloadConfig(TIM4, TIM_OCPreload_Disable);

波形如下图,不清楚为什么在一个周期内会有两个高电平,当间隔周期内不加TIM4->CCR1=0;则波形正常,希望得到各位的帮助,谢谢了

微信图片_20191126151935.jpg (372.94 KB )

微信图片_20191126151935.jpg

使用特权

评论回复
沙发
wape271|  楼主 | 2019-11-26 15:34 | 只看该作者
本帖最后由 wape271 于 2019-11-26 15:36 编辑

全部定时器设置如下

使用特权

评论回复
板凳
wape271|  楼主 | 2019-11-26 15:37 | 只看该作者
void TIM4_GPIO_Config(void) 
{
  GPIO_InitTypeDef GPIO_InitStructure;

        /* TIM2 clock enable */
        //PCLK1经过2倍频后作为TIM3的时钟源等于72MHz
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);
  /* GPIOA and GPIOB clock enable */
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB | RCC_APB2Periph_AFIO, ENABLE);

  /*GPIOA Configuration: TIM2 channel 1 and 2 as alternate function push-pull */
  GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_6 | GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_9;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;                    // 复用推挽输出
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;

  GPIO_Init(GPIOB, &GPIO_InitStructure);
}

void TIM4_Mode_Config(void)
{
        TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
  TIM_OCInitTypeDef  TIM_OCInitStructure;
        NVIC_InitTypeDef NVIC_InitStructure;
       
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4,ENABLE);
       
        TIM_DeInit(TIM4);//Use TIM_DeInit () function to set Timer as the default value;
  TIM_TimeBaseStructure.TIM_Prescaler = 1-1;//预分频 To set the prescaler coefficient
  TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;//
  TIM_TimeBaseStructure.TIM_Period = Fcount;//
  TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;//
  TIM_TimeBaseStructure.TIM_RepetitionCounter = 0;//
  TIM_TimeBaseInit(TIM4,&TIM_TimeBaseStructure);//
       
        TIM_ARRPreloadConfig(TIM4,ENABLE);                          
  
  TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
  TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
  TIM_OCInitStructure.TIM_OutputNState = TIM_OutputState_Disable;
  TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;//不反相输出
  TIM_OCInitStructure.TIM_OCNPolarity = TIM_OCNPolarity_Low;
  TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Reset;
  TIM_OCInitStructure.TIM_OCNIdleState = TIM_OCIdleState_Reset;
               
////////////////////////////////////////////////////////////////////////////////////
  TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
  TIM_OCInitStructure.TIM_Pulse = 0;
  TIM_OC1Init(TIM4,&TIM_OCInitStructure);
  TIM_OC1PreloadConfig(TIM4, TIM_OCPreload_Disable);
       
        TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
  TIM_OCInitStructure.TIM_Pulse = 0;
  TIM_OC2Init(TIM4,&TIM_OCInitStructure);
  TIM_OC2PreloadConfig(TIM4, TIM_OCPreload_Disable);

        TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
  TIM_OCInitStructure.TIM_Pulse = 0;
  TIM_OC3Init(TIM4,&TIM_OCInitStructure);
  TIM_OC3PreloadConfig(TIM4, TIM_OCPreload_Disable);

        TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
  TIM_OCInitStructure.TIM_Pulse = 0;        //设置通道4的电平跳变值,输出另外一个占空比的PWM
  TIM_OC4Init(TIM4, &TIM_OCInitStructure);        //使能通道4
  TIM_OC4PreloadConfig(TIM4, TIM_OCPreload_Disable);

        TIM_ITConfig(TIM4,TIM_IT_Update,ENABLE ); //使能指定的TIM4中断,允许更新中断
        //中断优先级NVIC设置
        NVIC_InitStructure.NVIC_IRQChannel = TIM4_IRQn;  //TIM4中断
        NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;  //先占优先级0级
        NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;  //从优先级3级
        NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能
        NVIC_Init(&NVIC_InitStructure);  //初始化NVIC寄存器

  TIM_Cmd(TIM4,ENABLE);
}

使用特权

评论回复
地板
wape271|  楼主 | 2019-11-26 15:40 | 只看该作者
想实现的功能是定时器4的3路PWM成三相输出,利用PWM定时中断在不同周期内打开或关闭某个PWM
现在只是试了其中一路PWM

使用特权

评论回复
5
香水城| | 2019-11-26 16:14 | 只看该作者
本帖最后由 香水城 于 2019-11-26 16:15 编辑

你关闭PWM是通过什么方式实现的? 修改CCR寄存器的值吗?
我看你已经关闭了CCR的预装功能,修改CCR的话,可以立即生效的。

怀疑你中断处理太啰嗦,在修改CCR时PWM已经切换到下一个周期了,这样可能导致窄脉冲出来。

也不知你进的是什么定时器事件的中断。

使用特权

评论回复
6
wape271|  楼主 | 2019-11-26 16:53 | 只看该作者
本帖最后由 wape271 于 2019-11-26 16:59 编辑
香水城 发表于 2019-11-26 16:14
你关闭PWM是通过什么方式实现的? 修改CCR寄存器的值吗?
我看你已经关闭了CCR的预装功能,修改CCR的话,可 ...

关闭PWM是将CCR的值修改为0;
但是从波形上看像是在同一周期内产生的一个窄脉冲,
定时器中断设置为TIM_ITConfig(TIM4,TIM_IT_Update,ENABLE );
定时器中断函数为void TIM4_IRQHandler(void)   //20us中断一次
{
static u8 ThreePhase=0;        
        if(TIM4->SR&0X0001)//溢出中断
        {
                TIM4->SR&=~(1<<0);//清除中断标志位
                switch(ThreePhase)
                {
                    case 0:
                    TIM4->CCR1=500;
                    ThreePhase=1;
                    break;
                    case 1:
                    TIM4->CCR1=0;
                    ThreePhase=2;
                    break;
                    case 2:
                    TIM4->CCR1=0;
                    ThreePhase=0;
                    break;
              }
       }
}


使用特权

评论回复
评论
wape271 2019-11-26 16:54 回复TA
PWM与定时中断同为TIM4 
7
labasi| | 2019-12-11 13:11 | 只看该作者
关闭一部分功能 排除一下问题原因

使用特权

评论回复
8
keaibukelian| | 2019-12-11 13:13 | 只看该作者
楼主找到问题的原因了吗

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

15

主题

166

帖子

5

粉丝