G431B_ESC1 Temp and pot reading unavailable when current sensing is enabled

Hi All,

I have a BLDC on a G431B_ESC and I want to switch from using a magnetic sensor AS5600 to using current sensing and need to get the Temperature of the board in all modes.

I have written code that is meant to work after exploring the issues stating

PB14 must be remapped over DMA which I failed at
then tried:

float temp = _readADCVoltageInline(A_TEMPERATURE, currentSense.params);

both approaches return a negative constant value of -30.53

Here is my code:

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

#define CURRENT_SENSING_ENABLE 0

// Motor instance
BLDCMotor motor = BLDCMotor(11, 0.1, 270, 0.00002);
BLDCDriver6PWM driver = BLDCDriver6PWM(A_PHASE_UH, A_PHASE_UL, A_PHASE_VH, A_PHASE_VL, A_PHASE_WH, A_PHASE_WL);

#if CURRENT_SENSING_ENABLE == 1
LowsideCurrentSense currentSense = LowsideCurrentSense(0.003f, -64.0f / 7.0f, A_OP1_OUT, A_OP2_OUT, A_OP3_OUT);
#endif

// Magnetic sensor instance
MagneticSensorI2C sensor = MagneticSensorI2C(AS5600_I2C);

// angle set point variable
float target_angle = 0;

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

void setup()
{
  Serial.begin(230400);

  ////////////////////////////////////////////////////////////////////////////
  // enable more verbose output for debugging
  // comment out if not needed
  SimpleFOCDebug::enable(&Serial);

  // initialise magnetic 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.init();
  // link the motor and the driver
  motor.linkDriver(&driver);

  /////// Current sensing /////////
#if CURRENT_SENSING_ENABLE == 1
  currentSense.linkDriver(&driver);
  currentSense.init();
  // no need for aligning
  currentSense.skip_align = true;
  motor.linkCurrentSense(&currentSense);
#endif
  /////// END Current sensing /////////

  // choose FOC modulation (optional)
  motor.foc_modulation = FOCModulationType::SpaceVectorPWM;

  // set motion control loop to be used
  motor.controller = MotionControlType::angle;

  // contoller configuration
  // default parameters in defaults.h

  // velocity PI controller parameters
  motor.PID_velocity.P = 0.2f;
  motor.PID_velocity.I = 20;
  motor.PID_velocity.D = 0;
  // maximal voltage to be set to the motor
  motor.voltage_limit = 1.5;

  // velocity low pass filtering time constant
  // the lower the less filtered
  motor.LPF_velocity.Tf = 0.01f;

  // angle P controller
  motor.P_angle.P = 20;
  // maximal velocity of the position control
  motor.velocity_limit = 5;

  // comment out if not needed
  motor.useMonitoring(Serial);

  // initialize motor
  motor.init();
  // setup sensor config and start FOC
  motor.sensor_direction = CW;
  motor.zero_electric_angle = 3.06;
  motor.initFOC();

  // Add commander functions
  command.add('A', onMotor, "motor");
  // command.add('M', setControlMode, "control mode");
  // add target command T
  command.add('T', doTarget, "target angle");

  Serial.println(F("Motor ready."));
  Serial.println(F("Set the target angle in degrees using serial terminal:"));

  ///////////////////////////////////////////////////////////////////////////////////////

  Serial.println("Setup...");
  delay(1000); // Delay for 1 second
}

void loop()
{

#if CURRENT_SENSING_ENABLE == 0
  float temp = analogRead(A_TEMPERATURE); // Read temperature sensor
#endif

#if CURRENT_SENSING_ENABLE == 1
  float temp = _readADCVoltageInline(A_TEMPERATURE, currentSense.params);
#endif

  float temperature = (1000. / 19.) * (3.3 / 1023.) * temp - 30.5263; // 10bit // @25degree Celcius V=1.055 // (0,-48.6842)(1023,125)

  Serial.print("Temperature: ");
  Serial.println(temperature);

  motor.loopFOC();

  motor.move((target_angle * _2PI / 360));

  // user communication
  command.run();
}

Platformio.ini:

[env:disco_b_g431b_esc1]
platform = ststm32
board = disco_b_g431b_esc1
framework = arduino
lib_archive = false
monitor_speed = 230400

lib_deps =
    askuric/Simple FOC@^2.3.4

build_flags =
    -D HAL_OPAMP_MODULE_ENABLED

Any help would be greatly appreciated.

Thanks,
Rafik

You need _readADCVoltageLowSide, not inline.

1 Like

Hi @dekutree64

Thank you so much for pointing me in the right direction !

The posts I read were pre G431B_ESC1 moving to lowside hence why the error.

I did also find out that the raw value to temperature formula needs to change as the values are not the same as per below

#if CURRENT_SENSING_ENABLE == 0
  float temp = analogRead(A_TEMPERATURE); // Read temperature sensor
  float temperature = (1000. / 19.) * (3.3 / 1023.) * temp - 30.5263; // 10bit // @25degree Celcius V=1.055 // (0,-48.6842)(1023,125)
#endif

#if CURRENT_SENSING_ENABLE == 1
  float temp = _readADCVoltageLowSide(A_TEMPERATURE, currentSense.params);
  float temperature = (1000.0 / 19.0) * temp - 30.5263;
#endif

Many thanks for your help,
Rafik

For the sake of completeness I am posting the more elegant solution to work around the temperature reading when currentSense is enabled (hopefully will save others the headache):

bool isCurrentSensingEnabled(BLDCMotor &motor)
{
  return motor.current_sense != nullptr;
}

float tempSense()
{
  float temperature;

  if (isCurrentSensingEnabled(motor))
  {
    float rawTemp = _readADCVoltageLowSide(A_TEMPERATURE, currentSense.params);
    temperature = (1000.0 / 19.0) * rawTemp - 30.5263;
  }
  else
  {
    float rawTemp = analogRead(A_TEMPERATURE);
    temperature = (1000. / 19.) * (3.3 / 1023.) * rawTemp - 30.5263; // 10bit // @25degree Celcius V=1.055 // (0,-48.6842)(1023,125)
  }
  return temperature;
}
1 Like