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.
Tool/software: Code Composer Studio
Hi , Yanming Luo :
I try your suggestion of HFI frequency. it seems work. at build level 8 , I apply a constant voltage at q axis ,just like bulid level 2 , rotor spins at speed about 350rpm.
but rotor can't spin under current loop at build level 9 . and i found out it needs low pass filter in other training video ( ) but I wonder what digital fitler algorithm is suitable.
Looking forward to your reply, thanks in advance.
Thanks for your reply. but I'm a little confused.
In bulid 9 block diagram, there is no filter block in d and q axis current loop , shown as below
In train video, there is band filter block. shown as below
signals after low pass filter go into d and q axis current regulator. signals after hign pass filter go into HFI to get zero or low speed position information. do you mean we don't need to filter d&q axis current feedback for current regulator?
Thanks for your reply. but I can not find any code related to low pass filter in example project , shown as below
// =============================== LEVEL 9 ======================================
// Level 9 uses high frequency injection at lower speeds to identify
// rotor position, and uses eSMO discussed in LEVEL7 at higher speeds,
// providing speed control over the entire range
// ==============================================================================
// lsw=0: controller in RESET state without powering the motor
// lsw=1: identify initial rotor position, change lsw to 2 if success else to 0
// lsw=2: motor runs in speed loop
/*************************************************************************
* NOTE:- *
* The executable for Initial Position Detection (IPD) and *
* High Frequency Injection (HFI) are in hfi.lib file, which are not *
* part of the downloadable version of control suite. *
* Any attempt to build LEVEL9 code will result in error. *
* For access to the library and/or source code, the user is advised *
* to contact the nearest TI sales office. *
* ***********************************************************************
*/
#if (BUILDLEVEL==LEVEL9)
// ------------------------------------------------------------------------------
// Connect inputs of the RMP module and call the ramp control macro
// ------------------------------------------------------------------------------
if(lsw != RUN_STATE) {
rc1.TargetValue = 0;
rc1.SetpointValue = 0;
}
else
rc1.TargetValue = SpeedRef;
RC_MACRO(rc1)
// ------------------------------------------------------------------------------
// Connect inputs of the RAMP GEN module and call the ramp generator macro
// ------------------------------------------------------------------------------
rg1.Freq = rc1.SetpointValue;
RG_MACRO(rg1)
ANGLE_WRAP(rg1.Out);
// ------------------------------------------------------------------------------
// Connect inputs of the SPEED_EST module and call the estimated speed macro
// ------------------------------------------------------------------------------
transition1.spd = rc1.SetpointValue;
transition1.angleHFI = hfi1.thetaEst;
transition1.angleSMO = esmo1.Theta;
ANGLE_TRANSIT(&transition1);
speed3.EstimatedTheta = transition1.angle;
if (lsw != RUN_STATE)
speed3.OldEstimatedTheta = speed3.EstimatedTheta;
SE_MACRO(speed3)
// ------------------------------------------------------------------------------
// Measure the DC bus voltage in _IQ format
// ------------------------------------------------------------------------------
volt1.DcBusVolt = _IQ12toIQ(AdcResult.ADCRESULT7);
// ------------------------------------------------------------------------------
// 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 = _IQmpy2(_IQ12toIQ(AdcResult.ADCRESULT1)-offsetA); // Phase A curr.
clarke1.Bs = _IQmpy2(_IQ12toIQ(AdcResult.ADCRESULT2)-offsetB); // Phase B curr.
CLARKE_MACRO(clarke1)
// clarke1.Cs = _IQmpy2(_IQ12toIQ(AdcResult.ADCRESULT3)-offsetC); // Phase C curr.
// CLARKE1_MACRO(clarke1)
// ------------------------------------------------------------------------------
// Connect inputs of the PARK module and call the park trans. macro
// ------------------------------------------------------------------------------
park1.Alpha = clarke1.Alpha;
park1.Beta = clarke1.Beta;
park1.Angle = speed3.EstimatedTheta;
park1.Sine = _IQsinPU(park1.Angle);
park1.Cosine = _IQcosPU(park1.Angle);
PARK_MACRO(park1)
hpf_Iq.In1 = park1.Qs;
// ------------------------------------------------------------------------------
// State Machine for motor control
// ------------------------------------------------------------------------------
if(lsw == RESET_STATE)
{
// reset all PI regulators
RESET_PI(pi_spd);
RESET_PI(pi_id);
RESET_PI(pi_iq);
HFI_RESET(&hfi1); // reset HFI module
HPF_RESET(&hpf_Iq); // reset HPF
HPF_INIT(&hpf_coeff1); // optional - to change HPF corner freq during debug
dbc1.gain = 0;
}
else if (lsw == IPD_STATE)
{
ZLSPD(&hpf_Iq, &hpf_coeff1, &hfi1, &ns_id1, &clarke1, &volt1);
pi_id.Out = hfi1.duty;
pi_iq.Out = 0;
if(hfi1.HFI_Status == HFI_RUN_STATE)
{
lsw = RUN_STATE;
pi_id.Out = 0;
}
else if(hfi1.HFI_Status == HFI_RESET_STATE)
{
lsw = RESET_STATE;
}
}
else if (lsw == RUN_STATE)
{
// ------------------------------------------------------------------------------
// Connect inputs of the PI module and call the PID speed controller macro
// ------------------------------------------------------------------------------
if (++SpeedLoopCount >= SpeedLoopPrescaler)
{
pi_spd.Ref = rc1.SetpointValue;
pi_spd.Fbk = speed3.EstimatedSpeed;
PI_MACRO(pi_spd);
SpeedLoopCount=0;
}
// ------------------------------------------------------------------------------
// Connect inputs of the PI module and call the PID IQ controller macro
// ------------------------------------------------------------------------------
pi_iq.Ref = pi_spd.Out;
pi_iq.Fbk = park1.Qs;
PI_MACRO(pi_iq);
// ------------------------------------------------------------------------------
// Connect inputs of the PI module and call the PID ID controller macro
// ------------------------------------------------------------------------------
pi_id.Ref = 0;
pi_id.Fbk = park1.Ds;
PI_MACRO(pi_id);
// Zero and low speed position detection
if ( _IQabs(rc1.SetpointValue) <= transition1.spdHi )
{
ZLSPD(&hpf_Iq, &hpf_coeff1, &hfi1, &ns_id1, &clarke1, &volt1);
pi_id.Out += hfi1.duty;
}
// dbc1.gain = _IQ(0.5); // comment to tune in debug environment
}
// ------------------------------------------------------------------------------
// 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 VOLT_CALC module and call the phase voltage macro
// ------------------------------------------------------------------------------
// volt1.DcBusVolt = _IQ12toIQ(AdcResult.ADCRESULT7);
volt1.MfuncV1 = svgen1.Ta;
volt1.MfuncV2 = svgen1.Tb;
volt1.MfuncV3 = svgen1.Tc;
PHASEVOLT_MACRO(volt1)
// ------------------------------------------------------------------------------
// Connect inputs of the eSMO_POS module and call the eSMO module
// ------------------------------------------------------------------------------
if ((lsw == RUN_STATE) && (esmo1.Kslide < smoK_set))
esmo1.Kslide += _IQ(0.00001);
esmo1.Ialpha = clarke1.Alpha;
esmo1.Ibeta = clarke1.Beta;
esmo1.Valpha = volt1.Valpha;
esmo1.Vbeta = volt1.Vbeta;
esmo1.runSpeed = speed3.EstimatedSpeed;
esmo1.cmdSpeed = rc1.SetpointValue;
eSMO_MODULE(&esmo1);
/********************************************************************
* Supplemental filter to remove jitters from esmo estimated angle
* ******************************************************************/
// esmo1.Theta = angleFilter(&pi_smo, &esmo1); // Uncomment to include
// ------------------------------------------------------------------------------
// 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
// ------------------------------------------------------------------------------
if (lsw != RUN_STATE) dbc1.gain = 0;
// else dbc1.gain = _IQ(0.5); // comment line to tune in debug
pwm1.MfuncC1 = svgen1.Ta;
pwm1.MfuncC2 = svgen1.Tb;
pwm1.MfuncC3 = svgen1.Tc;
if (hfi1.HFI_Status != HFI_NSID_STATE) // not NSID state
{
/**********************************************
* PWM Gen w Dead Band Compensation Macro
* if curA > 0 Ta = Ta + Tdt
* else Ta = Ta - Tdt
**********************************************/
dbc1.scale = _IQdiv(_IQdiv2(pwm1.Deadband), dbc1.Ith); // uncomment to tune in debug
dbc1.Kdtc = _IQmpy(dbc1.scale, dbc1.gain); // uncomment to tune " "
PWMwDBC_MACRO(1,2,3,pwm1,clarke1,dbc1);
}
// ------------------------------------------------------------------------------
// Connect inputs of the PWMDAC module
// ------------------------------------------------------------------------------
pwmdac1.MfuncC1 = speed3.EstimatedTheta;
pwmdac1.MfuncC2 = pi_id.Out;
PWMDAC_MACRO(6,pwmdac1) // PWMDAC 6A, 6B
pwmdac1.MfuncC1 = rg1.Out;
pwmdac1.MfuncC2 = pi_iq.Out;
PWMDAC_MACRO(7,pwmdac1) // PWMDAC 7A, 7B
// ------------------------------------------------------------------------------
// Connect inputs of the DATALOG module
// ------------------------------------------------------------------------------
DlogCh1 = (int16)_IQtoIQ15(rg1.Out);
DlogCh2 = (int16)_IQtoIQ15(clarke1.Bs);
DlogCh3 = (int16)_IQtoIQ15(volt1.VphaseA);
DlogCh4 = (int16)_IQtoIQ15(qep1.ElecTheta);
#endif // (BUILDLEVEL==LEVEL9)
as highlight part shows , d&q axis current feedback just come from signals after PARK transition, which is not filtered.
and no low pass filter is mentioned in HFI library document. the library version which I got from FAE is V13.1 . is it the latest version?