Other Parts Discussed in Thread: CONTROLSUITE
Hello TI Community,
I m trying to control a PMSM using FOC technic.
I started with an example project " sensorless 28335" and did some modifications.
I used PI controller for both current and speed loop, qep module ( encoder 4096 lines), speed macro...
lsw=0 , the rotor moves a bit then is locked : the field is oriented on the d axis.
qep1.calibratedAngle is equal to 0.
lsw= 1 : when i'm using park.angle = rg1.out the rotor spins but a there s a big difference between rg1.out and qep1.thetaElectric.
for park.angle=qep1.Thetaelectric, in this case the rotor stays locked doesn't spin.
my program is the following ,
--------------------------------------------------------------------------------------------------
if(lsw==0)rc1.TargetValue = 0;
else rc1.TargetValue = spdrf1;//1
RC_MACRO(rc1)
// ------------------------------------------------------------------------------
// Connect inputs of the RAMP GEN module and call the ramp generator macro
// ------------------------------------------------------------------------------
rg1.Freq = rc1.SetpointValue;
RG_MACRO(rg1)
// calibration Angle
if (lsw==0) {EQep1Regs.QPOSCNT=0; EQep1Regs.QCLR.bit.IEL = 1;} // Reset position cnt.
if ((EQep1Regs.QFLG.bit.IEL==1) && Init_IFlag==0) // Check the first index occurrence
{qep1.CalibratedAngle= EQep1Regs.QPOSILAT; Init_IFlag++;} // Keep the latched position
if (lsw!=0) QEP_MACRO(qep1);
// ------------------------------------------------------------------------------
// Measure phase currents, subtract the offset and normalize from (-0.5,+0.5) to (-1,+1).
// Connect inputs of the CLARKE module and call the clarke transformation macro
// ------------------------------------------------------------------------------
clarke1.As=((AdcMirror.ADCRESULT1)*0.00024414-offsetA)*2*0.909; // Phase A curr.
clarke1.Bs=((AdcMirror.ADCRESULT2)*0.00024414-offsetB)*2*0.909; // Phase B curr.
CLARKE_MACRO(clarke1)
// ------------------------------------------------------------------------------
// Connect inputs of the PARK module and call the park trans. macro
// ------------------------------------------------------------------------------
park1.Alpha = clarke1.Alpha;
park1.Beta = clarke1.Beta;
if(lsw==0) park1.Angle = 0;
else if(lsw==1) park1.Angle = qep1.ElecTheta ;//rg1.Out;//
park1.Sine = _IQsinPU(park1.Angle);
park1.Cosine = _IQcosPU(park1.Angle);
PARK_MACRO(park1)
// ------------------------------------------------------------------------------
// Call the QEP calculation module
// ------------------------------------------------------------------------------
QEP_MACRO(1,qep1);
// ------------------------------------------------------------------------------
// Connect inputs of the SPEED_FR module and call the speed calculation macro
// ------------------------------------------------------------------------------
speed1.ElecTheta = qep1.ElecTheta;
speed1.DirectionQep = (int32)(qep1.DirectionQep);
SPEED_FR_MACRO(speed1)
// ------------------------------------------------------------------------------
// Connect inputs of the PI for speed
// ------------------------------------------------------------------------------
if (SpeedLoopCount==SpeedLoopPrescaler){
pi_spd.Ref = rc1.SetpointValue;
pi_spd.Fbk = speed1.Speed;
PI_MACRO(pi_spd);
SpeedLoopCount= 1 ;
}
else {
SpeedLoopCount= SpeedLoopCount+1;
}
// ------------------------------------------------------------------------------
// Connect inputs of the PI module and call the PI IQ controller macro
// ------------------------------------------------------------------------------
if(lsw==0) pi_iq.Ref = 0;
else if(lsw==1) pi_iq.Ref = pi_spd.Out;//_IQ(0.1) ;//
pi_iq.Fbk = park1.Qs;
PI_MACRO(pi_iq)
// ------------------------------------------------------------------------------
// Connect inputs of the PI module and call the PI ID controller macro
// ------------------------------------------------------------------------------
if(lsw==0) pi_id.Ref = _IQ(0.05);
else pi_id.Ref = IdRef;
pi_id.Fbk = park1.Ds;
PI_MACRO(pi_id)
// ------------------------------------------------------------------------------
// Connect inputs of the INV_PARK module and call the inverse park trans. macro
// ------------------------------------------------------------------------------
ipark1.Ds = pi_id.Out;
ipark1.Qs = pi_iq.Out ;
ipark1.Sine = park1.Sine;
ipark1.Cosine = park1.Cosine;
IPARK_MACRO(ipark1)
// ------------------------------------------------------------------------------
// Connect inputs of the SVGEN_DQ module and call the space-vector gen. macro
// ------------------------------------------------------------------------------
svgen1.Ualpha = ipark1.Alpha;
svgen1.Ubeta = ipark1.Beta;
SVGENDQ_MACRO(svgen1)
// ------------------------------------------------------------------------------
// Connect inputs of the PWM_DRV module and call the PWM signal generation macro
// ------------------------------------------------------------------------------
pwm1.MfuncC1 = svgen1.Ta;
pwm1.MfuncC2 = svgen1.Tb;
pwm1.MfuncC3 = svgen1.Tc;
PWM_MACRO(1,2,3,pwm1) // Calculate the new PWM compare values
// ------------------------------------------------------------------------------
// Connect inputs of the PWMDAC module
// ------------------------------------------------------------------------------
pwmdac1.MfuncC1 = clarke1.As;
pwmdac1.MfuncC2 = clarke1.Bs;
PWMDAC_MACRO(6,pwmdac1) // PWMDAC 6A, 6B
pwmdac1.MfuncC1 = qep1.ElecTheta;
pwmdac1.MfuncC2 = svgen1.Tb-svgen1.Tc;
PWMDAC_MACRO(7,pwmdac1) // PWMDAC 7A, 7B
// ------------------------------------------------------------------------------
// Connect inputs of the DATALOG module
// ------------------------------------------------------------------------------
DlogCh1 = _IQtoQ15(clarke1.As );
DlogCh2 = _IQtoQ15(clarke1.Bs);
DlogCh3 = _IQtoQ15(qep1.ElecTheta);
DlogCh4 = _IQtoQ15(rg1.Out);
Could you please help me ?
Regards,