Failed full calibration with AMT232B-V absolute encoder

I ran into a problem trying to use an AMT232B-V absolute encoder. It fails AXIS_STATE_FULL_CALIBRATION_SEQUENCE with ERROR_PHASE_RESISTANCE_OUT_OF_RANGE.

Setup

  • Motor: MAD EEE 5010 370KV
  • Encoder: AMT232B-V absolute encoder
  • Power Supply: 24V 14.6A Mean Well
  • 2 ohm stock brake resistor
  • ODrive Firmware: 0.5.0
  • OS: Ubuntu 18.04

Problem

  • When running odrv0.axis0.requested_state = AXIS_STATE_FULL_CALIBRATION_SEQUENCE, it receives an error ERROR_PHASE_RESISTANCE_OUT_OF_RANGE. The motor makes a single clicking noise and doesn’t move.
  • However, when switching the encoder to an incremental one (AMT102-V), it passes the AXIS_STATE_FULL_CALIBRATION_SEQUENCE.

ODrive commands used to set up the system.

odrv0.erase_configuration()
odrv0.reboot()
odrv0.config.brake_resistance = 2
odrv0.axis0.motor.config.pole_pairs = 14
odrv0.axis0.motor.config.motor_type = MOTOR_TYPE_HIGH_CURRENT

When using an AMT232B-V encoder, the following commands are used as well.

odrv0.axis0.encoder.config.abs_spi_cs_gpio_pin = 7
odrv0.axis0.encoder.config.mode = ENCODER_MODE_SPI_ABS_CUI
odrv0.axis0.encoder.config.cpr = 2**14

After that, we do

odrv0.axis0.requested_state = AXIS_STATE_FULL_CALIBRATION_SEQUENCE

Any suggestions would be appreciated.

try increasing motor.config.max_calibration_voltage ?

When I increase odrv0.axis0.motor.config.resistance_calib_max_voltage, it triggers an error ERROR_DC_BUS_UNDER_VOLTAGE instead. What I don’t quite understand is that why it works with an incremental encoder with exactly the same motor settings (odrv0.axis0.motor.config ).

Ok, so you have two issues, because you are using FULL_CALIBRATION_SEQUENCE (which is really just MOTOR_CALIBRATION followed by ENCODER_OFFSET_CALIBRATION).

You need to increase the voltage for MOTOR_CALIBRATION to work (this doesn’t even use the encoder)
But for ENCODER_OFFSET_CALIBRATION you might have set motor.config.calibration_current too high for your power supply. Try reducing that.

That still doesn’t explain why it works on an incremental encoder setup (exactly the same physical motor and motor settings).

Btw, even if I call just odrv0.axis0.requested_state = AXIS_STATE_MOTOR_CALIBRATION, I still get the error ERROR_PHASE_RESISTANCE_OUT_OF_RANGE. As I increase the odrv0.axis0.motor.config.resistance_calib_max_voltage, the error becomes ERROR_DC_BUS_UNDER_VOLTAGE instead.

Changing the encoder will NOT change the outcome of AXIS_STATE_MOTOR_CALIBRATION, I guarantee it. Unless perhaps the encoder is somehow feeding in some electrical noise into the ODrive e.g. due to bad grounding. Maybe some other settings or conditions have changed?

Try to ensure that your motor chassis is grounded and can’t be coupling noise onto the encoder itself.

If DC_BUS_UNDER_VOLTAGE is occurring, then you have either a current limited power supply (e.g. mains powered PSU) or excessive resistance and/or inductance in the supply wires. (i.e. they are too long, too narrow gauge, not twisted) or, you have set your config.dc_bus_undervoltage_limit too high. Or else some noise on the voltage sensing circuit, perhaps due to a ground loop?

Otherwise, I’m puzzled. :frowning:

I successfully passed AXIS_STATE_MOTOR_CALIBRATION and AXIS_STATE_ENCODER_OFFSET_CALIBRATION separately. Then, it failed AXIS_STATE_CLOSED_LOOP_CONTROL.

Here are the steps I did.

# no encoder plugged in
odrv0.erase_configuration()

# there'll be a beep sound after this
odrv0.config.brake_resistance = 2
odrv0.axis0.motor.config.pole_pairs = 14
odrv0.axis0.motor.config.motor_type = MOTOR_TYPE_HIGH_CURRENT
odrv0.axis0.requested_state = AXIS_STATE_MOTOR_CALIBRATION
odrv0.axis0.motor.config.pre_calibrated = True
odrv0.save_configuration()
odrv0.reboot()

# plug in encoder
odrv0.axis0.encoder.config.abs_spi_cs_gpio_pin = 7
odrv0.axis0.encoder.config.mode = ENCODER_MODE_SPI_ABS_CUI
odrv0.axis0.encoder.config.cpr = 2**14
odrv0.save_configuration()
odrv0.reboot()

# motor will spin back and forth
odrv0.axis0.requested_state = AXIS_STATE_ENCODER_OFFSET_CALIBRATION
odrv0.axis0.encoder.config.pre_calibrated = True
odrv0.save_configuration()
odrv0.reboot()