CRC Calculation

Hello @Yogurt_Man and @willson ,

We are trying to write a library for Dynamixel XC330-M288-Y in Arduino. We wish to perform basic functions (i.e. move to goal position and move with some velocity). We saw how protocol 2.0 works and we were trying to set the instruction packet to implement a simple reset function. But we are not able to figure out how to calculate the CRC field. We set other packet fields as well such as Header, ID, Length, Instruction, and Parameters. We went through the site mentioning the CRC calculation but still we are not able to figure out how the set CRC_L and CRC_H filed, hence we need help with that.

1 Like

See the following,

  1. Regarding CRC_L and CRC_H, you should make it shift and separate High and Low bytes.
CRC = update_crc(0, TxPacket , 12);   // 12 = 5 + Packet Length(7)
CRC_L = (CRC & 0x00FF);               //Little-endian
CRC_H = (CRC>>8) & 0x00FF;
  1. If you are using any library, you should confirm the options as follows,

1 Like

Hey,
Thank you for your prompt response.
I see you used TXPacket in the update_crc function. I am confused as in the CRC calculation link Tx packet is defined as follows,

unsigned char TxPacket[] = {0xFF, 0xFF, 0xFD, 0x00, 0x01, 0x07, 0x00, 0x02, 0x00, 0x00, 0x02, 0x00, CRC_L, CRC_H}
CRC = update_crc(0, TxPacket , 12);   // 12 = 5 + Packet Length(7)
CRC_L = (CRC & 0x00FF);               //Little-endian
CRC_H = (CRC>>8) & 0x00FF;

How can we define CRC_L and CRC_H in TxPacket and calculate them later?
Also, I try to search what update_crc() function does, but I haven’t got any results explaining the function. Can you explain the function as well? Can we include the update_crc() function without including any library? If not which library we should include?
Can you explain CRC calculation by writing a simple reset instruction packet for Protocol 2.0? This will greatly help us to understand the writing Instruction packet.
Thank you!!!

Hi @Amey

Just out of my personal curiosity, is there any particular reason for rewriting the DYNAMIXEL2Arduino library for your Arduino project?

The update_crc() in the DYNAMIXEL2Arduino library accepts the address of the current crc and the DYNAMIXEL packet to calculate the index of the crc lookup table.

When implementing a custom library, many developers miss the byte stuffing which prevents unusual case when the data has the identical sequence with the Header(FF FF FD)

Please refer to the Packet Process section of the eManual for more information.

Thank you.

Hi @willson

Thank you for your reply.

We are trying to use ESPP32 V1 with Dynamixel XC330-T288-T. We tried running Dynamixel2Arduino code to ESP32, but that did not work. Connection; ESP to Dynamixel Shield and the shield to Dynamixel motor. We tried adding a level converter as well between ESP and Dynamixel shield, did not work. Then we came across this GitHub page, here they used ESP32 directly with Dynamixelc(video link) by creating their own library. Since they are using AX12 (Protocol 1.0) we cannot use it. Therefore we thought of writing our own. If you have any alternate suggestions for this please let us know.

Thank you.

@Amey

It might be much easier to modify the DYNAMIXELShield library (which is dependent on DYNAMIXEL2Arduino library) since it does not have specific hardware definitions in it.

Unfortunately, I do not have the ESP32 in my hand right now, so could you try the below and let me know?

  1. Install the DYNAMIXELShield library from Arduino IDE. It will ask whether to install the D2A library as well

  2. Select your ESP board from Arduino IDE > Tools > Board > ESP32 Arduino (or if you have installed other board manager, please let me know)

  3. Open a scan_dynamixel example from File > Examples > DynamixelShield > Basic

  4. Connect the Serial pins of the ESP32 to the DXL_TX / DXL_RX pins of the DYNAMIXEL Shield board

  5. Connect one of the GPIO pin to the DXL_DIR port

  6. Modify the scan_dynamixel example definitions to use the correct DXL_SERIAL port and DXL_DIR_PIN

  7. Set the UART SW of the DYNAMIXEL Shield to the DYNAMIXEL side.

  8. Connect the power to the DYNAMIXEL Shield and turn on the Power SW

  9. Upload the sketch and open the terminal to read the messages

Hey,

Thank you for the above information, we tried that and got the following output,

