20#include "motoron_protocol.h"
24extern const PROGMEM uint8_t motoronCrcTable[256];
31 Motoron18v18 = 0b0001,
32 Motoron24v14 = 0b0101,
33 Motoron18v20 = 0b1010,
34 Motoron24v16 = 0b1101,
91 uint8_t cmd = MOTORON_CMD_GET_FIRMWARE_VERSION;
94 if (productId !=
nullptr) { *productId = response[0] | (response[1] << 8); }
95 if (firmwareVersion !=
nullptr) { *firmwareVersion = response[2] | (response[3] << 8); }
141 MOTORON_CMD_SET_PROTOCOL_OPTIONS,
142 (uint8_t)(options & 0x7F),
143 (uint8_t)(~options & 0x7F),
145 sendCommandCore(
sizeof(cmd), cmd,
true);
173 | (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS)
174 | (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES));
181 & ~(1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS)
182 & ~(1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES));
189 | (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS));
196 & ~(1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS));
203 | (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES));
210 & ~(1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES));
217 | (1 << MOTORON_PROTOCOL_OPTION_I2C_GENERAL_CALL));
224 & ~(1 << MOTORON_PROTOCOL_OPTION_I2C_GENERAL_CALL));
231 void readEeprom(uint8_t offset, uint8_t length, uint8_t * buffer)
234 MOTORON_CMD_READ_EEPROM,
235 (uint8_t)(offset & 0x7F),
236 (uint8_t)(length & 0x7F),
248 readEeprom(MOTORON_SETTING_DEVICE_NUMBER, 1, &number);
265 cmd[0] = MOTORON_CMD_WRITE_EEPROM;
266 cmd[1] = offset & 0x7F;
267 cmd[2] = value & 0x7F;
268 cmd[3] = value >> 7 & 1;
269 cmd[4] = cmd[1] ^ 0x7F;
270 cmd[5] = cmd[2] ^ 0x7F;
271 cmd[6] = cmd[3] ^ 0x7F;
300 writeEeprom(MOTORON_SETTING_DEVICE_NUMBER, number & 0x7F);
301 writeEeprom(MOTORON_SETTING_DEVICE_NUMBER + 1, number >> 7 & 0x7F);
317 writeEeprom(MOTORON_SETTING_ALTERNATIVE_DEVICE_NUMBER, (number & 0x7F) | 0x80);
318 writeEeprom(MOTORON_SETTING_ALTERNATIVE_DEVICE_NUMBER + 1, number >> 7 & 0x7F);
333 writeEeprom(MOTORON_SETTING_ALTERNATIVE_DEVICE_NUMBER, 0);
334 writeEeprom(MOTORON_SETTING_ALTERNATIVE_DEVICE_NUMBER + 1, 0);
351 writeEeprom(MOTORON_SETTING_COMMUNICATION_OPTIONS, options);
365 if (baud < MOTORON_MIN_BAUD_RATE) { baud = MOTORON_MIN_BAUD_RATE; }
366 if (baud > MOTORON_MAX_BAUD_RATE) { baud = MOTORON_MAX_BAUD_RATE; }
367 writeEeprom16(MOTORON_SETTING_BAUD_DIVIDER, (16000000 + (baud >> 1)) / baud);
381 writeEeprom(MOTORON_SETTING_RESPONSE_DELAY, delay);
394 uint8_t cmd = MOTORON_CMD_REINITIALIZE;
395 sendCommandCore(1, &cmd,
true);
411 uint8_t cmd = MOTORON_CMD_RESET;
412 sendCommandCore(1, &cmd,
true);
429 void getVariables(uint8_t motor, uint8_t offset, uint8_t length, uint8_t * buffer)
432 MOTORON_CMD_GET_VARIABLES,
433 (uint8_t)(motor & 0x7F),
434 (uint8_t)(offset & 0x7F),
435 (uint8_t)(length & 0x7F),
445 uint8_t
getVar8(uint8_t motor, uint8_t offset)
461 return buffer[0] | ((uint16_t)buffer[1] << 8);
514 return getVar16(0, MOTORON_VAR_STATUS_FLAGS);
523 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_PROTOCOL_ERROR);
541 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_COMMAND_TIMEOUT_LATCHED);
550 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_MOTOR_FAULT_LATCHED);
559 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_NO_POWER_LATCHED);
599 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_MOTOR_FAULTING);
617 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_ERROR_ACTIVE);
626 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_MOTOR_OUTPUT_ENABLED);
635 return getStatusFlags() & (1 << MOTORON_STATUS_FLAG_MOTOR_DRIVING);
660 return getVar8(0, MOTORON_VAR_UART_FAULTS);
671 return getVar16(0, MOTORON_VAR_VIN_VOLTAGE);
686 uint16_t scale = (uint8_t)type & 1 ? 459 : 1047;
687 return (uint32_t)
getVinVoltage() * referenceMv / 1024 * scale / 47;
698 return getVar16(0, MOTORON_VAR_COMMAND_TIMEOUT) * 4;
710 return getVar8(0, MOTORON_VAR_ERROR_RESPONSE);
722 return getVar16(0, MOTORON_VAR_ERROR_MASK);
731 return getVar8(0, MOTORON_VAR_JUMPER_STATE);
743 return getVar16(motor, MOTORON_MVAR_TARGET_SPEED);
754 return getVar16(motor, MOTORON_MVAR_TARGET_BRAKE_AMOUNT);
766 return getVar16(motor, MOTORON_MVAR_CURRENT_SPEED);
777 return getVar16(motor, MOTORON_MVAR_BUFFERED_SPEED);
788 return getVar8(motor, MOTORON_MVAR_PWM_MODE);
800 return getVar16(motor, MOTORON_MVAR_MAX_ACCEL_FORWARD);
812 return getVar16(motor, MOTORON_MVAR_MAX_ACCEL_REVERSE);
824 return getVar16(motor, MOTORON_MVAR_MAX_DECEL_FORWARD);
836 return getVar16(motor, MOTORON_MVAR_MAX_DECEL_REVERSE);
842 uint16_t getMaxDecelerationTemporary(uint8_t motor)
844 return getVar16(motor, MOTORON_MVAR_MAX_DECEL_TMP);
857 return getVar16(motor, MOTORON_MVAR_STARTING_SPEED_FORWARD);
868 return getVar16(motor, MOTORON_MVAR_STARTING_SPEED_REVERSE);
880 return getVar8(motor, MOTORON_MVAR_DIRECTION_CHANGE_DELAY_FORWARD);
892 return getVar8(motor, MOTORON_MVAR_DIRECTION_CHANGE_DELAY_REVERSE);
905 return getVar16(motor, MOTORON_MVAR_CURRENT_LIMIT);
922 getVariables(motor, MOTORON_MVAR_CURRENT_SENSE_RAW,
sizeof(buffer), buffer);
924 r.raw = buffer[0] | ((uint16_t)buffer[1] << 8);
925 r.speed = buffer[2] | ((uint16_t)buffer[3] << 8);
926 r.processed = buffer[4] | ((uint16_t)buffer[5] << 8);
939 getVariables(motor, MOTORON_MVAR_CURRENT_SENSE_RAW,
sizeof(buffer), buffer);
941 r.raw = buffer[0] | ((uint16_t)buffer[1] << 8);
942 r.speed = buffer[2] | ((uint16_t)buffer[3] << 8);
955 getVariables(motor, MOTORON_MVAR_CURRENT_SENSE_SPEED,
sizeof(buffer), buffer);
957 r.speed = buffer[0] | ((uint16_t)buffer[1] << 8);
958 r.processed = buffer[2] | ((uint16_t)buffer[3] << 8);
972 return getVar16(motor, MOTORON_MVAR_CURRENT_SENSE_RAW);
996 return getVar16(motor, MOTORON_MVAR_CURRENT_SENSE_PROCESSED);
1009 return getVar8(motor, MOTORON_MVAR_CURRENT_SENSE_OFFSET);
1023 return getVar8(motor, MOTORON_MVAR_CURRENT_SENSE_MINIMUM_DIVISOR) << 2;
1040 if (value > 0x3FFF) { value = 0x3FFF; }
1042 MOTORON_CMD_SET_VARIABLE,
1043 (uint8_t)(motor & 0x1F),
1044 (uint8_t)(offset & 0x7F),
1045 (uint8_t)(value & 0x7F),
1046 (uint8_t)((value >> 7) & 0x7F),
1061 uint16_t timeout = (ms / 4) + ((ms & 3) ? 1 : 0);
1062 setVariable(0, MOTORON_VAR_COMMAND_TIMEOUT, timeout);
1081 setVariable(0, MOTORON_VAR_ERROR_RESPONSE, response);
1113 setErrorMask(defaultErrorMask & ~(1 << MOTORON_STATUS_FLAG_COMMAND_TIMEOUT));
1126 setVariable(0, MOTORON_VAR_UART_FAULTS, ~(uint16_t)flags & 0x3FFF);
1161 setVariable(motor, MOTORON_MVAR_MAX_ACCEL_FORWARD, accel);
1173 setVariable(motor, MOTORON_MVAR_MAX_ACCEL_REVERSE, accel);
1196 setVariable(motor, MOTORON_MVAR_MAX_DECEL_FORWARD, decel);
1208 setVariable(motor, MOTORON_MVAR_MAX_DECEL_REVERSE, decel);
1231 setVariable(motor, MOTORON_MVAR_STARTING_SPEED_FORWARD, speed);
1243 setVariable(motor, MOTORON_MVAR_STARTING_SPEED_REVERSE, speed);
1266 setVariable(motor, MOTORON_MVAR_DIRECTION_CHANGE_DELAY_FORWARD, duration);
1278 setVariable(motor, MOTORON_MVAR_DIRECTION_CHANGE_DELAY_REVERSE, duration);
1305 setVariable(motor, MOTORON_MVAR_CURRENT_LIMIT, limit);
1329 setVariable(motor, MOTORON_MVAR_CURRENT_SENSE_OFFSET, offset);
1349 setVariable(motor, MOTORON_MVAR_CURRENT_SENSE_MINIMUM_DIVISOR, speed >> 2);
1359 uint8_t cmd = MOTORON_CMD_COAST_NOW;
1375 uint8_t cmd[] = { MOTORON_CMD_CLEAR_MOTOR_FAULT, (uint8_t)(flags & 0x7F) };
1400 uint8_t cmd[] = { MOTORON_CMD_CLEAR_LATCHED_STATUS_FLAGS,
1401 (uint8_t)(flags & 0x7F),
1402 (uint8_t)(flags >> 7 & 0x7F)
1439 uint8_t cmd[] = { MOTORON_CMD_SET_LATCHED_STATUS_FLAGS,
1440 (uint8_t)(flags & 0x7F),
1441 (uint8_t)(flags >> 7 & 0x7F)
1467 MOTORON_CMD_SET_SPEED,
1468 (uint8_t)(motor & 0x7F),
1469 (uint8_t)(speed & 0x7F),
1470 (uint8_t)((speed >> 7) & 0x7F),
1488 MOTORON_CMD_SET_SPEED_NOW,
1489 (uint8_t)(motor & 0x7F),
1490 (uint8_t)(speed & 0x7F),
1491 (uint8_t)((speed >> 7) & 0x7F),
1513 MOTORON_CMD_SET_BUFFERED_SPEED,
1514 (uint8_t)(motor & 0x7F),
1515 (uint8_t)(speed & 0x7F),
1516 (uint8_t)((speed >> 7) & 0x7F),
1538 MOTORON_CMD_SET_ALL_SPEEDS,
1539 (uint8_t)(speed1 & 0x7F),
1540 (uint8_t)((speed1 >> 7) & 0x7F),
1541 (uint8_t)(speed2 & 0x7F),
1542 (uint8_t)((speed2 >> 7) & 0x7F),
1543 (uint8_t)(speed3 & 0x7F),
1544 (uint8_t)((speed3 >> 7) & 0x7F),
1553 MOTORON_CMD_SET_ALL_SPEEDS,
1554 (uint8_t)(speed1 & 0x7F),
1555 (uint8_t)((speed1 >> 7) & 0x7F),
1556 (uint8_t)(speed2 & 0x7F),
1557 (uint8_t)((speed2 >> 7) & 0x7F),
1566 MOTORON_CMD_SET_ALL_SPEEDS,
1567 (uint8_t)(speed1 & 0x7F),
1568 (uint8_t)((speed1 >> 7) & 0x7F),
1589 MOTORON_CMD_SET_ALL_SPEEDS_NOW,
1590 (uint8_t)(speed1 & 0x7F),
1591 (uint8_t)((speed1 >> 7) & 0x7F),
1592 (uint8_t)(speed2 & 0x7F),
1593 (uint8_t)((speed2 >> 7) & 0x7F),
1594 (uint8_t)(speed3 & 0x7F),
1595 (uint8_t)((speed3 >> 7) & 0x7F),
1604 MOTORON_CMD_SET_ALL_SPEEDS_NOW,
1605 (uint8_t)(speed1 & 0x7F),
1606 (uint8_t)((speed1 >> 7) & 0x7F),
1607 (uint8_t)(speed2 & 0x7F),
1608 (uint8_t)((speed2 >> 7) & 0x7F),
1617 MOTORON_CMD_SET_ALL_SPEEDS_NOW,
1618 (uint8_t)(speed1 & 0x7F),
1619 (uint8_t)((speed1 >> 7) & 0x7F),
1646 MOTORON_CMD_SET_ALL_BUFFERED_SPEEDS,
1647 (uint8_t)(speed1 & 0x7F),
1648 (uint8_t)((speed1 >> 7) & 0x7F),
1649 (uint8_t)(speed2 & 0x7F),
1650 (uint8_t)((speed2 >> 7) & 0x7F),
1651 (uint8_t)(speed3 & 0x7F),
1652 (uint8_t)((speed3 >> 7) & 0x7F),
1661 MOTORON_CMD_SET_ALL_BUFFERED_SPEEDS,
1662 (uint8_t)(speed1 & 0x7F),
1663 (uint8_t)((speed1 >> 7) & 0x7F),
1664 (uint8_t)(speed2 & 0x7F),
1665 (uint8_t)((speed2 >> 7) & 0x7F),
1674 MOTORON_CMD_SET_ALL_BUFFERED_SPEEDS,
1675 (uint8_t)(speed1 & 0x7F),
1676 (uint8_t)((speed1 >> 7) & 0x7F),
1690 uint8_t cmd = MOTORON_CMD_SET_ALL_SPEEDS_USING_BUFFERS;
1704 uint8_t cmd = MOTORON_CMD_SET_ALL_SPEEDS_NOW_USING_BUFFERS;
1729 MOTORON_CMD_SET_BRAKING,
1730 (uint8_t)(motor & 0x7F),
1731 (uint8_t)(amount & 0x7F),
1732 (uint8_t)((amount >> 7) & 0x7F),
1757 MOTORON_CMD_SET_BRAKING_NOW,
1758 (uint8_t)(motor & 0x7F),
1759 (uint8_t)(amount & 0x7F),
1760 (uint8_t)((amount >> 7) & 0x7F),
1777 uint8_t cmd = MOTORON_CMD_RESET_COMMAND_TIMEOUT;
1789 for (uint8_t i = 0; i < length; i++)
1791 crc = pgm_read_byte(&motoronCrcTable[crc ^ buffer[i]]);
1822 if (milliamps > 1000000) { milliamps = 1000000; }
1823 uint16_t limit = (uint32_t)(offset * 125 + 64) / 128 +
1824 milliamps * 20 / (referenceMv * ((uint8_t)type & 3));
1825 if (limit > 1000) { limit = 1000; }
1848 return (type == MotoronCurrentSenseType::Motoron453) ? 0
1849 : ((uint32_t)referenceMv * ((uint8_t)type & 3) * 25 / 512);
1872 return type == MotoronCurrentSenseType::Motoron453
1873 ? (uint32_t)referenceMv * 625 / 1056
1874 : ((uint32_t)referenceMv * ((uint8_t)type & 3) * 3125 / 64);
1889 bool sendCrc =
protocolOptions & (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS);
1890 sendCommandCore(length, cmd, sendCrc);
1896 uint8_t responseLength, uint8_t * response)
1901 memset(response, 0, responseLength);
1904 readResponse(responseLength, response);
1909 virtual void sendCommandCore(uint8_t length,
const uint8_t * cmd,
bool sendCrc) = 0;
1910 virtual void flushTransmission() = 0;
1911 virtual void readResponse(uint8_t length, uint8_t * response) = 0;
1913 static const uint8_t defaultProtocolOptions =
1914 (1 << MOTORON_PROTOCOL_OPTION_I2C_GENERAL_CALL) |
1915 (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS) |
1916 (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES);
1918 static const uint16_t defaultErrorMask =
1919 (1 << MOTORON_STATUS_FLAG_COMMAND_TIMEOUT) |
1920 (1 << MOTORON_STATUS_FLAG_RESET);
1931 MotoronI2C(uint8_t address = 16) : bus(&Wire), address(address) {}
1956 this->address = address;
1969 void sendCommandCore(uint8_t length,
const uint8_t * cmd,
bool sendCrc)
override
1971 bus->beginTransmission(address);
1972 for (uint8_t i = 0; i < length; i++)
1983 void flushTransmission() { }
1985 void readResponse(uint8_t length, uint8_t * response)
override
1987 bool crcEnabled =
protocolOptions & (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES);
1988 uint8_t byteCount = bus->requestFrom(address, (uint8_t)(length + crcEnabled));
1989 if (byteCount != length + crcEnabled)
1991 memset(response, 0, length);
1996 uint8_t * ptr = response;
1997 for (uint8_t i = 0; i < length; i++)
2002 if (crcEnabled && bus->read() !=
calculateCrc(length, response))
2032 port(nullptr), deviceNumber(deviceNumber), communicationOptions(0)
2039 port(&port), deviceNumber(deviceNumber), communicationOptions(0)
2074 this->deviceNumber = deviceNumber;
2083 return deviceNumber;
2100 communicationOptions = options;
2109 return communicationOptions;
2120 communicationOptions |= (1 << MOTORON_COMMUNICATION_OPTION_7BIT_RESPONSES);
2127 communicationOptions &= ~(1 << MOTORON_COMMUNICATION_OPTION_7BIT_RESPONSES);
2138 communicationOptions |= (1 << MOTORON_COMMUNICATION_OPTION_14BIT_DEVICE_NUMBER);
2145 communicationOptions &= ~(1 << MOTORON_COMMUNICATION_OPTION_14BIT_DEVICE_NUMBER);
2157 if (communicationOptions & (1 << MOTORON_COMMUNICATION_OPTION_14BIT_DEVICE_NUMBER))
2159 if (deviceCount > 0x3FFF) {
lastError = 55;
return; }
2161 MOTORON_CMD_MULTI_DEVICE_ERROR_CHECK,
2162 (uint8_t)(startingDeviceNumber & 0x7F),
2163 (uint8_t)(startingDeviceNumber >> 7 & 0x7F),
2164 (uint8_t)(deviceCount & 0x7F),
2165 (uint8_t)(deviceCount >> 7 & 0x7F),
2171 if (deviceCount > 0x7F) {
lastError = 55;
return; }
2173 MOTORON_CMD_MULTI_DEVICE_ERROR_CHECK,
2174 (uint8_t)(startingDeviceNumber & 0x7F),
2175 (uint8_t)deviceCount,
2202 for (i = 0; i < deviceCount; i++)
2205 size_t byteCount = port->readBytes(&response, 1);
2206 if (byteCount < 1 || response != MOTORON_ERROR_CHECK_CONTINUE)
2221 uint8_t bytesPerDevice, uint8_t commandByte,
const uint8_t * data)
2223 if (port ==
nullptr) {
lastError = 52;
return; }
2224 if (bytesPerDevice > 15) {
lastError = 56;
return; }
2226 bool sendCrc =
protocolOptions & (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_COMMANDS);
2228 uint8_t header[10] = { 0 };
2229 if (communicationOptions & (1 << MOTORON_COMMUNICATION_OPTION_14BIT_DEVICE_NUMBER))
2231 if (deviceCount > 0x3FFF) {
lastError = 55;
return; }
2233 header[4] = startingDeviceNumber & 0x7F;
2234 header[5] = startingDeviceNumber >> 7 & 0x7F;
2235 header[6] = deviceCount & 0x7F;
2236 header[7] = deviceCount >> 7 & 0x7F;
2237 header[8] = bytesPerDevice;
2238 header[9] = commandByte & 0x7F;
2240 if (deviceNumber == 0xFFFF)
2242 header[3] = MOTORON_CMD_MULTI_DEVICE_WRITE;
2243 port->write(header + 3, 7);
2248 header[1] = deviceNumber & 0x7F;
2249 header[2] = deviceNumber >> 7 & 0x7F;
2250 header[3] = MOTORON_CMD_MULTI_DEVICE_WRITE & 0x7F;
2251 port->write(header, 10);
2256 if (deviceCount > 0x7F) {
lastError = 55;
return; }
2258 header[6] = startingDeviceNumber & 0x7F;
2259 header[7] = deviceCount;
2260 header[8] = bytesPerDevice;
2261 header[9] = commandByte & 0x7F;
2263 if (deviceNumber == 0xFFFF)
2265 header[5] = MOTORON_CMD_MULTI_DEVICE_WRITE;
2266 port->write(header + 5, 5);
2271 header[4] = deviceNumber & 0x7F;
2272 header[5] = MOTORON_CMD_MULTI_DEVICE_WRITE & 0x7F;
2273 port->write(header + 3, 7);
2278 if (sendCrc) { crc =
calculateCrc(
sizeof(header), header); }
2284 port->write(data, bytesPerDevice);
2285 if (sendCrc) { crc =
calculateCrc(bytesPerDevice, data, crc); }
2286 data += bytesPerDevice;
2291 if (sendCrc) { port->write(crc); }
2296 uint16_t deviceNumber;
2297 uint8_t communicationOptions;
2299 void sendCommandCore(uint8_t length,
const uint8_t * cmd,
bool sendCrc)
override
2301 if (port ==
nullptr) {
lastError = 52;
return; }
2303 if (deviceNumber == 0xFFFF)
2305 port->write(cmd, length);
2314 if (communicationOptions & (1 << MOTORON_COMMUNICATION_OPTION_14BIT_DEVICE_NUMBER))
2317 header[1] = deviceNumber & 0x7F;
2318 header[2] = deviceNumber >> 7 & 0x7F;
2319 header[3] = cmd[0] & 0x7F;
2320 port->write(header, 4);
2326 header[2] = deviceNumber & 0x7F;
2327 header[3] = cmd[0] & 0x7F;
2328 port->write(header + 1, 3);
2330 port->write(cmd + 1, length - 1);
2341 void flushTransmission()
2343 if (port ==
nullptr) {
return; }
2347 void readResponse(uint8_t length, uint8_t * response)
override
2349 if (port ==
nullptr)
2352 memset(response, 0, length);
2356 bool response7Bit = communicationOptions & (1 << MOTORON_COMMUNICATION_OPTION_7BIT_RESPONSES);
2357 if (response7Bit && length > 7)
2363 memset(response, 0, length);
2369 size_t byteCount = port->readBytes(response, length);
2370 if (byteCount != length)
2373 memset(response, 0, length);
2380 if (port->readBytes(&msbs, 1) != 1)
2387 bool crcEnabled =
protocolOptions & (1 << MOTORON_PROTOCOL_OPTION_CRC_FOR_RESPONSES);
2391 if (port->readBytes(&crc, 1) != 1)
2403 if (crc != expected_crc)
2412 for (uint8_t i = 0; i < length; i++)
2414 if (msbs & 1) { response[i] |= 0x80; }
@ Motoron550
M*550 Motorons.
@ MotoronHp
High-power Motorons.
@ Motoron256
M*256 Motorons.
void setDirectionChangeDelay(uint8_t motor, uint8_t duration)
void setCommandTimeoutMilliseconds(uint16_t ms)
uint16_t getMaxAccelerationForward(uint8_t motor)
uint16_t getCurrentLimit(uint8_t motor)
int16_t getBufferedSpeed(uint8_t motor)
void setErrorResponse(uint8_t response)
void setBraking(uint8_t motor, uint16_t amount)
int16_t getTargetSpeed(uint8_t motor)
uint16_t getMaxDecelerationForward(uint8_t motor)
bool getMotorDrivingFlag()
void clearUARTFaults(uint8_t flags)
void writeEepromAlternativeDeviceNumber(uint16_t number)
uint16_t getTargetBrakeAmount(uint8_t motor)
uint16_t getMaxAccelerationReverse(uint8_t motor)
uint8_t getErrorResponse()
void setErrorMask(uint16_t mask)
void writeEepromDeviceNumber(uint16_t number)
void setMaxDeceleration(uint8_t motor, uint16_t decel)
void setVariable(uint8_t motor, uint8_t offset, uint16_t value)
uint16_t getStartingSpeedReverse(uint8_t motor)
void enableI2cGeneralCall()
Enables the I2C general call address. See setProtocolOptions().
void setAllBufferedSpeeds(int16_t speed1, int16_t speed2)
An overload of setAllBufferedSpeeds() for 2-channel Motorons.
uint16_t getMaxDecelerationReverse(uint8_t motor)
uint16_t getVar16(uint8_t motor, uint8_t offset)
MotoronCurrentSenseReading getCurrentSenseReading(uint8_t motor)
void writeEeprom(uint8_t offset, uint8_t value)
void enableCrcForCommands()
Enables CRC for commands. See setProtocolOptions().
static constexpr uint32_t currentSenseUnitsMicroamps(MotoronCurrentSenseType type, uint16_t referenceMv)
static uint8_t calculateCrc(uint8_t length, const uint8_t *buffer, uint8_t init=0)
void setCurrentSenseMinimumDivisor(uint8_t motor, uint16_t speed)
void disableCrc()
Disables CRC for commands and responses. See setProtocolOptions().
void setAllSpeedsUsingBuffers()
void setAllBufferedSpeeds(int16_t speed1, int16_t speed2, int16_t speed3)
uint8_t getCurrentSenseOffset(uint8_t motor)
uint16_t getCommandTimeoutMilliseconds()
uint32_t getVinVoltageMv(uint16_t referenceMv, MotoronVinSenseType type=MotoronVinSenseType::Motoron256)
void disableCrcForResponses()
Disables CRC for responses. See setProtocolOptions().
void setBufferedSpeed(uint8_t motor, int16_t speed)
void setStartingSpeedForward(uint8_t motor, uint16_t speed)
void setMaxAccelerationForward(uint8_t motor, uint16_t accel)
void getVariables(uint8_t motor, uint8_t offset, uint8_t length, uint8_t *buffer)
bool getMotorFaultLatchedFlag()
void setMaxAccelerationReverse(uint8_t motor, uint16_t accel)
void disableCrcForCommands()
Disables CRC for commands. See setProtocolOptions().
void enableCrcForResponses()
Enables CRC for responses. See setProtocolOptions().
uint16_t getStatusFlags()
void clearMotorFaultUnconditional()
void writeEepromDisableAlternativeDeviceNumber()
bool getCommandTimeoutLatchedFlag()
uint8_t getPwmMode(uint8_t motor)
void setProtocolOptionsLocally(uint8_t options)
uint8_t readEepromDeviceNumber()
uint8_t getDirectionChangeDelayForward(uint8_t motor)
uint8_t getDirectionChangeDelayReverse(uint8_t motor)
void setAllBufferedSpeeds(int16_t speed1)
An overload of setAllBufferedSpeeds() for 1-channel Motorons.
void setDirectionChangeDelayReverse(uint8_t motor, uint8_t duration)
void setPwmMode(uint8_t motor, uint8_t mode)
void setCurrentLimit(uint8_t motor, uint16_t limit)
void sendCommandAndReadResponse(uint8_t cmdLength, const uint8_t *cmd, uint8_t responseLength, uint8_t *response)
void disableI2cGeneralCall()
Disables the I2C general call address. See setProtocolOptions().
void setAllSpeeds(int16_t speed1, int16_t speed2, int16_t speed3)
uint8_t protocolOptions
See setProtocolOptions.
bool getProtocolErrorFlag()
void resetCommandTimeout()
void setLatchedStatusFlags(uint16_t flags)
uint8_t getProtocolOptionsLocally()
void getFirmwareVersion(uint16_t *productId, uint16_t *firmwareVersion)
void setAllSpeedsNow(int16_t speed1, int16_t speed2, int16_t speed3)
void setAllSpeeds(int16_t speed1)
An overload of setAllSpeeds() for single-channel Motorons.
void setMaxDecelerationReverse(uint8_t motor, uint16_t decel)
void setStartingSpeed(uint8_t motor, uint16_t speed)
void clearLatchedStatusFlags(uint16_t flags)
void setMaxDecelerationForward(uint8_t motor, uint16_t decel)
static constexpr uint16_t currentSenseUnitsMilliamps(MotoronCurrentSenseType type, uint16_t referenceMv)
MotoronCurrentSenseReading getCurrentSenseProcessedAndSpeed(uint8_t motor)
bool getMotorOutputEnabledFlag()
uint16_t getCurrentSenseRaw(uint8_t motor)
void setCurrentSenseOffset(uint8_t motor, uint8_t offset)
void setMaxAcceleration(uint8_t motor, uint16_t accel)
bool getErrorActiveFlag()
void sendCommand(uint8_t length, const uint8_t *cmd)
void setStartingSpeedReverse(uint8_t motor, uint16_t speed)
uint16_t getStartingSpeedForward(uint8_t motor)
void writeEepromBaudRate(uint32_t baud)
void setAllSpeeds(int16_t speed1, int16_t speed2)
An overload of setAllSpeeds() for 2-channel Motorons.
void setAllSpeedsNowUsingBuffers()
bool getNoPowerLatchedFlag()
uint16_t getCurrentSenseMinimumDivisor(uint8_t motor)
void disableCommandTimeout()
void setDirectionChangeDelayForward(uint8_t motor, uint8_t duration)
uint8_t getVar8(uint8_t motor, uint8_t offset)
void writeEeprom16(uint8_t offset, uint16_t value)
void setAllSpeedsNow(int16_t speed1)
An overload of setAllSpeedsNow() for single-channel Motorons.
void setBrakingNow(uint8_t motor, uint16_t amount)
void enableCrc()
Enables CRC for commands and responses. See setProtocolOptions().
uint16_t getCurrentSenseProcessed(uint8_t motor)
void readEeprom(uint8_t offset, uint8_t length, uint8_t *buffer)
void setSpeed(uint8_t motor, int16_t speed)
void writeEepromResponseDelay(uint8_t delay)
bool getMotorFaultingFlag()
static uint16_t calculateCurrentLimit(uint32_t milliamps, MotoronCurrentSenseType type, uint16_t referenceMv, uint16_t offset)
void setSpeedNow(uint8_t motor, int16_t speed)
void setAllSpeedsNow(int16_t speed1, int16_t speed2)
An overload of setAllSpeedsNow() for 2-channel Motorons.
void setProtocolOptions(uint8_t options)
void clearMotorFault(uint8_t flags=0)
MotoronCurrentSenseReading getCurrentSenseRawAndSpeed(uint8_t motor)
int16_t getCurrentSpeed(uint8_t motor)
void writeEepromCommunicationOptions(uint8_t options)
void setBus(TwoWire *bus)
void setAddress(uint8_t address)
MotoronI2C(uint8_t address=16)
uint8_t getAddress()
Returns the 7-bit I2C address that this object is configured to use.
void setCommunicationOptions(uint8_t options)
MotoronSerial(Stream &port, uint16_t deviceNumber=0xFFFF)
void use7BitDeviceNumber()
void expect8BitResponses()
uint16_t multiDeviceErrorCheck(uint16_t startingDeviceNumber, uint16_t deviceCount)
void multiDeviceWrite(uint16_t startingDeviceNumber, uint16_t deviceCount, uint8_t bytesPerDevice, uint8_t commandByte, const uint8_t *data)
void multiDeviceErrorCheckStart(uint16_t startingDeviceNumber, uint16_t deviceCount)
uint8_t getCommunicationOptionsLocally()
MotoronSerial(uint16_t deviceNumber=0xFFFF)
uint16_t getDeviceNumber()
void use14BitDeviceNumber()
void setPort(Stream *port)
void setDeviceNumber(uint16_t deviceNumber)
void expect7BitResponses()