打印
[STM32F1]

关于电机2.0库中的SVPWM算法

[复制链接]
8093|5
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
rickemma|  楼主 | 2015-6-8 13:57 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
小弟最近在用ST的2.0电机库 ,发现它的3电阻采样部分的程序代码好乱。尤其是它的ADC的设定和使用。贴出2.0库中的SVPWM算法。他的算法到底是用了ABC三路的电流采样还是用了两路的电流采样计算出第三路。其中的计算每一路电流采样为什么是   0电压误差值减去采样值。不应该是采样值减去0电压误差吗。还有他的算法流程很不解。代码如下:
Curr_Components SVPWM_3ShuntGetPhaseCurrentValues(void)
{
  Curr_Components Local_Stator_Currents;
  s32 wAux;

  switch (bSector)
   {
   case 4:  //È¡µÃÔÚÄǸöÉÈÇøµÄʱºòÔÚ¶ÁÈ¡AD      ÒòΪADCÊý¾ÝÑ¡ÔñÁË×ó¶ÔÆ룬ÔÚ×¢ÈëͨµÀÀïÓзûºÅλËùÒÔ²ÅÓÐÊý¾ÝֵΪÎÞ·ûºÅ65535£¨ÓзûºÅÔò32767£©
   case 5: //Current on Phase C not accessible     
           // Ia = (hPhaseAOffset)-(ADC Channel 11 value)   
            wAux = (s32)(hPhaseAOffset)- ((ADC1->JDR1)<<1);         
           //Saturation of Ia
            if (wAux < S16_MIN)
            {
              Local_Stator_Currents.qI_Component1= S16_MIN;
            }  
            else  if (wAux > S16_MAX)
                  {
                    Local_Stator_Currents.qI_Component1= S16_MAX;
                  }
                  else
                  {
                    Local_Stator_Currents.qI_Component1= wAux;
                  }
                     
           // Ib = (hPhaseBOffset)-(ADC Channel 12 value)
            wAux = (s32)(hPhaseBOffset)-((ADC2->JDR1)<<1);
           // Saturation of Ib
            if (wAux < S16_MIN)
            {
              Local_Stator_Currents.qI_Component2= S16_MIN;
            }  
            else  if (wAux > S16_MAX)
                  {
                    Local_Stator_Currents.qI_Component2= S16_MAX;
                  }
                  else
                  {
                    Local_Stator_Currents.qI_Component2= wAux;
                  }
           break;
           
   case 6:
   case 1:  //Current on Phase A not accessible     
            // Ib = (hPhaseBOffset)-(ADC Channel 12 value)
            wAux = (s32)(hPhaseBOffset)-((ADC1->JDR1)<<1);
            //Saturation of Ib
            if (wAux < S16_MIN)
            {
              Local_Stator_Currents.qI_Component2= S16_MIN;
            }  
            else  if (wAux > S16_MAX)
                  {
                    Local_Stator_Currents.qI_Component2= S16_MAX;
                  }
                  else
                  {
                    Local_Stator_Currents.qI_Component2= wAux;
                  }
            // Ia = -Ic -Ib
            wAux = ((ADC2->JDR1)<<1)-hPhaseCOffset-
                                            Local_Stator_Currents.qI_Component2;
            //Saturation of Ia
            if (wAux> S16_MAX)
            {
               Local_Stator_Currents.qI_Component1 = S16_MAX;
            }
            else  if (wAux <S16_MIN)
                  {
                   Local_Stator_Currents.qI_Component1 = S16_MIN;
                  }
                  else
                  {  
                    Local_Stator_Currents.qI_Component1 = wAux;
                  }
           break;
           
   case 2:
   case 3:  // Current on Phase B not accessible
            // Ia = (hPhaseAOffset)-(ADC Channel 11 value)     
            wAux = (s32)(hPhaseAOffset)-((ADC1->JDR1)<<1);
            //Saturation of Ia
            if (wAux < S16_MIN)
            {
              Local_Stator_Currents.qI_Component1= S16_MIN;
            }  
            else  if (wAux > S16_MAX)
                  {
                    Local_Stator_Currents.qI_Component1= S16_MAX;
                  }
                  else
                  {
                    Local_Stator_Currents.qI_Component1= wAux;
                  }
     
            // Ib = -Ic-Ia;
            wAux = ((ADC2->JDR1)<<1) - hPhaseCOffset -
                                            Local_Stator_Currents.qI_Component1;
            // Saturation of Ib
            if (wAux> S16_MAX)
            {
              Local_Stator_Currents.qI_Component2=S16_MAX;
            }
            else  if (wAux <S16_MIN)
                  {  
                    Local_Stator_Currents.qI_Component2 = S16_MIN;
                  }
                  else  
                  {
                    Local_Stator_Currents.qI_Component2 = wAux;
                  }                     
           break;

   default:
           break;
   }
  
  return(Local_Stator_Currents);
}
沙发
CS_Police| | 2015-6-9 21:12 | 只看该作者
楼主可以看下STM32F103的ADC外设,它有两个ADC模块,也就是可以同时读取两路的电流信号,所以三电阻采样可以直接同时读取两路的电流信号,另外一路当然可以通过Ia+Ib+Ic=0计算出数据的,2.0的库里面根据扇区在做ADC通道的切换;至于Offset部分,看定义的电流方向了,是进入电机为正还是电机输出为正了,不管何种定义,最后的电流电压一定是以Offset电压为中心的上下(正负)数据。
个人认为ST的2.0的库相对后面的3.0,4.0库还是比较好上手的,但后面的库支持的单片机比较多,没办法因为研发需要,4.0的库面向对象的编程本人还在熟悉中。。。。。

使用特权

评论回复
板凳
rickemma|  楼主 | 2015-6-23 09:17 | 只看该作者
CS_Police 发表于 2015-6-9 21:12
楼主可以看下STM32F103的ADC外设,它有两个ADC模块,也就是可以同时读取两路的电流信号,所以三电阻采样可 ...

我让2.0的电机库终于转起来了,不过用 的是对应的电机PMSM。我想让它运行BLDC可行吗?可以的话,我该修改哪些参数呢,麻烦大侠能告知一二,感激不尽。

使用特权

评论回复
地板
309579471| | 2015-6-24 10:51 | 只看该作者
你真要用 就不会问修改哪几个参数就可以运行了 这种问题 ,你得把代码都搞清楚才行

使用特权

评论回复
5
CS_Police| | 2015-6-26 09:53 | 只看该作者
楼上说的在理,好的产品程序需要花时间去深入研究,简单说可以控制BLDC,让电机转动没问题,要转的好需要根据实际情况进行调整。

使用特权

评论回复
6
gaoyang9992006| | 2015-6-26 12:31 | 只看该作者
case语句不错啊,我喜欢用的。

使用特权

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

本版积分规则

2

主题

4

帖子

0

粉丝