HF-TMC9660 Driver 0.1.0-dev
Hardware Agnostic C++ Driver for the TMC9660
Loading...
Searching...
No Matches
tmc9660::TMC9660Bootloader< CommType > Class Template Reference

Main TMC9660 bootloader interface class. More...

#include <tmc9660_bootloader.hpp>

Public Member Functions

 TMC9660Bootloader (CommType &comm) noexcept
 Construct a TMC9660Bootloader instance.
 
bool setBank (uint8_t bank) noexcept
 Select the target memory bank for subsequent operations.
 
bool setBank (MemoryBank bank) noexcept
 Select the target register bank using enum (overloaded).
 
bool setAddress (uint32_t addr) noexcept
 Set the address within the current memory bank.
 
bool write8 (uint8_t v) noexcept
 Write a single byte to the previously selected address.
 
bool write16 (uint16_t v) noexcept
 Write a 16-bit word to the previously selected address.
 
bool write32 (uint32_t v) noexcept
 Write a 32-bit word to the previously selected address.
 
bool write8Inc (uint8_t v) noexcept
 Write a single byte and increment address by 1.
 
bool write16Inc (uint16_t v) noexcept
 Write a 16-bit word and increment address by 2.
 
bool write32Inc (uint32_t v) noexcept
 Write a 32-bit word and increment address by 4.
 
bool write32IncMultiple (const uint32_t *values, size_t count) noexcept
 Write multiple 32-bit words starting at the current address.
 
bool read8 (uint8_t *value) noexcept
 Read a single byte from the previously selected address.
 
bool read16 (uint16_t *value) noexcept
 Read a 16-bit word from the previously selected address.
 
bool read32 (uint32_t *value) noexcept
 Read a 32-bit word from the previously selected address.
 
bool read8Inc (uint8_t *value) noexcept
 Read a single byte and increment address by 1.
 
bool read16Inc (uint16_t *value) noexcept
 Read a 16-bit word and increment address by 2.
 
bool read32Inc (uint32_t *value) noexcept
 Read a 32-bit word and increment address by 4.
 
bool getBank (uint8_t *bank) noexcept
 Get the currently selected memory bank.
 
bool getAddress (uint32_t *address) noexcept
 Get the currently selected memory address.
 
bool noOp (uint32_t *reply=nullptr) noexcept
 No operation - retrieve reply from previous command (SPI only).
 
bool readAndVerify8 (uint8_t expected, const char *config_name) noexcept
 Read back and verify an 8-bit value matches the expected value.
 
bool readAndVerify16 (uint16_t expected, const char *config_name) noexcept
 Read back and verify a 16-bit value matches the expected value.
 
bool readAndVerify32 (uint32_t expected, const char *config_name) noexcept
 Read back and verify a 32-bit value matches the expected value.
 
bool otpLoad (uint8_t page, OtpLoadResult *result) noexcept
 Load an OTP (One-Time Programmable) page into the OTP memory bank.
 
bool otpLoad (uint8_t page, uint8_t *error_count=nullptr, uint8_t *page_tag=nullptr) noexcept
 Load an OTP page (legacy method with separate parameters).
 
bool otpBurn (uint8_t page, uint8_t page_addr, OtpBurnResult *result) noexcept
 Permanently burn data to OTP (One-Time Programmable) memory.
 
bool otpBurn (uint8_t page, uint8_t page_addr=0) noexcept
 Permanently burn OTP page (legacy method without detailed results).
 
bool otpBurnWithWorkaround (uint8_t page, uint8_t page_addr, OtpBurnResult *result, uint32_t vdrv_wait_ms=1000) noexcept
 Burn OTP page with Erratum 1 workaround for reliable operation.
 
bool checkOtpBurnStatus (bool *result) noexcept
 Check OTP burn status using Erratum 1 workaround verification.
 
bool memIsConfigured (MemoryBank bank, bool *is_configured) noexcept
 Check if external memory is configured.
 
bool memIsConnected (MemoryBank bank, bool *is_connected) noexcept
 Check if external memory is connected.
 
bool memIsBusy (MemoryBank bank, bool *is_busy) noexcept
 Check if external memory is busy.
 
bool flashLoadBuffer (uint8_t offset, uint32_t data) noexcept
 Load data into internal 6-byte flash command buffer.
 
bool flashReadBuffer (uint8_t offset, uint32_t *data) noexcept
 Read data from internal 6-byte flash command buffer.
 
bool flashSendDatagram (uint8_t num_bytes) noexcept
 Send datagram to SPI flash and receive reply.
 
bool flashEraseSector (uint32_t address) noexcept
 Erase a sector on external SPI flash.
 
bool flashReadJedecId (uint8_t *manufacturer_id) noexcept
 Read JEDEC manufacturer ID from SPI flash.
 
bool bootstrapRS485 (uint8_t tx_en_pin, uint8_t pre_delay, uint8_t host_addr, uint8_t device_addr) noexcept
 Configure RS485 communication (must be first command for RS485).
 
bool getInfo (InfoQuery query, uint32_t *value) noexcept
 Get bootloader information.
 
bool getChipType (uint32_t *chip_type) noexcept
 Get chip type (should return 0x544D0001 for TMC9660).
 
bool getBootloaderVersion (BootloaderVersion *version) noexcept
 Get bootloader version information.
 
bool getFeatures (BootloaderFeatures *features) noexcept
 Get available feature flags.
 
