Firmware 0.5.3 Release Thread

Firmware v0.5.3 is now officially released! A matching version of odrivetool is also published.

Updating odrivetool

To update odrivetool, simply use pip install --upgrade odrive.

Updating ODrive firmware

Updating ODrive firmware can be done by using odrivetool dfu. The current recommended process for flashing is as follows:


  1. Power off the ODrive
  2. Set the DFU / RUN switch to DFU
  3. Power on the ODrive
  4. In a shell, type odrivetool dfu. Flashing should succeed.
  5. Power off the ODrive
  6. Set the DFU / RUN switch to RUN
  7. Power on the ODrive
  8. Verify functionality by launching odrivetool


odrivetool dfu is not supported on windows. To update:
You can use the DfuSe app from ST.

  1. Download the tool here. Unfortunately they make you create a login to download. Sorry about that.
  2. After installing the tool, launch DfuFileMgr.exe which probably got added to the start menu as “Dfu file manager”.
  3. Select “I want to GENERATE a DFU file from S19, HEX or BIN files”, press OK.
  4. Click the button that says “S19 or Hex…”, find the ODriveFirmware.hex file you built or downloaded.
  5. Leave all the other settings as default and click the “Generate…” button.
  6. Save the output file as ODriveFirmware.dfu. Note that the success message has a warning sign for some reason…
  7. Launch DfuSeDemo.exe which probably got added to the start menu as “DfuSeDemo”.
  8. Force the ODrive into DFU mode, as per the instructions above “How to force DFU mode”.
  9. In the top left it should now be connected to “STM Device in DFU Mode”.
  10. If it doesn’t appear, it may be because the driver is set to libusb by Zadig. We need to set it back to the original driver. Follow these instructions.
  11. If, after doing the above step, the ODrive still installs itself as a libusb device in Device Manager, you can try to delete the libusb driver (this is OK, since we can use Zadig to install it again). You can simply delete the file C:\Windows\System32\drivers\libusb0.sys.
  12. In the bottom right section called “Upgrade or Verify Action” click the button “Choose…”.
  13. Locate the ODriveFirmware.dfu we made before.
  14. Click button “Upgrade”.
  15. If you get a warning that it’s not possible to check that it’s the correct device type: click yes to continue.
  16. Congratulations your ODrive should now be flashed; you can now quit DfuSeDemo.
  17. Turn off the power to the ODrive and set the DIP switch back to RUN mode.


Changelog: ODrive/ at master · odriverobotics/ODrive · GitHub

[0.5.3] - 2021-09-03


  • ASCII protocol commands with multiline responses (i, h) now return the expected response (in v0.5.2 the response was corrupted)
  • odrivetool no longer shows the message <Task pending coro=... running at ...> when closing
  • Homing used to erroneously complete with is_homed == True even if it failed for some reason
  • When entering closed loop control in trapezoidal trajectory mode the axis no longer snaps to the 0 position
  • Fix python DFU firmware version prerelease status resolution to use correct attribute
  • Fixed firmware compiled-in version number


  • brake_resistor_current added to interface for reading the commanded brake resistor current


  • Removed odrivetool generate-code. This feature was broken in 0.5.2. Use instead (see Tupfile.lua for examples).
  • Firmware boots on devices with unset OTP.
  • Changed CAN heartbeat message to include “trajectory done” flag

Please report any bugs here or on the odriverobotics github page: Issues · odriverobotics/ODrive · GitHub

1 Like

I might have stumbled upon a couple of bugs.
The first one is related to startup_encoder_index_search. With the previous firmware version, I was able to start the index search at startup on both axis. Now, it simply does not work. All variables seem to be correctly set, but at startup nothing happens. Furthermore, if I try to put one of the axes in AXIS_STATE_CLOSED_LOOP_CONTROL right after bootup (no new calibration), I hear the current running through the phases, but the motor does not hold its position (maybe it is due to the failed index search).
dump_errors(odrv0) doesn’t show any errors.

I’ll report here the steps I used for axis0 configuration(axis1 is the same):

odrv0.axis0.controller.config.vel_limit= 5
odrv0.axis0.encoder.config.mode = ENCODER_MODE_INCREMENTAL
odrv0.axis0.encoder.config.use_index =True
odrv0.axis0.encoder.config.calib_range = 0.05
odrv0.axis0.motor.config.calibration_current = 10.0
odrv0.axis0.motor.config.resistance_calib_max_voltage = 2.0

odrv0.axis0.requested_state = AXIS_STATE_FULL_CALIBRATION_SEQUENCE
odrv0.axis0.config.startup_encoder_index_search =True


It might be related to this change.
I was testing the CAN communication between my ODrive and my RPI 4B.
The RPI 4B mounts a CAN-SPI hat from Seedstudio (see 2 Channel CAN BUS FD Shield for Raspberry Pi - Seeed Wiki), which has two MCP2518FD chips.
I already tested successfully this shield with ODrive using the previous firmware and Buster OS on the RPI. For setting up the hat I simply used the installation script available at seeed-linux-dtoverlays/modules/CAN-HAT at master · Seeed-Studio/seeed-linux-dtoverlays · GitHub and I was able to receive correctly the Heartbeat and also use the
Now, due to practical reasons, I have installed Ubuntu 20.04 Server on my RPI. Following the Wiki at 2 Channel CAN BUS FD Shield for Raspberry Pi - Seeed Wiki, I added " dtoverlay=seeed-can-fd-hat-v2" in my /boot/firmware/usercfg.txt file and rebooted.
After this, it appears that the two CAN interfaces are successfully initialized

After this, I set the can0 interface with “sudo ip link set can0 up type can bitrate 250000”, power up the ODrive and connect it to the CAN bus (after having set the correct bitrate) and I run “candump can0 -xct z” to check the Heartbeat message.
I have the following strange result:

The bus configuration if the following:

And ODrive can settings are:

To further investigate the problem, I also tried to run the, with the following result:

Basically, the calibration starts and seems to finish successfully, but the script does not detect that the axis is back to IDLE state.

1 Like

Small update. Apparently the only reason why wasn’t working is that and, as a consequence, odrive-cansimple.dbc were not update to take into account the different Heartbeat message structure. Modifying the database with protocol message specs available at solves the “issue”.
However, I still do not understand why I am getting all those additional messages, since the Heartbeat should run, as far as I am aware, at 10Hz.

You’re not the only person who’s reported an issue with index search. See Encoder Index Search Fails on 0.5.3 · Issue #605 · odriverobotics/ODrive · GitHub

Can you do any more experiments to see if it works during normal calibration, etc?

Yes, sorry, the .dbc file wasn’t updated. I will fix that on the repo.

0x001 is the axis 0 heartbeat (10Hz by default)
0x021 is the axis 1 heartbeat (10Hz by default)
0x009 is the axis 0 encoder positions (100hz by default)
0x029 is the axis 1 encoder position (100Hz by default)

See <axis>.config.can.encoder_rate_ms

Actually, I was doing some tests this morning to isolate better the problem.
What happens is that normal calibration seems to work just fine on both axes.
When I run encoder index search, the following happens:
Axis0 starts to rotate and then seems to sort of slip at a certain point. However, if I run dump_errors(odrv0) no error is reported.
Axis1 does not move at all (not even noise from the phases).
Normal calibration and closed loop control seems to work fine.

1 Like

Thanks @Wetmelon. I couldn’t understand why all those messages were popping up

1 Like

@Samuel looks like there may be some issues with the ascii protocol introspection on v0.5.3: