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.

How to raise the rate of motor on InstaSPIN Solutions

Other Parts Discussed in Thread: MOTORWARE

Hi All,

I am using LaunchPad XL TMS320F28069M + BOOSTXL-DRV8301 revB to control our probe module. The tool of development  is Code Composer Studio, Version: 6.1.2.00015, the compiler version as 6.4.6.  The probe module used brushless DC-Servomotor Faulhaber's 1628T024B, encoder 256. The probe stroke is 67mm, corresponding to 6.86 revolutions of the motor. My control is based on lab13b and Id/Iq PI  and bandwidth of position controller have been tuned. After the program runs it finds mechanical stop (home) first, and then up 6 revolutions and down 6 revolutions continuously. To define up 6 revolutions and down 6 revolutions as a contact. Normally, the rate of motion is always more than 3 contacts per second. In order to raise the rate, I changed 2 parameters,
USER_NUM_CTRL_TICKS_PER_SPEED_TICK  and USER_NUM_CTRL_TICKS_PER_TRAJ_TICK from 30 to 6. The value of the rate is different after restarting the program, sometimes it is more than 1 contacts per second, sometimes more than 3 or 5. I want to know the reason why to generate different results per resume. How to raise the rate of motor on InstaSPIN Solutions. Thanks in advance for your help.
 
Some parameters definition:
USER_IQ_FULL_SCALE_FREQ_Hz        (1/0.002)
USER_PWM_FREQ_kHz                          (30.0)
USER_NUM_PWM_TICKS_PER_ISR_TICK        (1)
USER_NUM_ISR_TICKS_PER_CTRL_TICK       (1)
USER_NUM_CTRL_TICKS_PER_CURRENT_TICK   (1)
USER_NUM_CTRL_TICKS_PER_EST_TICK       (1)
 
