MKS DUAL FOC burning up

Hi,

I have a set up consisting of a GM3506 gimbal motor with a MKS Dual FOC plus driver. Ive had issues with two separate boards burning up when driving a motor through the second driver with current torque control.

I had torque control working properly through the first driver(with a bit of jitter when holding position) but I ran into a severe issue when testing that same torque control mode with the second driver on the MKS board(A1,B1,C1). In the code the first driver is not enabled so the pins are left floating, but the second driver is properly enabled. And when I run the code and do some tests the MKS board burns out and then pulls 10Amps or so from the power supply. Ive had that happen with two separate boards. I am not sure what the issue is but I think it make be something with the first driver left floating.

Set up: I am driving the MKS Dual FOC plus board at 24 volts with a motor voltage limit of 12V. I am using the esp32 chip that comes with the Dual FOC board. The Gimbal motor has a resistance of 5.6Ω. The set up works if I’m driving the motor with the first driver, but if I switch to the second driver then the driver burned out

#include <Arduino.h>
#include <SimpleFOC.h>

// BLDC motor & driver instance
BLDCMotor motor = BLDCMotor(11);
//BLDCDriver3PWM driver = BLDCDriver3PWM(32, 33, 25, 22);  ///MKS esp32
BLDCDriver3PWM driver = BLDCDriver3PWM(26, 27, 14, 12);  //MKS esp32 // SECOND DRIVER (One with problem)

MagneticSensorSPI sensor = MagneticSensorSPI(AS5147_SPI, 5);
//MagneticSensorSPI sensor = MagneticSensorSPI(AS5147_SPI, 15);

// current sensor
//InlineCurrentSense current_sense = InlineCurrentSense(0.01f, 50.0f, 39, 36);  //MKS esp32
InlineCurrentSense current_sense = InlineCurrentSense(0.01f, 50.0f, 35, 34);  //MKS esp32 // SECOND DRIVER (One with problem)

float target_angle = 0;
float target_velocity = 0;
float current_limit;

unsigned long flagTime;
int flag = 1;

// instantiate the commander
Commander command = Commander(Serial);
/*
void doTarget(char* cmd) {
  command.scalar(&motor.target, cmd);
}
*/

void doTarget(char* cmd) {
  command.scalar(&target_angle, cmd);
}

void currentLim(char* cmd) {
  command.scalar(&current_limit, cmd);
  motor.current_limit = current_limit;
  motor.PID_velocity.limit = motor.current_limit;
}

void setup() {

  // initialize encoder sensor hardware
  sensor.init();
  // link the motor to the sensor
  motor.linkSensor(&sensor);

  // driver config
  // power supply voltage [V]
  driver.voltage_power_supply = 24;
  driver.voltage_limit = 24;  // max voltage to motor
  driver.init();
  // link driver
  motor.linkDriver(&driver);
  // link the driver to the current sense
  current_sense.linkDriver(&driver);

  // current sense init hardware
  current_sense.init();

  current_sense.gain_b *= -1;
  // link the current sense to the motor
  motor.linkCurrentSense(&current_sense);

  motor.foc_modulation = FOCModulationType::SpaceVectorPWM;
  // set torque mode:
  motor.torque_controller = TorqueControlType::foc_current;
  motor.current_limit = .5;  // Amp limit
  // set motion control loop to be used
  //motor.controller = MotionControlType::torque;
  //motor.controller = MotionControlType::velocity;
  motor.controller = MotionControlType::angle;

  /*
  // foc current control parameters (Arduino UNO/Mega)
  motor.PID_current_q.P = 5;
  motor.PID_current_q.I = 300;
  motor.PID_current_d.P = 5;
  motor.PID_current_d.I = 300;
  motor.LPF_current_q.Tf = 0.01;
  motor.LPF_current_d.Tf = 0.01;
*/
  /*
  motor.PID_current_q.P = 2;    //修改合适的PID参数以实现更好的效果
  motor.PID_current_q.I = 800;  //电机出现抖动、转速不稳定的情况,很有可能就是PID参数没调到合适的
  motor.PID_current_d.P = 2;
  motor.PID_current_d.I = 800;
  motor.LPF_current_q.Tf = 0.002;  // 1ms default
  motor.LPF_current_d.Tf = 0.002;  // 1ms default
*/
  /*
  // Q axis
  // PID parameters - default
  motor.PID_current_q.P = 5;     // 3    - Arduino UNO/MEGA
  motor.PID_current_q.I = 1000;  // 300  - Arduino UNO/MEGA
  motor.PID_current_q.D = 0;
  motor.PID_current_q.limit = motor.voltage_limit;
  
  // Low pass filtering - default
  motor.LPF_current_q.Tf = 0.005;  // 0.01 - Arduino UNO/MEGA

  // D axis
  // PID parameters - default
  motor.PID_current_d.P = 5;     // 3    - Arduino UNO/MEGA
  motor.PID_current_d.I = 1000;  // 300  - Arduino UNO/MEGA
  motor.PID_current_d.D = 0;
  motor.PID_current_d.limit = motor.voltage_limit;
  // Low pass filtering - default
  motor.LPF_current_d.Tf = 0.005;
*/

  // Q axis
  // PID parameters - default
  motor.PID_current_q.P = .7;   //.7 //.1 //2
  motor.PID_current_q.I = 100;  //300 // 10 //400
  motor.PID_current_q.D = 0;
  motor.PID_current_q.limit = motor.voltage_limit;

  // Low pass filtering - default
  motor.LPF_current_q.Tf = .001;  // 0.01 - Arduino UNO/MEGA

  // D axis
  // PID parameters - default
  motor.PID_current_d.P = .7;   //.7 // .1
  motor.PID_current_d.I = 100;  //300 //10
  motor.PID_current_d.D = 0;
  motor.PID_current_d.limit = motor.voltage_limit;
  // Low pass filtering - default
  motor.LPF_current_d.Tf = .001;

  // velocity PI controller parameters
  motor.PID_velocity.P = .07;  //.1
  motor.PID_velocity.I = 1;    //2
  motor.PID_velocity.D = 0;

  motor.LPF_velocity.Tf = 0.005f;

  motor.P_angle.P = 20; //35

  motor.velocity_limit = 300;  //180

  // use monitoring with serial
  Serial.begin(115200);
  // comment out if not needed
  motor.useMonitoring(Serial);

  // initialize motor
  motor.init();
  // align sensor and start FOC
  motor.initFOC();

  // add target command T
  command.add('T', doTarget, "target angle");
  command.add('C', currentLim, "current Limmit");

  Serial.println(F("Motor ready."));
  Serial.println(F("Set the target current using serial terminal:"));
  _delay(1000);
  flagTime = millis();
}

