This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

DRV8301: 在用我自己设计的BLDC代码驱动BLDC时,高占空比下会启动失败

Part Number: DRV8301

我最近写了一个BLDC的驱动程序,是基于TI官方给出的BLDC-sensored的历程里的level2写的。代码如下:

_iq iqVaIn;
_iq iqVbIn;
_iq IDCfdbk;

d_pwm=_IQ(1);
D_com=_IQ(0.333333333333333); //120 degree commutation
// ------------------------------------------------------------------------------
// ADC conversion and offset adjustment
// ------------------------------------------------------------------------------
iqVaIn = _IQ15toIQ((AdcResult.ADCRESULT4<<3)-BemfA_offset);
iqVbIn = _IQ15toIQ((AdcResult.ADCRESULT5<<3)-BemfA_offset);
IDCfdbk= (_IQ15toIQ(AdcResult.ADCRESULT7<<3)-IDC_offset)<<1;

d_pwm= _IQ(0.6);

Connect inputs of the HALL module and call the Hall sensor read macro.
// ------------------------------------------------------------------------------
HALL3_READ_MACRO(hall1)

if (hall1.Revolutions>=30)
ClosedFlag=TRUE;


if (hall1.CmtnTrigHall==0x7FFF) /*只有当hall模块检测到换相使能信号时下列代码才执行,也就是说每个换相周期内执行一次计算,也就是在新的换相周期开始的那一时刻计算*/
{
speed2.TimeStamp = VirtualTimer; /*input of speed2*/
SPEED_PR_MACRO1(speed2)

if (hall1.Revolutions<=5){ /*because filter is fifth order so it needs five previous period value*/
speed3.EventPeriod=speed2.EventPeriod_n_1;
speed3.SUflag=TRUE;
}else{
speed3.currenttheta=rg1.Angle;
speed3.HallGpio=hall1.HallGpioAccepted;
speed3.EventPeriod=speed2.EventPeriod_n;
speed3.SUflag=FALSE;
}

SE_MACRO1(speed3)/*calculate speed*/

}


rg1.Freq = speed3.nextspeed;/*把速度的值赋给rg1.Freq*/
RG_MACRO(rg1)/*calculate angle*/
fa1.Angle= rg1.Out; /* motor A 0 */
fa1.phiv=_IQ(-0);/*advancing firing angle is zero*/ /* motor D 48V ~0.9/0.7Nm -0.508 */
FA_MACRO(fa1) /*add phiv with actual angle*/ /* motor C 48V ~0.7Nm -0.05 */
theta= (fa1.Out);

theta_ref1= _IQmpy(D_com,_IQ(0.5));
theta_ref2= D_com-_IQ(0.333333333333333);

if (ClosedFlag == FALSE)
{
pwmcntl1.Duty1 = _IQmpy(_IQ((hall1.HallGpioAccepted==2)||(hall1.HallGpioAccepted==3)),d_pwm);
pwmcntl1.Duty2 = _IQ(1)-(_IQ((hall1.HallGpioAccepted==5)||(hall1.HallGpioAccepted==4)));
pwmcntl1.Duty3 = _IQmpy(_IQ((hall1.HallGpioAccepted==1)||(hall1.HallGpioAccepted==5)),d_pwm);
pwmcntl1.Duty4 = _IQ(1)-(_IQ((hall1.HallGpioAccepted==6)||(hall1.HallGpioAccepted==2)));
pwmcntl1.Duty5 = _IQmpy(_IQ((hall1.HallGpioAccepted==4)||(hall1.HallGpioAccepted==6)),d_pwm);
pwmcntl1.Duty6 = _IQ(1)-(_IQ((hall1.HallGpioAccepted==3)||(hall1.HallGpioAccepted==1)));
}
else{
pwmcntl1.Duty1 = _IQ((theta>=_IQ(0.25)-theta_ref1) && (theta<_IQ(0.25)))+_IQmpy( d_pwm,_IQ(((theta>=0) && ((theta<_IQ(0.25)-theta_ref1))) || ((theta>=_IQ(0.916666666666667)-theta_ref2) && (theta<_IQ(1)))) );

pwmcntl1.Duty2 = _IQ(1)-_IQ((theta>=_IQ(0.75)-theta_ref1) && (theta<_IQ(0.75)))+_IQmpy( d_pwm,_IQ(((theta>=_IQ(0.416666666666667)-theta_ref2) && ((theta<_IQ(0.75)-theta_ref1)))) );

pwmcntl1.Duty3 = _IQ((theta>=_IQ(0.583333333333333)-theta_ref1) && (theta<_IQ(0.583333333333333)))+_IQmpy( d_pwm,_IQ(((theta>=_IQ(0.25)-theta_ref2) && ((theta<_IQ(0.583333333333333)-theta_ref1)))) );

pwmcntl1.Duty4 = _IQ(1)-_IQ( (theta>=_IQ(0)) && (theta < _IQ(0.083333333333333)) )+_IQ(((theta>=_IQ(0.083333333333333)+_IQ(1)-theta_ref1) && (theta<_IQ(1.0))))+_IQmpy( d_pwm,_IQ(((theta>=_IQ(0.75)-theta_ref2) && ((theta<_IQ(0.083333333333333)+_IQ(1)-theta_ref1)))) );


pwmcntl1.Duty5 = _IQ((theta>=_IQ(0.916666666666667)-theta_ref1) && (theta<_IQ(0.916666666666667)))+_IQmpy( d_pwm,_IQ(((theta>=_IQ(0.583333333333333)-theta_ref2) && ((theta<_IQ(0.916666666666667)-theta_ref1)))) );

pwmcntl1.Duty6 = _IQ(1)-_IQ((theta>=_IQ(0.416666666666667)-theta_ref1) && (theta<_IQ(0.416666666666667)))+_IQmpy( d_pwm,_IQ(((theta>=_IQ(0.083333333333333)-theta_ref2) && ((theta<_IQ(0.416666666666667)-theta_ref1))) || ((theta>=_IQ(0.083333333333333)-theta_ref2+_IQ(1)) && (theta<_IQ(1)))) );
}
PWM_CNTL_MACRO(pwmcntl1) /*generate PWM wave*/

我的这个程序是将6个MOSFETs分别独立控制,EPWM宏里的设置如下:

#define PWM_CNTL_AQCTLA_INIT_STATE (CAU_CLEAR + CAD_SET)
#define PWM_CNTL_AQCTLB_INIT_STATE (CBU_SET + CBD_CLEAR)

epwmA和epwmB的动作限定子模块的动作方式是相反的,这也是为什么上面代码里的下管脚的占空比前面多了一个“1-”。

我的代码在占空比d_pwm小于0.75时可以正常工作,但是当d_pwm大于0.75时,点击运行之后程序会直接报错,亮红灯,显示过流。

在示波器上观察PWM1A和PWM1B的波形发现,刚开始会出现占空比约为0.5的互补的波形,之后PWM1A会一直保持1,PWM1B则会一直保持0(我猜测这可能是触发了短路保护)。

我实在想不明白为什么占空比高了之后会导致短路并且报错,低占空比就没有问题。

请各位专家帮帮我。