bool getGitInfo (GitInfo *git_info) noexcept
 Get Git version control information.
 
bool getChipVersion (uint32_t *version) noexcept
 Get chip version (silicon revision).
 
bool getChipFrequency (uint32_t *frequency) noexcept
 Get system frequency in MHz.
 
bool getConfigMemStart (uint32_t *address) noexcept
 Get CONFIG memory bank start address.
 
bool getConfigMemSize (uint32_t *size) noexcept
 Get CONFIG memory bank size.
 
bool getOtpMemSize (uint32_t *size) noexcept
 Get OTP memory page size.
 
bool getI2cMemSize (uint32_t *size) noexcept
 Get I2C memory size.
 
bool getSpiMemSize (uint32_t *size) noexcept
 Get SPI memory size.
 
bool getPartitionVersion (PartitionVersion *version) noexcept
 Get partition version information.
 
bool getSpiMemPartitions (uint32_t *count) noexcept
 Get number of SPI memory partitions.
 
bool getI2cMemPartitions (uint32_t *count) noexcept
 Get number of I2C memory partitions.
 
bool getChipVariant (uint32_t *variant) noexcept
 Get chip variant (TMC9660 reports value 2).
 
bool getAllBootloaderInfo () noexcept
 Retrieve and log all available bootloader information.
 
bool applyConfiguration (const BootloaderConfig &cfg, bool fail_on_verify_error=true) noexcept
 Apply all fields of a ::BootloaderConfig.
 
bool startMotorControl (bootcfg::BootMode boot_mode=bootcfg::BootMode::Parameter) noexcept
 Start the motor control system and exit bootloader mode.
 

Private Member Functions

bool sendCommand (uint8_t cmd, uint32_t value, uint32_t *reply=nullptr) noexcept
 Send a bootloader command and optionally receive a reply.
 
bool sendCommandSPI (uint8_t cmd, uint32_t value, uint32_t *reply) noexcept
 Send a bootloader command via SPI interface.
 
bool sendCommandUART (uint8_t cmd, uint32_t value, uint32_t *reply) noexcept
 Send a bootloader command via UART interface.
 

Private Attributes

CommTypecomm_
 
uint8_t deviceAddr_
 Device address for UART protocol.
 
uint8_t hostAddr_
 Host address for UART protocol.
 

Detailed Description

template<typename CommType>
class tmc9660::TMC9660Bootloader< CommType >

Main TMC9660 bootloader interface class.

This class provides comprehensive bootloader functionality for the TMC9660 including memory operations, configuration management, OTP programming, and system initialization. The bootloader is essential for configuring the TMC9660 before transitioning to parameter mode operation.

Key Features

  • Memory Operations: Read/write to RAM, OTP, SPI Flash, I2C EEPROM
  • Configuration Management: Complete bootloader configuration application
  • OTP Programming: One-time programmable memory burning with workarounds
  • System Information: Retrieve bootloader version, features, and capabilities
  • Protocol Support: Both SPI and UART communication interfaces
  • Error Handling: Comprehensive error reporting and verification

Usage Pattern

// Create bootloader instance
// Configure the system
cfg.ldo.vext1_voltage = bootcfg::LDOVoltage::V3_3;
cfg.boot.start_motor_control = true;
// Apply configuration and start motor control
bootloader.applyConfiguration(cfg);
SPI status codes as per TMC9660 Parameter Mode.
Definition tmc9660_comm_interface.hpp:514
@ V3_3
3.3V output voltage
@ Parameter
Parameter mode - TMCL command-based motor control (recommended)
Complete bootloader configuration structure.
Definition bootloader_config.hpp:998
Template Parameters
CommTypeThe communication interface type (must inherit from SpiCommInterface<CommType> or UartCommInterface<CommType>)

Constructor & Destructor Documentation

◆ TMC9660Bootloader()

template<typename CommType >
TMC9660Bootloader::TMC9660Bootloader ( CommType & comm)
explicitnoexcept

Construct a TMC9660Bootloader instance.

Initializes the bootloader with the specified communication interface and sets default UART addresses as per the TMC9660 specification.

Parameters
commReference to the communication interface for bootloader commands

Member Function Documentation

◆ applyConfiguration()

template<typename CommType >
bool TMC9660Bootloader::applyConfiguration ( const BootloaderConfig & cfg,
bool failOnVerifyError = true )
noexcept

Apply all fields of a ::BootloaderConfig.

Apply all fields of a BootloaderConfig to the TMC9660.

This function applies a complete bootloader configuration by writing all configuration structures to their respective registers in the CONFIG memory bank. It provides a convenient single-call interface for comprehensive system configuration.

Parameters
cfgConfiguration to apply
fail_on_verify_errorIf true, return false on read-back verification failure; if false, log warning but continue
Returns
true if successful
Note
If cfg.boot.start_motor_control is true, bootloader will exit after this call

This method performs the complete bootloader configuration sequence by writing all configuration registers in the correct order. It handles the complex register dependencies and ensures proper initialization.

The configuration is applied in the following order:

  1. LDO configuration
  2. Clock configuration (CRITICAL - must be done before motor control)
  3. UART addresses and RS485 delays
  4. Communication interface selection
  5. SPI flash and I2C EEPROM configuration
  6. GPIO configuration (output levels, directions, pull settings)
  7. Encoder and sensor configuration
  8. Brake and mechanical configuration
  9. Memory storage configuration
  10. Boot configuration (FINAL - may exit bootloader)
Parameters
cfgComplete bootloader configuration to apply
failOnVerifyErrorIf true, return false on read-back verification failure; if false, log warning but continue
Returns
true if configuration was applied successfully, false on error
Note
If cfg.boot.start_motor_control is true, bootloader will exit after this call
Warning
Clock reconfiguration takes time and the TMC9660 cannot respond during this process

Apply complete bootloader configuration with proper register sequencing.

This method performs the complete bootloader configuration sequence by writing all configuration registers in the correct order. It handles complex register dependencies and ensures proper initialization of the TMC9660 system.

The configuration is applied in a specific order to handle dependencies:

  1. LDO configuration - Power supply settings
  2. Clock configuration - CRITICAL timing setup (may cause temporary unresponsiveness)
  3. UART addresses and RS485 delays - Communication parameters
  4. Communication interface selection - SPI/UART mode
  5. SPI flash and I2C EEPROM configuration - External memory settings
  6. GPIO configuration - Pin directions, levels, and pull settings
  7. Encoder and sensor configuration - Feedback system setup
  8. Brake and mechanical configuration - Safety and mechanical systems
  9. Memory storage configuration - Data storage parameters
  10. Boot configuration - FINAL step (may exit bootloader mode)
Parameters
cfgComplete bootloader configuration structure to apply
failOnVerifyErrorIf true, return false on read-back verification failure; if false, log warning but continue with configuration
Returns
true if configuration was applied successfully, false on error
Note
If cfg.boot.start_motor_control is true, bootloader will exit after this call
Warning
Clock reconfiguration takes time and the TMC9660 cannot respond during this process

◆ bootstrapRS485()

template<typename CommType >
bool TMC9660Bootloader::bootstrapRS485 ( uint8_t tx_en_pin,
uint8_t pre_delay,
uint8_t host_addr,
uint8_t device_addr )
noexcept

Configure RS485 communication (must be first command for RS485).

Initializes RS485 half-duplex communication parameters. This command must be sent as the first command when using RS485 communication interface. It configures the transmit enable pin and timing parameters.

Parameters
tx_en_pinGPIO pin for TX_EN (1=GPIO8, 2=GPIO2)
pre_delayDelay between TX_EN assertion and TX start
host_addrHost address
device_addrDevice address
Returns
true if successful

◆ checkOtpBurnStatus()

template<typename CommType >
bool TMC9660Bootloader::checkOtpBurnStatus ( bool * result)
noexcept

Check OTP burn status using Erratum 1 workaround verification.

Verifies the result of an OTP burn operation by checking multiple status indicators. Implements Erratum 1 workaround for reliable status verification.

Parameters
resultPointer to receive true if burn was successful
Returns
true if status check completed successfully
Note
This method implements the Erratum 1 status check workaround

◆ flashEraseSector()

template<typename CommType >
bool TMC9660Bootloader::flashEraseSector ( uint32_t address)
noexcept

Erase a sector on external SPI flash.

Performs a sector erase operation on the external SPI flash memory at the specified address. This prepares the sector for new data programming.

Parameters
address24-bit sector address
Returns
true if successful

◆ flashLoadBuffer()

template<typename CommType >
bool TMC9660Bootloader::flashLoadBuffer ( uint8_t offset,
uint32_t data )
noexcept

Load data into internal 6-byte flash command buffer.

Loads data into the TMC9660's internal flash command buffer, which is used to prepare SPI flash commands before transmission. The buffer can hold up to 6 bytes of command and address data.

Parameters
offsetByte offset in buffer (0-5)
data24-bit data to load (bits 23-0)
Returns
true if successful

◆ flashReadBuffer()

template<typename CommType >
bool TMC9660Bootloader::flashReadBuffer ( uint8_t offset,
uint32_t * data )
noexcept

Read data from internal 6-byte flash command buffer.

Reads data from the TMC9660's internal flash command buffer. This can be used to verify buffer contents or read response data from flash operations.

Parameters
offsetByte offset in buffer (0-5)
dataReturns 24-bit data read (bits 23-0)
Returns
true if successful

◆ flashReadJedecId()

template<typename CommType >
bool TMC9660Bootloader::flashReadJedecId ( uint8_t * manufacturer_id)
noexcept

Read JEDEC manufacturer ID from SPI flash.

Reads the JEDEC manufacturer ID from the external SPI flash device. This can be used to identify the flash chip type and verify connectivity.

Parameters
manufacturer_idReturns manufacturer ID
Returns
true if successful

◆ flashSendDatagram()

template<typename CommType >
bool TMC9660Bootloader::flashSendDatagram ( uint8_t num_bytes)
noexcept

Send datagram to SPI flash and receive reply.

Transmits the specified number of bytes from the internal flash command buffer to the external SPI flash device and receives the response.

Parameters
num_bytesNumber of bytes to transmit (1-6)
Returns
true if successful

◆ getAddress()

template<typename CommType >
bool TMC9660Bootloader::getAddress ( uint32_t * address)
noexcept

Get the currently selected memory address.

Retrieves the memory address that was last set via setAddress() within the currently selected bank. Useful for tracking address pointer state.

Parameters
addressPointer to receive the current address
Returns
true if query successful

◆ getAllBootloaderInfo()

template<typename CommType >
bool TMC9660Bootloader::getAllBootloaderInfo ( )
noexcept

Retrieve and log all available bootloader information.

This function queries all GET_INFO commands and logs the results. Useful for debugging and verifying chip configuration.