gMotorVars.MaxVel_krpm = _IQ(30.0);
gMotorVars.MaxAccel_krpmps = _IQ18(3600.0);
gMotorVars.MaxDecel_krpmps = _IQ18(3600.0);
gMotorVars.MaxJrk_krpmps2 = _IQ18(6000.0);
  • can you attach your user.h file please

  • sorry, attach the user_j5.h please
  • your timing is off. 30 KHz PWM with no CTRL ticks is really pushing the ISR usage, especially with SpinTAC.

    try
    #define USER_NUM_PWM_TICKS_PER_ISR_TICK (2)

    so the ISR is at 15 KHz

    then you can try these at (15) - default 1 KHz, (3) - 5 KHz, or (1) - 15 KHz
    #define USER_NUM_CTRL_TICKS_PER_SPEED_TICK (6)
    #define USER_NUM_CTRL_TICKS_PER_TRAJ_TICK (6)
  • if the ISR is at 15 KHz, then CTRL is also 15 KHz, it will generate an error of 'USER_ErrorCode_ctrlFreq_Hz_Low', because 'USER_MOTOR_Rs / USER_MOTOR_Ls_q + 1e-9' = 28,762
  • ahhhh, I see. these types of motors are over designed for control stability for ridiculous R over L values with huge Rs.

    in this case I would just comment out the error code being set in user.h or the error check in proj_lab##.c

    in this case the RoverL shouldn't affect the control itself...it should work once the error is no longer flagged.
  • After commenting out the error code, the program can run stably and the rate of motion keeps always more than 6 contacts per second. Besides this approach, if are there other methods that can raise the rate of motion with SpinTAC? And how to adjust the torque of motor within that platform?
  • I don't understand what you mean by rate of motion.
    "the rate of motion keeps always more than 6 contacts per second."

    "And how to adjust the torque of motor within that platform?"
    The torque is controlled by the velocity/position controller output directly. The torque limit is set in user.h bu
    USER_MOTOR_MAX_CURRENT
    this is the peak IqRef_A command allowed by the output of the velocity controller
  • At the beginning of the question I have defined the contact, that is 'To define up 6 revolutions and down 6 revolutions as a contact'.
  • so is more than 6 contacts per second good? does it meet the goals?
  • Oh, sorry, I made a mistake. When the ISR changed to 15 KHz, I forgot to modify timer. So right now the rate is still more than 3 contacts per second. Our goals should be more than 7.
  • I still don't understand what you mean by contacts. If you need it to make more revs in a time frame increase the allowed acceleration and jerk.

  • You are right. Indeed more contacts mean more revolutions in a time frame. On velocity, acceleration and jerk, I saw some definitions in 'spintac_pos_move.h', such as:

    _iq24 VelLim; //!< Velocity Limit { unit: [pu/s], value range: (0.0, 1.0] )
    _iq18 AccLim; //!< Acceleration Limit { unit: [pu/s^2], value range: [0.001, 120.0] }
    _iq18 DecLim; //!< Deceleration Limit { unit: [pu/s^2], value range: [0.001, 120.0] }
    _iq18 JrkLim; //!< Jerk Limit { unit: [pu/s^3], value range: [0.0005, 2000.0] }

    ST_SPEED_PU_PER_KRPM = (1/30)

    I want to know if that values I assigned can exceed value range above limit in spintac?

  • insure you are setting a velocity that will satisfy your revs/time frame requirement. Make sure the VelLim is larger.
    set a large enough Acceleration and AccLim to reach the VelLim in time so it can complete your res/time.
    insure jerk is large enough to allow you to meet acceleration setting.
  • Winston,

    The limits you quoted are the pu mathematical limits of the SpinTAC module.  They cannot be exceeded. 

    For acceleration, that translates to (for your settings) 3600krpm/s [ (500 {USER_IQ_FULL_SCALE_FREQ_Hz} * 60 {Hz to RPM Scale}) / 1 {USER_MOTOR_NUM_POLE_PAIRS}  * 120 {SpinTAC AccMax} ] which is enormous.  

    I would echo Chris' suggestions.  Numerically work out what Velocity, Acceleration/Deceleration will meet your application requirements.  You can change the curve type from ST-Curve to Trapezodial in order to ignore the Jerk term.  This will simplify the calculations.

  • In our application, the motor turns forward 6 revolutions and then reverse 6 revolution. We call this loop as a contact. The motor loops continuously. For each 6 revolutions' motion, parameters of motion as
    gMotorVars.MaxVel_krpm = _IQ(30.0);
    gMotorVars.MaxAccel_krpmps = _IQ18(3600.0);
    gMotorVars.MaxDecel_krpmps = _IQ18(3600.0);
    The curve type of motion is Trapezoidal. By calculation of mathematics, the value of contacts per second should be more than 24, but real value we have got in project is more than 3. Why is there so big difference?
  • Winston,

    Did you modify the code so that it will translate your IQ18 SI Acceleration and Deceleration values into the appropriate IQ24 PU Acceleration and Deceleration to provide to the SpinTAC block?

  • Adam,
    Yes, I modified the code because the value range of IQ24 is too narrow.
  • Winston,

    Can you please paste the code where you provide the value from gMotorVars.MaxAccel_krpmps to STPOSMOVE_setAccelerationLimit?
  • Adam,

    In  ST_runPosMove() function, 

    void ST_runPosMove(ST_Handle handle)
    {
        ST_Obj *stObj = (ST_Obj *)handle;

        // Run SpinTAC Position Profile Generator
        // If we are not running a profile, and command indicates we should has been modified
        if((STPOSMOVE_getStatus(stObj->posMoveHandle) == ST_MOVE_IDLE) && (gMotorVars.RunPositionProfile == true))
        {
            // Get the configuration for SpinTAC Position Move
            STPOSMOVE_setCurveType(stObj->posMoveHandle, gMotorVars.SpinTAC.PosMoveCurveType);
            STPOSMOVE_setPositionStep_mrev(stObj->posMoveHandle, gMotorVars.PosStepInt_MRev, gMotorVars.PosStepFrac_MRev);
            STPOSMOVE_setVelocityLimit(stObj->posMoveHandle, _IQmpy(gMotorVars.MaxVel_krpm, _IQ(ST_SPEED_PU_PER_KRPM)));
            STPOSMOVE_setAccelerationLimit(stObj->posMoveHandle, _IQ18mpy(gMotorVars.MaxAccel_krpmps, _IQ18(ST_SPEED_PU_PER_KRPM)));
            STPOSMOVE_setDecelerationLimit(stObj->posMoveHandle, _IQ18mpy(gMotorVars.MaxDecel_krpmps, _IQ18(ST_SPEED_PU_PER_KRPM)));
            STPOSMOVE_setJerkLimit(stObj->posMoveHandle, _IQ18mpy(gMotorVars.MaxJrk_krpmps2, _IQ18(ST_SPEED_PU_PER_KRPM)));

            // Enable the SpinTAC Position Profile Generator
            STPOSMOVE_setEnable(stObj->posMoveHandle, true);

            if(gMotorVars.PosStepInt_MRev > 0) Flag_End_Upward = true;
            if(gMotorVars.PosStepInt_MRev < 0) Flag_End_Downward = true;
            // clear the position step command
            gMotorVars.PosStepInt_MRev = 0;
            gMotorVars.PosStepFrac_MRev = 0;
            gMotorVars.RunPositionProfile = false;
        }

        STPOSMOVE_run(stObj->posMoveHandle);
    }

  • Winston,

    That is the issue.  You are passing an IQ18 value into SpinTAC.  This needs to be an IQ24 value.  Try the following code.

    STPOSMOVE_setAccelerationLimit(stObj->posMoveHandle, _IQ24mpyIQX(gMotorVars.MaxAccel_krpmps, 18, _IQ18(ST_SPEED_PU_PER_KRPM), 18));
    STPOSMOVE_setDecelerationLimit(stObj->posMoveHandle, _IQ24mpyIQX(gMotorVars.MaxDecel_krpmps, 18, _IQ18(ST_SPEED_PU_PER_KRPM), 18));
    STPOSMOVE_setJerkLimit(stObj->posMoveHandle, _IQ20mpyIQX(gMotorVars.MaxJrk_krpmps2, 18, _IQ18(ST_SPEED_PU_PER_KRPM), 18));

    The SpinTAC interface expect all inputs to be a particular Q-ness.  So instead of providing IQ24(120) like you expected, you were really providing IQ24(1.875) since IQ18(120) == IQ24(1.875).

  • Hi Adam,

    According to the code you provided, I modified my software and everything was correct. Thanks a lot.

    Right now I set parameters of motor motion as:

    gMotorVars.MaxVel_krpm = _IQ(6.33345);
    gMotorVars.MaxAccel_krpmps = _IQ20(690.844);
    gMotorVars.MaxDecel_krpmps = _IQ20(690.844);

    PosMoveCurveType = ST_MOVE_CUR_TRAP;

    The motor rotates same revolutions in forward and reverse directions. When the revolution = 1 or 2, all things are right. But while the revolution is more than 3, the motion of motor is unstable. I want to know the reason to generate this. Is the torque not enough? 

  • Winston,

    That is probably the case. The SpinTAC profile generator will generate the fastest possible curve under your limits. Which means it will always use a value less than your limits.

    As you increase the number of revolutions, the speed and acceleration are getting larger and so you are probably either running our of torque of trying to spin faster than the motor is capable of.
  • Adam,

    Can you tell me how to improve this and make the motor run stably.

  • Winston,

    There could be many reasons for this instability. First thing I should suggest would be to reduce the acceleration limits and attempt to spin 3 revolutions. See if you are reaching an acceleration that is not achievable with your motion system.
  • Adam,
    I reduced the acceleration limits and kept the same speed, let motor spin 3 revolutions. Parameters as
    gMotorVars.MaxVel_krpm = _IQ(6.33345);
    gMotorVars.MaxAccel_krpmps = _IQ20(390.844);
    gMotorVars.MaxDecel_krpmps = _IQ20(390.844);
    The motor run stably.
  • But after I increased acceleration limits to 690.844, the motor happened running unstably. So I thought the motion system can not provide Sufficient torque in this condition.
  • Winston,

    It is possible.  You can try increased the  USER_MOTOR_MAX_CURRENT_A in order to allow your motor to command more torque.

  • Adam,

    There was no improvement after I increased USER_MOTOR_MAX_CURRENT until the value of 3 times. What are other reasons that can result in unstable motion?

  • Winston,

    Try lowering the maximum velocity, you might be exceeding the maximum possible speed of the motor.

    Depending on your motor, you may need to rescale the phase current sense resistors so that you can maximize the performance of the FOC.  

    You can also try increasing the stiffness of the current controller.  There should be some posts/blogs that talk about tuning the current controller.

  • Adam,

    I tested my motor system according to your advise. When I changed these parameters the motor run still unstably. But I found that when some parameters were fixed let the motor start running, stop, reset, and restart, stop, reset,.....repeat these procedures. In a loop of these repeats the motor will work very well, that means work state of the motor is related to the moment of the motor starting. So how to adjust parameters make them synchronized at every starting.

  • Winston,

    I'm not quite sure what you are saying here. Can you provide some additional clarification?

  • Adam,

    Presently I set parameters of motor motion as:

    gMotorVars.MaxVel_krpm = _IQ(6.33345);
    gMotorVars.MaxAccel_krpmps = _IQ20(390.844);
    gMotorVars.MaxDecel_krpmps = _IQ20(390.844);

    PosMoveCurveType = ST_MOVE_CUR_TRAP;

    The motor rotates 4 revolutions in forward and reverse directions.  And then I start running program, observing state of motion, stopping and resetting program, repeat this procedure many times. In occasional one of these procedures, the motor will work very well as setting parameters. But in the majority of cases, the state of motor motion is unstable, speed and number of revolution of motor motion are all different every time. So I think this is not a torque issue, but a synchronization problem. How do I resolve it?

  • Winston,

    In the InstaSPIN-MOTION labs the motor and encoder are synchronized when the resistance is recalibrated prior to each start.  Have you disabled this functionality?

    You may need to increase the amount of alignment current in order to guarantee this alignment occurs.  In order to do that you should modify the USER_MOTOR_RES_EST_CURRENT_A in the user.h file.

  • Adam,

    I can't find out reasons on the motor synchronization issue. So I did labs again from beginning of Instaspin. I have a question to ask you. SpinTAC.PosCtlBw_radps is defined as _iq20, can I modify it as _iq18.

  • Winston,

    winston wu said:
    SpinTAC.PosCtlBw_radps is defined as _iq20, can I modify it as _iq18.

    The q-ness of variable within SpinTAC cannot be modified since the library was compiled with the assumed q-ness.

  • Adam,

    Based on lab13b of MotorWare, I finished the motor control. But I had a new problem. 

    Presently parameters of motor motion was set as:

    gMotorVars.MaxVel_krpm = _IQ(6.33345);
    gMotorVars.MaxAccel_krpmps = _IQ20(690.844);
    gMotorVars.MaxDecel_krpmps = _IQ20(690.844);

    PosMoveCurveType = ST_MOVE_CUR_TRAP;

    The motor rotates 6 revolutions in forward and then reverse directions continuously. When I define 'ST_POS_ERROR_MAXIMUM_MREV  (1.0)', the motor works well. However when I define 'ST_POS_ERROR_MAXIMUM_MREV  (0.5)', there will be 'gMotorVars.SpinTAC.PosCtlErrorID = 2002'. I tried to adjust parameter gMotorVars.SpinTAC.PosCtlBw_radps, there is no improvement. In my project I hope getting position accuracy less than 50 counts at above parameters of motor motion. If can I obtain that result by MotorWare?

  • winston wu said:
    In my project I hope getting position accuracy less than 50 counts at above parameters of motor motion. If can I obtain that result by MotorWare?

    Are you positive that the combination of your motor, inertia, and inverter can reach your goal acceleration?

    My suspicion is that your motor is lagging behind the reference and is unable to actually track your command signal.  This is difficult to look at without logging the position error in realtime during a movement.

    So if that is the case, than your position controller will be commanding maximum current and adjusting the bandwidth will do nothing.  Only thing you can really do here is increase the maximum current so that your motor can accelerate faster.

    So I don't think this is a limitation of Motorware but a limitation of the maximum current applied to the motor.