From 0cfd87dbce985fc1177bc434138d7d172b57f9cc Mon Sep 17 00:00:00 2001 From: joshua-8 Date: Sun, 3 Dec 2023 22:28:12 -0500 Subject: [PATCH] basic speed control is working for both motors --- README.md | 6 ++-- examples/basic/basic.ino | 24 +++++++++++++-- src/TMC7300.h | 65 ++++++++++++++++++++++++++++++++++++---- src/TMCSerial.h | 29 ++++++++++++++++++ 4 files changed, 113 insertions(+), 11 deletions(-) create mode 100644 src/TMCSerial.h diff --git a/README.md b/README.md index 43143e4..6c34e7c 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,8 @@ # 7300 (under development) ## Arduino library for controlling TMC7300 DC motor driver ICs +[![Arduino Lint](https://github.com/joshua-8/TMC7300/actions/workflows/arduino-lint.yml/badge.svg)](https://github.com/joshua-8/TMC7300/actions/workflows/arduino-lint.yml) + https://github.com/joshua-8/TMC7300 ## [Doxygen reference](https://joshua-8.github.io/TMC7300/) @@ -15,7 +17,7 @@ My goal is to make a good library for controlling the TMC7300 chips, and to keep * ESP32-S3 QT Py # Acknowledgements -* This library is based on @bread-wolf's work in the [TMCSerial](https://github.com/bread-wolf/TMCSerial) and[TMCField](https://github.com/bread-wolf/TMCField) libraries, both of which are generously licensed under the AGPL3.0 license. -* This library is also based on work done by @trinamic and Analog Devices Inc. in the [TMC-API](https://github.com/trinamic/TMC-API/tree/master), which is generously licensed under the MIT license. +* This library is based on [@bread-wolf](https://github.com/bread-wolf)'s work in the [TMCSerial](https://github.com/bread-wolf/TMCSerial) and [TMCField](https://github.com/bread-wolf/TMCField) libraries, both of which are generously licensed under the AGPL3.0 license. +* This library is based on work done by [@trinamic](https://github.com/trinamic) and [Analog Devices Inc.](https://www.analog.com) in the [TMC-API](https://github.com/trinamic/TMC-API/tree/master), which is generously licensed under the MIT license. Find the comments in the code of this library to see which parts are based on which of the above libraries. diff --git a/examples/basic/basic.ino b/examples/basic/basic.ino index bfffd28..40d30bb 100644 --- a/examples/basic/basic.ino +++ b/examples/basic/basic.ino @@ -1,10 +1,28 @@ #include -#include +#include + +/* + * https://github.com/joshua-8/TMC7300 + */ + +const byte ENpin = A1; // EN pin of driver, pulling it low until setup is complete prevents a short twitch on start +TMC7300IC driver = TMC7300IC(5, 0, 10000); // uartPin, chipAddress, baudrate -TMC7300IC a = TMC7300IC(); void setup() { + pinMode(ENpin, OUTPUT); + digitalWrite(ENpin, LOW); + driver.begin(); + digitalWrite(ENpin, HIGH); } void loop() { -} \ No newline at end of file + driver.writeField(TMC7300_PWM_A, -230); + delay(1000); + driver.writeField(TMC7300_PWM_B, 150); + delay(1000); + driver.writeField(TMC7300_PWM_A, 250); + delay(1000); + driver.writeField(TMC7300_PWM_B, -230); + delay(1000); +} diff --git a/src/TMC7300.h b/src/TMC7300.h index 177f795..6f08b08 100644 --- a/src/TMC7300.h +++ b/src/TMC7300.h @@ -1,10 +1,32 @@ #ifndef TMC7300_H #define TMC7300_H #include "TMC7300_Map.h" +#include "TMCSerial.h" #include +#define TMC_WRITE_BIT 0x80 + class TMC7300IC { +public: + TMC7300IC(uint8_t _pin, uint8_t _chipAddress, uint32_t _baudrate = 115200) + : pin(_pin) + , chipAddress(_chipAddress) + , baudrate(_baudrate) + { + } + void begin() + { + pinMode(pin, OUTPUT); + digitalWrite(pin, HIGH); + delay(10); // TODO: WHAT DELAY ON STARTUP IS NEEDED? + writeField(TMC7300_PWM_DIRECT, 1); + } + protected: + uint8_t pin; + uint8_t chipAddress; + uint32_t baudrate; + // clang-format off int32_t registers[10] = { // 0 1 2 3 4 5 6 7 8 9 @@ -20,16 +42,47 @@ class TMC7300IC { } uint32_t readField(TMCField field) { - uint32_t registerValueReceived = readRegister(field.address()); - registers[field.valueAddress()] = registerValueReceived; + // uint32_t registerValueReceived = readRegister(field.address()); + // registers[field.valueAddress()] = registerValueReceived; return field.getField(registers[field.valueAddress()]); } void writeRegister(uint8_t address, uint32_t value) { + + // from https://github.com/bread-wolf/TMCSerial/blob/cb87877ab4f3c39ed7a5b1ec99cf73eb0f4d5a6c/TMCSerial.cpp#L78C4-L94C6 + uint8_t addressWrite = address | TMC_WRITE_BIT; + uint8_t writeRequest[8] = { SYNC_BYTE, chipAddress, addressWrite, 0, 0, 0, 0, 0 }; + + /* Fill data to be written */ + writeRequest[3] = (value >> 24) & 0xFF; + writeRequest[4] = (value >> 16) & 0xFF; + writeRequest[5] = (value >> 8) & 0xFF; + writeRequest[6] = (value) & 0xFF; + + /* Calculate CRC */ + writeRequest[7] = calcCRC(writeRequest, 7); + + unsigned long lastMicros = 0; + /* Write data */ + for (uint8_t j = 0; j < 8; j++) { + lastMicros = micros(); + digitalWrite(TX, LOW); // Start bit + while ((micros() - lastMicros) < (1000000 / baudrate)) { } + lastMicros = micros(); + for (uint8_t i = 0; i < 8; i++) { + digitalWrite(TX, (writeRequest[j] >> i) & 0x01); + while ((micros() - lastMicros) < (1000000 / baudrate)) { } + lastMicros = micros(); + } + digitalWrite(TX, HIGH); // Stop bit + while ((micros() - lastMicros) < (1000000 / baudrate)) { } + lastMicros = micros(); + } + // TODO: DELAY SOME BETWEEN MESSAGES? } - uint32_t readRegister(uint8_t address) - { - return 0; - } + // uint32_t readRegister(uint8_t address) + // { + // return 0; + // } }; #endif // TMC7300_H diff --git a/src/TMCSerial.h b/src/TMCSerial.h new file mode 100644 index 0000000..8455380 --- /dev/null +++ b/src/TMCSerial.h @@ -0,0 +1,29 @@ +#ifndef TMCSERIAL_H +#define TMCSERIAL_H +#include + +#define SYNC_BYTE 0x55 +#define WRITE_BIT 0x80 + +// from https://github.com/bread-wolf/TMCSerial/blob/cb87877ab4f3c39ed7a5b1ec99cf73eb0f4d5a6c/TMCSerial.cpp#L181C1-L206C2 +uint8_t calcCRC(uint8_t data[], uint8_t dataLength) +{ + uint8_t crc, currentByte; + + /* Initialize crc at 0 */ + crc = 0; + for (uint8_t j = 0; j < dataLength; j++) { + currentByte = data[j]; + for (uint8_t k = 0; k < 8; k++) { + if ((crc >> 7) ^ (currentByte & 0x01)) { + /* Use 0b100000111 as polynomial */ + crc = (crc << 1) ^ 0x07; + } else { + crc = (crc << 1); + } + currentByte >>= 1; + } + } + return crc; +} +#endif // TMCSERIAL_H