Information retrieved:

  • Chip type, version, variant
  • Bootloader version and Git info
  • System frequency
  • Available features (SRAM, ROM, OTP, SPI flash, I2C EEPROM)
  • Memory sizes and partition info
Returns
true if at least basic info was retrieved successfully
Note
Some queries may fail if features are not available (e.g., no SPI flash)
Here is the call graph for this function:

◆ getBank()

template<typename CommType >
bool TMC9660Bootloader::getBank ( uint8_t * bank)
noexcept

Get the currently selected memory bank.

Retrieves the memory bank number that was last selected via setBank(). Useful for verifying the current bank configuration.

Parameters
bankPointer to receive the current bank number (0-5)
Returns
true if query successful

◆ getBootloaderVersion()

template<typename CommType >
bool TMC9660Bootloader::getBootloaderVersion ( BootloaderVersion * version)
noexcept

Get bootloader version information.

Retrieves and parses the bootloader version information from the TMC9660. The version is returned in major.minor format for easy interpretation.

Parameters
versionReturns parsed version information
Returns
true if successful

Retrieves the bootloader version information including major and minor version numbers. This is useful for compatibility checking and debugging.

Parameters
versionPointer to store the parsed version information
Returns
true if version was retrieved successfully, false on error
Here is the call graph for this function:

◆ getChipFrequency()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getChipFrequency ( uint32_t * frequency)
inlinenoexcept

Get system frequency in MHz.

Retrieves the current system clock frequency in MHz. This reflects the actual operating frequency after PLL and divider configurations.

Parameters
frequencyReturns frequency in MHz
Returns
true if successful
Here is the call graph for this function:

◆ getChipType()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getChipType ( uint32_t * chip_type)
inlinenoexcept

Get chip type (should return 0x544D0001 for TMC9660).

Retrieves the chip type identifier. For TMC9660, this should return 0x544D0001, which can be used to verify correct chip identification.

Parameters
chip_typeReturns chip type
Returns
true if successful
Here is the call graph for this function:

◆ getChipVariant()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getChipVariant ( uint32_t * variant)
inlinenoexcept

Get chip variant (TMC9660 reports value 2).

Retrieves the chip variant identifier. For TMC9660, this should return value 2, which can be used to verify correct chip identification.

Parameters
variantReturns chip variant
Returns
true if successful
Here is the call graph for this function:

◆ getChipVersion()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getChipVersion ( uint32_t * version)
inlinenoexcept

Get chip version (silicon revision).

Retrieves the silicon revision number of the TMC9660 chip. This information is useful for identifying chip variants and applying silicon-specific workarounds.

Parameters
versionReturns chip version
Returns
true if successful
Here is the call graph for this function:

◆ getConfigMemSize()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getConfigMemSize ( uint32_t * size)
inlinenoexcept

Get CONFIG memory bank size.

Retrieves the size of the CONFIG memory bank in bytes. This indicates how much configuration space is available for bootloader settings.

Parameters
sizeReturns memory size
Returns
true if successful
Here is the call graph for this function:

◆ getConfigMemStart()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getConfigMemStart ( uint32_t * address)
inlinenoexcept

Get CONFIG memory bank start address.

Retrieves the starting address of the CONFIG memory bank (bank 5). This is typically 0x00020000 for TMC9660.

Parameters
addressReturns start address
Returns
true if successful
Here is the call graph for this function:

◆ getFeatures()

template<typename CommType >
bool TMC9660Bootloader::getFeatures ( BootloaderFeatures * features)
noexcept

Get available feature flags.

Retrieves feature flags indicating which capabilities are supported by the bootloader hardware, including available memory types and interfaces.

Parameters
featuresReturns parsed feature flags
Returns
true if successful
Here is the call graph for this function:

◆ getGitInfo()

template<typename CommType >
bool TMC9660Bootloader::getGitInfo ( GitInfo * git_info)
noexcept

Get Git version control information.

Retrieves Git commit hash and dirty bit from the bootloader firmware, indicating the exact firmware build version and development state.

Parameters
git_infoReturns parsed Git information
Returns
true if successful
Here is the call graph for this function:

◆ getI2cMemPartitions()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getI2cMemPartitions ( uint32_t * count)
inlinenoexcept

Get number of I2C memory partitions.

Retrieves the number of partitions available in the connected I2C EEPROM memory for storing TMCL scripts and configuration data.

Parameters
countReturns number of partitions
Returns
true if successful
Here is the call graph for this function:

◆ getI2cMemSize()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getI2cMemSize ( uint32_t * size)
inlinenoexcept

Get I2C memory size.

Retrieves the total size of connected I2C EEPROM memory in bytes. Returns 0 if no I2C EEPROM is configured or connected.

Parameters
sizeReturns I2C memory size
Returns
true if successful
Here is the call graph for this function:

◆ getInfo()

template<typename CommType >
bool TMC9660Bootloader::getInfo ( InfoQuery query,
uint32_t * value )
noexcept

Get bootloader information.

Get bootloader information using the specified query type.

Generic function to query various types of system information from the bootloader. Use the specific convenience methods for typed access to parsed information structures.

Parameters
queryInformation type to query
valueReturns queried value
Returns
true if successful

Queries various information about the TMC9660 bootloader including version, features, memory sizes, and chip identification. This is useful for debugging and verifying the bootloader configuration.

Parameters
queryInformation type to query (see InfoQuery enum)
valuePointer to store the queried value
Returns
true if query was successful, false on error
Here is the caller graph for this function:

◆ getOtpMemSize()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getOtpMemSize ( uint32_t * size)
inlinenoexcept

Get OTP memory page size.

Retrieves the size of a single OTP (One-Time Programmable) memory page in bytes. This is the unit size for OTP burn operations.

Parameters
sizeReturns OTP page size
Returns
true if successful
Here is the call graph for this function:

◆ getPartitionVersion()

template<typename CommType >
bool TMC9660Bootloader::getPartitionVersion ( PartitionVersion * version)
noexcept

Get partition version information.

Retrieves the version of the external memory partition format used for storing TMCL scripts and parameters in external memory.

Parameters
versionReturns parsed partition version
Returns
true if successful
Here is the call graph for this function:

◆ getSpiMemPartitions()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getSpiMemPartitions ( uint32_t * count)
inlinenoexcept

Get number of SPI memory partitions.

Retrieves the number of partitions available in the connected SPI flash memory for storing TMCL scripts and configuration data.

Parameters
countReturns number of partitions
Returns
true if successful
Here is the call graph for this function:

◆ getSpiMemSize()

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::getSpiMemSize ( uint32_t * size)
inlinenoexcept

Get SPI memory size.

Retrieves the total size of connected SPI flash memory in bytes. Returns 0 if no SPI flash is configured or connected.

Parameters
sizeReturns SPI memory size
Returns
true if successful
Here is the call graph for this function:

◆ memIsBusy()

template<typename CommType >
bool TMC9660Bootloader::memIsBusy ( MemoryBank bank,
bool * is_busy )
noexcept

Check if external memory is busy.

Verifies whether the specified external memory device is currently busy with an operation (e.g., write cycle, erase operation).

Parameters
bankMemory bank to check
is_busyReturns true if busy
Returns
true if command successful

◆ memIsConfigured()

template<typename CommType >
bool TMC9660Bootloader::memIsConfigured ( MemoryBank bank,
bool * is_configured )
noexcept

Check if external memory is configured.

Verifies whether the specified external memory bank has been properly configured in the bootloader settings. Configuration is required before the memory can be accessed.

Parameters
bankMemory bank to check
is_configuredReturns true if configured
Returns
true if command successful

◆ memIsConnected()

template<typename CommType >
bool TMC9660Bootloader::memIsConnected ( MemoryBank bank,
bool * is_connected )
noexcept

Check if external memory is connected.

Verifies whether the specified external memory device is physically connected and responding to communication attempts.

Parameters
bankMemory bank to check
is_connectedReturns true if connected
Returns
true if command successful

◆ noOp()

template<typename CommType >
bool TMC9660Bootloader::noOp ( uint32_t * reply = nullptr)
noexcept

No operation - retrieve reply from previous command (SPI only).

Due to SPI protocol, replies are delayed by one transaction. This command sends a NO_OP to retrieve the reply from the previous command. Primarily used internally by the bootloader implementation.

Parameters
replyOptional pointer to store the 32-bit reply value
Returns
true if command successful
Note
Not needed when using UART protocol

◆ otpBurn() [1/2]

template<typename CommType >
bool TMC9660Bootloader::otpBurn ( uint8_t page,
uint8_t pageAddr,
OtpBurnResult * result )
noexcept

Permanently burn data to OTP (One-Time Programmable) memory.

Permanently burn the given OTP page.

WARNING: OTP burn operations are IRREVERSIBLE! Once a page is burned, it cannot be modified. The burn operation requires specific voltage conditions and timing to succeed.

Parameters
pageOTP page number to burn (bits 7-0)
page_addrOTP page address to write (bits 15-8)
resultPointer to receive detailed burn result with error information
Returns
true if command executed (check result.isSuccess and result.error_code)
Note
⚠️ This operation is PERMANENT and IRREVERSIBLE!

Burns (programs) the specified OTP page with the given page address. This operation is irreversible and can only be performed once per page. The OTP memory is used for storing permanent configuration data.

Parameters
pageOTP page number to burn (0-255)
pageAddrOTP page address to write (0-255)
resultPointer to store the detailed burn result with error information
Returns
true if command was sent successfully, false on communication error
Note
Check result.isSuccess and result.error_code for burn operation status
Warning
This operation is irreversible! Use with extreme caution.
Here is the call graph for this function:

◆ otpBurn() [2/2]

template<typename CommType >
bool TMC9660Bootloader::otpBurn ( uint8_t page,
uint8_t page_addr = 0 )
noexcept

Permanently burn OTP page (legacy method without detailed results).

Simplified version that only returns boolean success/failure without error details. Use the overload with OtpBurnResult for detailed error information.

Parameters
pageOTP page number to burn (bits 7-0)
page_addrOTP page address to write (bits 15-8)
Returns
true if successful
Note
⚠️ This operation is PERMANENT and IRREVERSIBLE!

◆ otpBurnWithWorkaround()

template<typename CommType >
bool TMC9660Bootloader::otpBurnWithWorkaround ( uint8_t page,
uint8_t pageAddr,
OtpBurnResult * result,
uint32_t vdrvWaitMs = 1000 )
noexcept

Burn OTP page with Erratum 1 workaround for reliable operation.

Perform OTP burn operation with Erratum 1 workaround for TMC9660.

Implements a workaround for silicon Erratum 1 that improves reliability of OTP burn operations. The workaround waits for VDRV voltage to stabilize before and after the burn operation.

Parameters
pageOTP page number to burn (bits 7-0)
page_addrOTP page address to write (bits 15-8)
resultPointer to receive detailed burn result with error information
vdrv_wait_msWait time for VDRV voltage to drop (default 1000ms for 10uF capacitor)
Returns
true if command executed (check result.isSuccess and result.error_code)
Note
⚠️ This operation is PERMANENT and IRREVERSIBLE!
Recommended method for production OTP burning

This method implements a complex workaround for TMC9660 Erratum 1, which affects OTP (One-Time Programmable) memory burning operations. The workaround involves a specific sequence of register operations to ensure proper OTP programming.

The workaround sequence:

  1. Set memory bank to 0
  2. Set address to 0x4801B010 (specific register for workaround)
  3. Read 32-bit value from the register
  4. Clear bit 0 of the read value
  5. Write the modified value back
  6. Wait for VDRV voltage to drop below 8.4V (critical timing)
  7. Perform the actual OTP burn operation
  8. Verify the burn operation success

This workaround is essential for reliable OTP programming and must be used instead of the standard OTP burn procedure when working with affected TMC9660 silicon revisions.

Parameters
pageOTP page number to burn
pageAddrAddress within the OTP page
resultPointer to store burn operation result
vdrvWaitMsMilliseconds to wait for VDRV voltage drop (typically 100-200ms)
Returns
true if workaround sequence completed successfully, false on error
Note
This method implements TMC9660 Erratum 1 workaround - do not use standard OTP burn
Warning
VDRV voltage timing is critical - incorrect timing may cause burn failure
Here is the call graph for this function:

◆ otpLoad() [1/2]

template<typename CommType >
bool TMC9660Bootloader::otpLoad ( uint8_t page,
OtpLoadResult * result )
noexcept

Load an OTP (One-Time Programmable) page into the OTP memory bank.

Load an OTP page into the OTP memory bank.

Loads a previously programmed OTP page into RAM for reading. Returns information about the loaded page including the page tag and any bit errors detected.

Parameters
pageOTP page number to load (0-based)
resultPointer to receive parsed OTP load result (error count + page tag)
Returns
true if command executed successfully (check result.error_count for bit errors)
Note
Check result.error_count for bit errors, result.page_tag for page identification

Loads the specified OTP (One-Time Programmable) page into the OTP memory bank for reading or verification. The OTP memory contains factory-programmed data that cannot be modified by the user.

Parameters
pageOTP page number to load (0-255)
resultPointer to store the OTP load result including error count and page tag
Returns
true if command was sent successfully, false on communication error
Note
Check result.errorCount for bit errors, result.pageTag for page tag
Here is the call graph for this function:

◆ otpLoad() [2/2]

template<typename CommType >
bool TMC9660Bootloader::otpLoad ( uint8_t page,
uint8_t * error_count = nullptr,
uint8_t * page_tag = nullptr )
noexcept

Load an OTP page (legacy method with separate parameters).

Legacy overload that returns error count and page tag as separate parameters instead of a structured result object.

Parameters
pageOTP page number to load
error_countOptional pointer to receive bit error count (bits 15-8)
page_tagOptional pointer to receive page tag (bits 7-0)
Returns
true if successful

◆ read16()

template<typename CommType >
bool TMC9660Bootloader::read16 ( uint16_t * value)
noexcept

Read a 16-bit word from the previously selected address.

Reads a 16-bit value from the current bank and address without modifying the address pointer. Little-endian byte order.

Parameters
valuePointer to receive the 16-bit value read
Returns
true if read successful

Reads a 16-bit value from the current address in the selected memory bank. The address pointer is not incremented after the read operation.

Parameters
valuePointer to store the 16-bit value read
Returns
true if read was successful, false on error

◆ read16Inc()

template<typename CommType >
bool TMC9660Bootloader::read16Inc ( uint16_t * value)
noexcept

Read a 16-bit word and increment address by 2.

Reads a 16-bit value and automatically increments the address pointer by 2. Useful for reading sequential data arrays.

Parameters
valuePointer to receive the 16-bit value read
Returns
true if read successful

◆ read32()

template<typename CommType >
bool TMC9660Bootloader::read32 ( uint32_t * value)
noexcept

Read a 32-bit word from the previously selected address.

Reads a 32-bit value from the current bank and address without modifying the address pointer. Little-endian byte order.

Parameters
valuePointer to receive the 32-bit value read
Returns
true if read successful

Reads a 32-bit value from the current address in the selected memory bank. The address pointer is not incremented after the read operation.

Parameters
valuePointer to store the 32-bit value read
Returns
true if read was successful, false on error

◆ read32Inc()

template<typename CommType >
bool TMC9660Bootloader::read32Inc ( uint32_t * value)
noexcept

Read a 32-bit word and increment address by 4.

Reads a 32-bit value and automatically increments the address pointer by 4. Commonly used for reading configuration registers and data arrays.

Parameters
valuePointer to receive the 32-bit value read
Returns
true if read successful

◆ read8()

template<typename CommType >
bool TMC9660Bootloader::read8 ( uint8_t * value)
noexcept

Read a single byte from the previously selected address.

Reads an 8-bit value from the current bank and address without modifying the address pointer.

Parameters
valuePointer to receive the 8-bit value read
Returns
true if read successful

Reads an 8-bit value from the current address in the selected memory bank. The address pointer is not incremented after the read operation.

Parameters
valuePointer to store the 8-bit value read
Returns
true if read was successful, false on error

◆ read8Inc()

template<typename CommType >
bool TMC9660Bootloader::read8Inc ( uint8_t * value)
noexcept

Read a single byte and increment address by 1.

Reads an 8-bit value and automatically increments the address pointer. Useful for reading sequential data arrays.

Parameters
valuePointer to receive the 8-bit value read
Returns
true if read successful

◆ readAndVerify16()

template<typename CommType >
bool TMC9660Bootloader::readAndVerify16 ( uint16_t expected,
const char * config_name )
noexcept

Read back and verify a 16-bit value matches the expected value.

Performs a read operation and compares the returned value with the expected value. Useful for verification after configuration writes. Logs the result for debugging purposes.

Parameters
expectedThe expected 16-bit value to match
config_nameHuman-readable configuration name for logging
Returns
true if read successful and value matches

◆ readAndVerify32()

template<typename CommType >
bool TMC9660Bootloader::readAndVerify32 ( uint32_t expected,
const char * config_name )
noexcept

Read back and verify a 32-bit value matches the expected value.

Performs a read operation and compares the returned value with the expected value. Useful for verification after configuration writes. Logs the result for debugging purposes.

Parameters
expectedThe expected 32-bit value to match
config_nameHuman-readable configuration name for logging
Returns
true if read successful and value matches

◆ readAndVerify8()

template<typename CommType >
bool TMC9660Bootloader::readAndVerify8 ( uint8_t expected,
const char * config_name )
noexcept

Read back and verify an 8-bit value matches the expected value.

Performs a read operation and compares the returned value with the expected value. Useful for verification after configuration writes. Logs the result for debugging purposes.

Parameters
expectedThe expected 8-bit value to match
config_nameHuman-readable configuration name for logging
Returns
true if read successful and value matches

◆ sendCommand()

template<typename CommType >
bool TMC9660Bootloader::sendCommand ( uint8_t cmd,
uint32_t value,
uint32_t * reply = nullptr )
privatenoexcept

Send a bootloader command and optionally receive a reply.

This method dispatches the command to the appropriate protocol handler based on the communication interface type (SPI or UART). It provides a unified interface for all bootloader commands.

Parameters
cmdBootloader command code to send
value32-bit value to send with the command
replyOptional pointer to store the 32-bit reply value
Returns
true if command was sent successfully, false on error

◆ sendCommandSPI()

template<typename CommType >
bool TMC9660Bootloader::sendCommandSPI ( uint8_t cmd,
uint32_t value,
uint32_t * reply )
privatenoexcept

Send a bootloader command via SPI interface.

