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.

CCS/TMS320F28069M: 2motor can not Simultaneously run, but can alone run

Part Number: TMS320F28069M
Other Parts Discussed in Thread: MOTORWARE

Tool/software: Code Composer Studio

My project change form   motorWare  proj-13e  to  2 motor control。 Each motor  can    run alone ,but can not  Running simultaneously 。 first run motor 1 normal,then run motor 2 ,

 Start when executing the following program ,Very large current , achieve 40A !!! ( #define USER_MOTOR_MAX_CURRENT          (20.0))

// if we are forcing alignment, using the Rs Recalculation, align the eQEP angle with the rotor angle

if((EST_getState(obj->estHandle) == EST_State_Rs) && (USER_MOTOR_TYPE == MOTOR_Type_Pm))
{
ENC_setZeroOffset(encHandle[HAL_MTR1], (uint32_t)(HAL_getQepPosnMaximum(halHandle,HAL_MTR1) - HAL_getQepPosnCounts(halHandle,HAL_MTR1)));
}

for(;;)
{

// Waiting for enable system flag to be set
while(!(gMotorVars[motorNum].Flag_enableSys));

// Dis-able the Library internal PI. Iq has no reference now
if( gMotorVars[HAL_MTR1].Flag_enableUserParams == false )
{
CTRL_setFlag_enableSpeedCtrl(ctrlHandle[HAL_MTR1], true);
}
else
{
CTRL_setFlag_enableSpeedCtrl(ctrlHandle[HAL_MTR1], false);
}

if( gMotorVars[HAL_MTR2].Flag_enableUserParams == false )
{
CTRL_setFlag_enableSpeedCtrl(ctrlHandle[HAL_MTR2], true);
}
else
{
CTRL_setFlag_enableSpeedCtrl(ctrlHandle[HAL_MTR2], false);
}

// loop while the enable system flag is true
while(gMotorVars[motorNum].Flag_enableSys)
{

for(motorNum=HAL_MTR1; motorNum<=HAL_MTR2; motorNum++ )
{
CTRL_Obj *obj = (CTRL_Obj *)ctrlHandle[motorNum];
ST_Obj *stObj = (ST_Obj *)stHandle[motorNum];


// increment counters
gCounter_updateGlobals[motorNum]++;

// enable/disable the use of motor parameters being loaded from user.h
CTRL_setFlag_enableUserMotorParams(ctrlHandle[motorNum],gMotorVars[motorNum].Flag_enableUserParams);

// enable/disable Rs recalibration during motor startup
EST_setFlag_enableRsRecalc(obj->estHandle,gMotorVars[motorNum].Flag_enableRsRecalc);

// enable/disable automatic calculation of bias values
CTRL_setFlag_enableOffset(ctrlHandle[motorNum],gMotorVars[motorNum].Flag_enableOffsetcalc);


if(CTRL_isError(ctrlHandle[motorNum]))
{
// set the enable controller flag to false
CTRL_setFlag_enableCtrl(ctrlHandle[motorNum],false);

// set the enable system flag to false
gMotorVars[motorNum].Flag_enableSys = false;

// disable the PWM
HAL_disablePwm(halHandle,motorNum);
}
else
{
// update the controller state
bool flag_ctrlStateChanged = CTRL_updateState(ctrlHandle[motorNum]);

// enable or disable the control
CTRL_setFlag_enableCtrl(ctrlHandle[motorNum], gMotorVars[motorNum].Flag_Run_Identify);

if(flag_ctrlStateChanged)
{
CTRL_State_e ctrlState = CTRL_getState(ctrlHandle[motorNum]);

if(ctrlState == CTRL_State_OffLine)
{
// enable the PWM
HAL_enablePwm(halHandle,motorNum);

}
else if(ctrlState == CTRL_State_OnLine)
{
if(gMotorVars[motorNum].Flag_enableOffsetcalc == true)
{
// update the ADC bias values
HAL_updateAdcBias(halHandle,motorNum);
}
else
{
// set the current bias
HAL_setBias(halHandle,HAL_SensorType_Current,0,_IQ(I_A_offset),motorNum);
HAL_setBias(halHandle,HAL_SensorType_Current,1,_IQ(I_B_offset),motorNum);
HAL_setBias(halHandle,HAL_SensorType_Current,2,_IQ(I_C_offset),motorNum);

// set the voltage bias
HAL_setBias(halHandle,HAL_SensorType_Voltage,0,_IQ(V_A_offset),motorNum);
HAL_setBias(halHandle,HAL_SensorType_Voltage,1,_IQ(V_B_offset),motorNum);
HAL_setBias(halHandle,HAL_SensorType_Voltage,2,_IQ(V_C_offset),motorNum);
}

// Return the bias value for currents
gMotorVars[motorNum].I_bias.value[0] = HAL_getBias(halHandle,HAL_SensorType_Current,0,motorNum);
gMotorVars[motorNum].I_bias.value[1] = HAL_getBias(halHandle,HAL_SensorType_Current,1,motorNum);
gMotorVars[motorNum].I_bias.value[2] = HAL_getBias(halHandle,HAL_SensorType_Current,2,motorNum);

// Return the bias value for voltages
gMotorVars[motorNum].V_bias.value[0] = HAL_getBias(halHandle,HAL_SensorType_Voltage,0,motorNum);
gMotorVars[motorNum].V_bias.value[1] = HAL_getBias(halHandle,HAL_SensorType_Voltage,1,motorNum);
gMotorVars[motorNum].V_bias.value[2] = HAL_getBias(halHandle,HAL_SensorType_Voltage,2,motorNum);

// enable the PWM
HAL_enablePwm(halHandle,motorNum);
}
else if(ctrlState == CTRL_State_Idle)
{
// disable the PWM
HAL_disablePwm(halHandle,motorNum);
gMotorVars[motorNum].Flag_Run_Identify = false;
}

if((CTRL_getFlag_enableUserMotorParams(ctrlHandle[motorNum]) == true) &&
(ctrlState > CTRL_State_Idle) &&
(gMotorVars[motorNum].CtrlVersion.minor == 6))
{
// call this function to fix 1p6
USER_softwareUpdate1p6(ctrlHandle[motorNum]);
}

}
}


if(EST_isMotorIdentified(obj->estHandle))
{
// set the current ramp
EST_setMaxCurrentSlope_pu(obj->estHandle,gMaxCurrentSlope[motorNum]);
gMotorVars[motorNum].Flag_MotorIdentified = true;

// set the speed reference
CTRL_setSpd_ref_krpm(ctrlHandle[motorNum],gMotorVars[motorNum].SpeedRef_krpm);

// set the speed acceleration
CTRL_setMaxAccel_pu(ctrlHandle[motorNum],_IQmpy(MAX_ACCEL_KRPMPS_SF,gMotorVars[motorNum].MaxAccel_krpmps));

// enable the SpinTAC Speed Controller


if( ctrlMode[motorNum] == speed )
{
STVELCTL_setEnable(stObj->velCtlHandle, true);
STPOSCTL_setEnable(stObj->posCtlHandle, false);
}
else
{
STVELCTL_setEnable(stObj->velCtlHandle, false);
STPOSCTL_setEnable(stObj->posCtlHandle, true);
}


if(EST_getState(obj->estHandle) != EST_State_OnLine)
{
// if the estimator is not running, place SpinTAC into reset
STVELCTL_setEnable(stObj->velCtlHandle, false);
STPOSCTL_setEnable(stObj->posCtlHandle, false);
// If motor is not running, feed the position feedback into SpinTAC Position Move
STPOSMOVE_setPositionStart_mrev(stObj->posMoveHandle, STPOSCONV_getPosition_mrev(stObj->posConvHandle));
}

if(Flag_Latch_softwareUpdate[motorNum])
{
Flag_Latch_softwareUpdate[motorNum] = false;

USER_calcPIgains(ctrlHandle[motorNum]);

// initialize the watch window kp and ki current values with pre-calculated values
gMotorVars[motorNum].Kp_Idq = CTRL_getKp(ctrlHandle[motorNum],CTRL_Type_PID_Id);
gMotorVars[motorNum].Ki_Idq = CTRL_getKi(ctrlHandle[motorNum],CTRL_Type_PID_Id);


gMotorVars[motorNum].Kp_spd = CTRL_getKp(ctrlHandle[motorNum],CTRL_Type_PID_spd);
gMotorVars[motorNum].Ki_spd = CTRL_getKi(ctrlHandle[motorNum],CTRL_Type_PID_spd);

// initializes the value for GoalSpeed and TorqueRampTime
gMotorVars[motorNum].SpinTAC.VelIdGoalSpeed_krpm = _IQmpy(STVELID_getGoalSpeed(stObj->velIdHandle), _IQ(ST_SPEED_KRPM_PER_PU));
gMotorVars[motorNum].SpinTAC.VelIdTorqueRampTime_sec = STVELID_getTorqueRampTime_sec(stObj->velIdHandle);
STVELID_setSensorlessFeedback(stObj->velIdHandle, false);


// initialize the watch window Bw value with the default value
gMotorVars[motorNum].SpinTAC.VelCtlBw_radps = STVELCTL_getBandwidth_radps(stObj->velCtlHandle);
// initialize the watch window with maximum and minimum Iq reference
gMotorVars[motorNum].SpinTAC.VelCtlOutputMax_A = _IQmpy(STVELCTL_getOutputMaximum(stObj->velCtlHandle), _IQ(USER_IQ_FULL_SCALE_CURRENT_A));
gMotorVars[motorNum].SpinTAC.VelCtlOutputMin_A = _IQmpy(STVELCTL_getOutputMinimum(stObj->velCtlHandle), _IQ(USER_IQ_FULL_SCALE_CURRENT_A));


gMotorVars[motorNum].SpinTAC.PosCtlBw_radps = STPOSCTL_getBandwidth_radps(stObj->posCtlHandle);
// initialize the watch window with maximum and minimum Iq reference
gMotorVars[motorNum].SpinTAC.PosCtlOutputMax_A = _IQmpy(STPOSCTL_getOutputMaximum(stObj->posCtlHandle), _IQ(USER_IQ_FULL_SCALE_CURRENT_A));
gMotorVars[motorNum].SpinTAC.PosCtlOutputMin_A = _IQmpy(STPOSCTL_getOutputMinimum(stObj->posCtlHandle), _IQ(USER_IQ_FULL_SCALE_CURRENT_A));


}

}
else
{
Flag_Latch_softwareUpdate[motorNum] = true;

// the estimator sets the maximum current slope during identification
gMaxCurrentSlope[motorNum] = EST_getMaxCurrentSlope_pu(obj->estHandle);
}


// when appropriate, update the global variables
if(gCounter_updateGlobals[motorNum] >= NUM_MAIN_TICKS_FOR_GLOBAL_VARIABLE_UPDATE)
{
// reset the counter
gCounter_updateGlobals[motorNum] = 0;

updateGlobalVariables_motor(ctrlHandle[motorNum], stHandle[motorNum],motorNum);
}

if(gMotorVars[motorNum].Flag_enableUserParams == true)
{
// update Kp and Ki gains
updateKpKiGains(ctrlHandle[motorNum],motorNum);
}
else
{
if(CTRL_getMotorType(ctrlHandle[motorNum]) == MOTOR_Type_Induction)
{
// recalculate Kp and Ki gains to fix the R/L limitation of 2000.0, and Kp limit to 0.11
recalcKpKi(ctrlHandle[motorNum]);

// set electrical frequency limit to zero while identifying an induction motor
setFeLimitZero(ctrlHandle[motorNum]);

// calculate Dir_qFmt for acim motors
acim_Dir_qFmtCalc(ctrlHandle[motorNum]);
}
else
{
// recalculate Kp and Ki gains to fix the R/L limitation of 2000.0, and Kp limit to 0.11
// as well as recalculates gains based on estimator state to allow low inductance pmsm to id
recalcKpKiPmsm(ctrlHandle[motorNum]);

// calculate an Ls qFmt that allows ten times smaller inductance compared to Lhf
CTRL_calcMax_Ls_qFmt(ctrlHandle[motorNum], &gMax_Ls_qFmt);

gLs_pu = EST_getLs_d_pu(obj->estHandle);
gLs_qFmt = EST_getLs_qFmt(obj->estHandle);
}
}

// update Kp and Ki gains
// updateKpKiGains(ctrlHandle[motorNum],motorNum);

// set the SpinTAC (ST) bandwidth scale
STVELCTL_setBandwidth_radps(stObj->velCtlHandle, gMotorVars[motorNum].SpinTAC.VelCtlBw_radps);

// set the maximum and minimum values for Iq reference
STVELCTL_setOutputMaximums(stObj->velCtlHandle, _IQmpy(gMotorVars[motorNum].SpinTAC.VelCtlOutputMax_A, _IQ(1.0/USER_IQ_FULL_SCALE_CURRENT_A)), _IQmpy(gMotorVars[motorNum].SpinTAC.VelCtlOutputMin_A, _IQ(1.0/USER_IQ_FULL_SCALE_CURRENT_A)));


STPOSCTL_setBandwidth_radps(stObj->posCtlHandle, gMotorVars[motorNum].SpinTAC.PosCtlBw_radps);

// set the maximum and minimum values for Iq reference
STPOSCTL_setOutputMaximums(stObj->posCtlHandle, _IQmpy(gMotorVars[motorNum].SpinTAC.PosCtlOutputMax_A, _IQ(1.0/USER_IQ_FULL_SCALE_CURRENT_A)), _IQmpy(gMotorVars[motorNum].SpinTAC.PosCtlOutputMin_A, _IQ(1.0/USER_IQ_FULL_SCALE_CURRENT_A)));

// enable/disable the forced angle
EST_setFlag_enableForceAngle(obj->estHandle,gMotorVars[motorNum].Flag_enableForceAngle);

// enable or disable power warp
CTRL_setFlag_enablePowerWarp(ctrlHandle[motorNum],gMotorVars[motorNum].Flag_enablePowerWarp);

} // end of for(motorNum=HAL_MTR1; motorNum<=HAL_MTR2; motorNum++ ) loop


} // end of while(gFlag_enableSys) loop


// disable the PWM
HAL_disablePwm(halHandle,HAL_MTR1);
HAL_disablePwm(halHandle,HAL_MTR2);

// set the default controller parameters (Reset the control to re-identify the motor)
CTRL_setParams(ctrlHandle[HAL_MTR1],&gUserParams[HAL_MTR1]);
CTRL_setParams(ctrlHandle[HAL_MTR2],&gUserParams[HAL_MTR2]);
gMotorVars[HAL_MTR1].Flag_Run_Identify = false;
gMotorVars[HAL_MTR2].Flag_Run_Identify = false;

// setup the SpinTAC Components


ST_setupPosConv(stHandle[HAL_MTR1]);
ST_setupVelId(stHandle[HAL_MTR1]);
ST_setupVelCtl(stHandle[HAL_MTR1]);
ST_setupPosCtl(stHandle[HAL_MTR1]);
ST_setupPosMove(stHandle[HAL_MTR1]);
gMotorVars[HAL_MTR1].MaxVel_krpm = 0;

ST_setupPosConv(stHandle[HAL_MTR2]);
ST_setupVelId(stHandle[HAL_MTR2]);
ST_setupVelCtl(stHandle[HAL_MTR2]);
ST_setupPosCtl(stHandle[HAL_MTR2]);
ST_setupPosMove(stHandle[HAL_MTR2]);
gMotorVars[HAL_MTR2].MaxVel_krpm = 0;

} // end of for(;;) loop