rst:0x8 (TG1WDT_SYS_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1344
load:0x40078000,len:13864
load:0x40080400,len:3608
entry 0x400805f0
SCAN PROTOCOL 1
SCAN BAUDRATE 57600
ets Jun  8 2016 00:22:57

We also tried running the Position mode from examples but that didn’t move the Dynamixel but we got the same output on the serial monitor as above.

Thank you.

Hi @Amey

It looks like the dxl.begin() function is blocking the loop.
Could you check which ESP32 pin is connected to the DXL_DIR of the DYNAMIXEL Shield?
If possible, please share your connection diagram so that I can better understand your system.
Thanks!

Hello Wilson,

I hope you had a great weekend.

We tried to come up with a better idea to send you connections but it looks like a block diagram is the only easy option. We are also supplying external power to the shield.
Let us know if any other information is required.

Thank you

1 Like

Thanks Amey,

Could you specify the exact model name of the ESP32 board you use?
Does the PIN2 in your diagram mean GPIO2 in the image below?
Could you check the Arduino pin serial definition for those TX2 / RX2?

You’ll need to add the serial port and DIR pin Arduino definitions to the example code in order to make DYNAMIXEL2Arduino access the port.

If you have a logic analyzer or an oscilloscope, it will be very helpful to probe the PIN2 and the TX2 signals and see if there’s any DYNAMIXEL packet is transmitted.

Thanks!

I happen to find a Feather ESP32 and below is my setup to run the scan_dynamixel Arduino example.

The Tx/Rx serial port was defined as Serial in the ESP board manager, and I needed to define the DXL_DIR pin in the DynamixelShield.h of the DynamixelShield library as below.

#if defined(USE_ARDUINO_MKR_PIN_LAYOUT) || defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_PORTENTA_H7_M4)
  #define DXL_DIR_PIN		A6
#elif defined(ARDUINO_FEATHER_ESP32)  // Define pin 21 of the feather ESP32 as DXL Direction control pin
  #define DXL_DIR_PIN   21
#else
  #define DXL_DIR_PIN		2
#endif

I connected my XL330-M288-T which has a model number of 1200 and it was correctly detected as shown below.

Thank you for the reply and useful information.

I will change the pin definition in the .h file and also do the necessary changes and let you know.

Thank you

Hello Willison,

Could you specify the exact model name of the ESP32 board you use?

→ ESP32 Devkit V1

Does the PIN2 in your diagram mean GPIO2 in the image below?

→ Yes

I checked and modified the pin definition the results are shown below:-

  1. For Tx0/Rx0

image

The output I am receiving is

rst:0x8 (TG1WDT_SYS_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1344
load:0x40078000,len:13864
load:0x40080400,len:3608
entry 0x400805f0
SCAN PROTOCOL 1
SCAN BAUDRATE 57600
ets Jun  8 2016 00:22:57

I also faced an error while uploading, when I connect Rx/Tx for ESP32 and Dynamixel shield and try to upload code I see the following error. Maybe because ESP32 USB also uses serial(Tx0/Rx0).

image

  1. For Tx1/Rx1

By changing serial to serial1 in code and keeping the connecting Tx0/Rx0 of Esp32 to shield we got the following output, we also tried to change it to Tx2/Rx2 but same output.

rst:0x8 (TG1WDT_SYS_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1344
load:0x40078000,len:13864
load:0x40080400,len:3608
entry 0x400805f0
ets Jun  8 2016 00:22:57

There is no pin in ESP32 labeled as Tx1/Rx1. ESP32 will crash if use them more details are here

The last attempt, connecting Tx2/Rx2 to shield. Changing serial to serial2 output is shown below:-

rst:0x8 (TG1WDT_SYS_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1344
load:0x40078000,len:13864
load:0x40080400,len:3608
entry 0x400805f0
ets Jun  8 2016 00:22:57

I also checked other baud rates like 57600 or 1000000 but got garbage values on the serial monitor.

Hi @Amey

I just noticed that your TX and RX connections are switched.
You should connect the TX from the ESP board to the DXL_TX of the DYNAMIXEL Shield, and the same goes for the RX pins.

Unfortunately, I’m not that familiar with the ESP32 boards and don’t have much information to debug the error message you’ve copied in the above.

From the ESP32 Dev Kit V1 in the Arduino ESP32 library that I downloaded, I wasn’t able to find which pin is connected to the GPIO2(or Pin2 in your diagram that is connected to the DXL_DIR).
If you can find the pin definition of your board, you should replace the DXL_DIR_PIN number from 21 to a correct pin value of your ESP32 board.

Last but not least, please make sure to supply 5V and 3.3V to the DYNAMIXEL Shield as these voltages are necessary to run the ICs on it.

Thanks!

Hello Willson,

I tried switching RX/TX pins but got the same result. We have a constant 5V supply to DYNAMIXEL shield.
I tried changing pins for DXL_DIR but no outcome. I tried 2, 21, 26, 23, 33, 34.
Can you please tell me what information is missing? I can get you all information you want.

Thanks!

I happen to find a Feather ESP32 and below is my setup to run the scan_dynamixel Arduino example.

image

The Tx/Rx serial port was defined as Serial in the ESP board manager, and I needed to define the DXL_DIR pin in the DynamixelShield.h of the DynamixelShield library as below.

#if defined(USE_ARDUINO_MKR_PIN_LAYOUT) || defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_PORTENTA_H7_M4)
  #define DXL_DIR_PIN		A6
#elif defined(ARDUINO_FEATHER_ESP32)  // Define pin 21 of the feather ESP32 as DXL Direction control pin
  #define DXL_DIR_PIN   21
#else
  #define DXL_DIR_PIN		2
#endif

I connected my XL330-M288-T which has a model number of 1200 and it was correctly detected as shown below.

image

I tried exact same connection and changed the code as well but it didn’t work. I switched the TX/RX pin and changed DXL_DIR_PIN as well. Our final output is Dynamixel not found.

Can you share details about your Feather Board?

Thank you!

1 Like

Hii @Yogurt_Man @willson

Just following up - did you get a chance to take a look at this config?

Thank you for your continued help! You’re the best!

Hi @Amey

I’m sorry about the delayed response.
The Feather board that I used is made by Adafruit.

I installed esp32 board package by Espressif Systems as below

and selected adafruit_feather_esp32_v2 from the ESP32 Arduino boards.
Then modified the DynamixelShield.h to use the pin 21 as DXL_DIR_PIN.

2 Likes