void loop() {

  // main FOC algorithm function
  motor.loopFOC();

  // Motion control function
  motor.move(target_angle);

  // monitor angles & velocity at ~10 Hz
  static unsigned long t_last = 0;

  if (millis() - t_last > 150) {
    t_last = millis();

    /*
    if (flag == 1 && millis() - flagTime > 500) {
      target_angle = 0;
      flag++;
      flagTime = millis();
    } else if (flag == 2 && millis() - flagTime > 500) {
      target_angle = 10; 
      flag = 1;
      flagTime = millis();
    } 
*/

    //motor.current_limit = current_limit;
    //motor.PID_velocity.limit = motor.current_limit;
    Serial.print("  θ1:");
    //Serial.print(motor.shaft_angle);
    Serial.print(sensor.getAngle());
    Serial.print("\tω1:");
    Serial.print(motor.shaft_velocity, 3);
    Serial.print("\tVq1:");
    Serial.print(motor.voltage.q, 2);
    Serial.print("\tA:");
    Serial.print(current_sense.getDCCurrent());  // total current in Amps
    Serial.print("\tAQ:");
    Serial.println(motor.current.q);  // Q current in Amps


    // user communication
    command.run();
  }
}

driver.voltage_limit = 24; // max voltage to motor

to

driver.voltage_limit = 6; // max voltage to motor

You need to use a current limited power supply when working on these controllers, any problems and they will short and bun it and possibly the motor, there are no safeties as you’re directly controlling the hardware, so dont connect to a battery until your sure its working. use a current limited power supply set to 1A. so it wont let enough power into it to cause damage if it shorts.

If you dont have access to one, get a 12v incandecent car light bulb and install it in series with the battery, it will act like a smoke stopper and limit the current so all a short will do is light the bulb.

Which control method are you using?

I burned a lot of my MKS ESP32 FOC v1.0 boards because I was testing with open loop and MKS doesnt recommend running the open loop for more than one minute.

I only found about this recommendation on this file MKS-ESP32FOC/Test Code/Read Before You Begin.txt at MKS-ESP32-FOC-V2.0 · makerbase-motor/MKS-ESP32FOC · GitHub that is present only on a version that I’m not using and in a file that’s so hidden that I thought it had some confidential information about the government or something

If you are using open loop, I recommend using only for very low velocities and for a brief period of time. For the torque control, if you need some simple, try using voltage mode and limit the voltage and the speed of the motor.

To be honest, I’m using the Voltage Mode with current estimation (when you pass the phase resistance R) because in this mode, I find it easier to relate the current with torque (even tho there are some points about this - see Pratical Limitations on the documentation). I’m just using this mode to test my components and to debug some troubles, so I wasn’t running high speeds or needing high torque for more than 2 minutes. I’m also limiting the current on phases to 1A because the driver’s transistor has a diode that has this limit (I’m’ not remebering which one is, but I found it on the transistor datasheet. I’m not sure if the limitation works in just voltage mode, without using current estimation).

From what I know, the MKS Dual FOC has a current sensing. I strongly recommend using it in your control mode with a current limit on motor. If you have the phase resistance R, for example, you can just limit the voltage to a lower value. Or if you have Kv ou L, from what I know you can use just the voltage limitation too because they allow a estimation of the current

I recommend searching for more details about the transistor on MKS DUAL FOC like the voltage range operation and the current range operation, as well if there are some current limit to operate. If you search for the code that you see on the component, you will find the datasheet in english without difficulties (it can happen to be in chinese)

Moreover, if the problem is in your power supply, I think that it would burn some component near the board’s terminal power supply. I had some problem with power supply and it burn a protection fuse of the board and the voltage regulator (my board has a voltage regulator to power the ESP32). Running in open loop can also cause this problem near the power supply instead of near the motor’s terminal so you need to be very cautious

Sorry about my previous comment, I saw the code now

in the code that you send, I couldnt find where you set the voltage limit to the motor to 12V. For default, the driver.voltage_limit = 24; will be the voltage_limit of the motor. You can verify this in the method BLDCMotor::init (file in github BLDCMotor.cpp )

I’ll recommend too adding the motor.voltage_limit besides the motor.current_limit because you didnt inform any phase resistance R, kv ou another param that allow the code to estimate the voltage limit