Implements the SPI bootloader protocol which requires two transactions:

  1. Send command (receive previous reply, ignored)
  2. Send NO_OP command (receive current command's reply)

This is standard SPI behavior where replies are delayed by one transaction.

Parameters
cmdBootloader command code to send
value32-bit value to send with the command
replyOptional pointer to store the 32-bit reply value
Returns
true if command was sent successfully, false on error
Here is the call graph for this function:

◆ sendCommandUART()

template<typename CommType >
bool TMC9660Bootloader::sendCommandUART ( uint8_t cmd,
uint32_t value,
uint32_t * reply )
privatenoexcept

Send a bootloader command via UART interface.

Implements the UART bootloader protocol which uses a single transaction: Send command and receive reply immediately. The UART protocol includes CRC-8 checksum verification for data integrity.

Parameters
cmdBootloader command code to send
value32-bit value to send with the command
replyOptional pointer to store the 32-bit reply value
Returns
true if command was sent successfully, false on error
Here is the call graph for this function:

◆ setAddress()

template<typename CommType >
bool TMC9660Bootloader::setAddress ( uint32_t addr)
noexcept

Set the address within the current memory bank.

Sets the memory address for subsequent read/write operations within the currently selected bank. Addresses are bank-relative (offset within bank).

Parameters
addrMemory address within current bank
Returns
true if command successful

Sets the address pointer for subsequent read/write operations within the currently selected memory bank. The address is bank-specific.

Parameters
addr32-bit address within the current bank
Returns
true if address was set successfully, false on error

◆ setBank() [1/2]

template<typename CommType >
bool tmc9660::TMC9660Bootloader< CommType >::setBank ( MemoryBank bank)
inlinenoexcept

Select the target register bank using enum (overloaded).

Convenience overload that accepts a MemoryBank enum instead of raw bank number. Automatically converts to the numeric value.

Parameters
bankMemory bank enum value
Returns
true if command successful
Here is the call graph for this function:

◆ setBank() [2/2]

template<typename CommType >
bool TMC9660Bootloader::setBank ( uint8_t bank)
noexcept

Select the target memory bank for subsequent operations.

Select the target memory bank for bootloader operations.

Sets which memory bank (RAM, OTP, SPI Flash, I2C EEPROM, or CONFIG) will be accessed by subsequent read/write operations. The bank must be selected before performing any memory access operations.

Parameters
bankMemory bank number (0-5, see MemoryBank enum)
Returns
true if command successful
Note
Common banks: 0=RAM, 1=OTP, 5=CONFIG

Sets the memory bank that subsequent read/write operations will target. Valid banks include RAM, OTP, SPI Flash, I2C EEPROM, and CONFIG.

Parameters
bankMemory bank number (0-5)
Returns
true if bank was set successfully, false on error
Here is the caller graph for this function:

◆ startMotorControl()

template<typename CommType >
bool TMC9660Bootloader::startMotorControl ( bootcfg::BootMode bootMode = bootcfg::BootMode::Parameter)
noexcept

Start the motor control system and exit bootloader mode.

This function writes START_MOTOR_CTRL=1 to the BOOT_CONFIG register, causing the bootloader to immediately exit and launch the motor control application based on the current BOOT_MODE setting.

⚠️ CRITICAL: After calling this function, the bootloader will no longer respond to commands. All bootloader configuration must be completed BEFORE calling this function.

Parameters
boot_modeMotor control mode to start (Register or Parameter mode)
Returns
true if command sent successfully
Note
The bootloader exits immediately after this command
Allow 100-150ms for motor control to fully initialize after calling
// Configure everything first
bootloader.setBank(5);
bootloader.setAddress(0x00020002);
// ... more configuration ...
// Finally, start motor control (bootloader exits here)
vTaskDelay(pdMS_TO_TICKS(150)); // Wait for motor control to start
// Now use motor control commands

This function writes START_MOTOR_CTRL=1 to the BOOT_CONFIG register, causing the bootloader to immediately exit and launch the motor control application based on the current BOOT_MODE setting.

Warning
CRITICAL: After calling this function, the bootloader will no longer respond to commands. All bootloader configuration must be completed BEFORE calling this function.
Parameters
bootModeMotor control mode to start (Register or Parameter mode)
Returns
true if command sent successfully, false on error
Note
The bootloader exits immediately after this command
Allow 100-150ms for motor control to fully initialize after calling
// Configure everything first
bootloader.setBank(5);
bootloader.setAddress(0x00020002);
// ... more configuration ...
// Finally, start motor control (bootloader exits here)
vTaskDelay(pdMS_TO_TICKS(150)); // Wait for motor control to start
// Now use motor control commands

◆ write16()

template<typename CommType >
bool TMC9660Bootloader::write16 ( uint16_t v)
noexcept

Write a 16-bit word to the previously selected address.

Writes a 16-bit value to the current bank and address. Little-endian byte order. Does not increment the address pointer.

Parameters
v16-bit value to write
Returns
true if write successful

Writes a 16-bit value to the current address in the selected memory bank. The address pointer is not incremented after the write operation.

Parameters
v16-bit value to write
Returns
true if write was successful, false on error

◆ write16Inc()

template<typename CommType >
bool TMC9660Bootloader::write16Inc ( uint16_t v)
noexcept

Write a 16-bit word and increment address by 2.

Writes a 16-bit value and automatically increments the address pointer by 2. Useful for writing sequential data arrays.

Parameters
v16-bit value to write
Returns
true if write successful

◆ write32()

template<typename CommType >
bool TMC9660Bootloader::write32 ( uint32_t v)
noexcept

Write a 32-bit word to the previously selected address.

Writes a 32-bit value to the current bank and address. Little-endian byte order. Does not increment the address pointer.

Parameters
v32-bit value to write
Returns
true if write successful

Writes a 32-bit value to the current address in the selected memory bank. The address pointer is not incremented after the write operation.

Parameters
v32-bit value to write
Returns
true if write was successful, false on error

◆ write32Inc()

template<typename CommType >
bool TMC9660Bootloader::write32Inc ( uint32_t v)
noexcept

Write a 32-bit word and increment address by 4.

Writes a 32-bit value and automatically increments the address pointer by 4. Commonly used for writing configuration registers and data arrays.

Parameters
v32-bit value to write
Returns
true if write successful

◆ write32IncMultiple()

template<typename CommType >
bool TMC9660Bootloader::write32IncMultiple ( const uint32_t * vals,
size_t count )
noexcept

Write multiple 32-bit words starting at the current address.

Writes multiple consecutive 32-bit words using WRITE_32_INC commands. The address pointer is incremented automatically for each word.

Parameters
valuesPointer to array of 32-bit values to write
countNumber of 32-bit words to write
Returns
true if all writes successful

Writes an array of 32-bit values using the WRITE_32_INC command, which automatically increments the address pointer after each write. This is useful for writing configuration blocks or data arrays.

Parameters
valsPointer to array of 32-bit values to write
countNumber of 32-bit values to write
Returns
true if all writes were successful, false on error

◆ write8()

template<typename CommType >
bool TMC9660Bootloader::write8 ( uint8_t v)
noexcept

Write a single byte to the previously selected address.

Writes an 8-bit value to the current bank and address. Does not increment the address pointer.

Parameters
v8-bit value to write
Returns
true if write successful

Writes an 8-bit value to the current address in the selected memory bank. The address pointer is not incremented after the write operation.

Parameters
v8-bit value to write
Returns
true if write was successful, false on error

◆ write8Inc()

template<typename CommType >
bool TMC9660Bootloader::write8Inc ( uint8_t v)
noexcept

Write a single byte and increment address by 1.

Writes an 8-bit value and automatically increments the address pointer. Useful for writing sequential data arrays.

Parameters
v8-bit value to write
Returns
true if write successful

Member Data Documentation

◆ comm_

◆ deviceAddr_

template<typename CommType >
uint8_t tmc9660::TMC9660Bootloader< CommType >::deviceAddr_
private

Device address for UART protocol.

◆ hostAddr_

template<typename CommType >
uint8_t tmc9660::TMC9660Bootloader< CommType >::hostAddr_
private

Host address for UART protocol.


The documentation for this class was generated from the following files: