Protocol specification

Communication between mcbootflash and a connected bootloader is split up into discrete packets. The layout of a basic packet is as follows:

class mcbootflash.protocol.Packet(command: BootCommand, data_length: int = 0, unlock_sequence: int = 0, address: int = 0)[source]

Base class for communication packets to and from the bootloader.

Layout:

| uint8   | uint16      | uint32          | uint32   |
| command | data_length | unlock_sequence | address  |
Parameters
  • command (BootCommand) – Command code which specifies which command should be executed by the bootloader.

  • data_length (int) –

    Meaning depends on value of ‘command’-field:

    WRITE_FLASH: Number of bytes following the command packet.
    ERASE_FLASH: Number of flash pages to be erased.
    CALC_CHECKSUM: Number of bytes to checksum.
    

    For other commands this field is ignored.

  • unlock_sequence (uint32) – Key to unlock flash memory for writing. Write operations (WRITE_FLASH, ERASE_FLASH) will fail SILENTLY if this key is incorrect.

  • address (uint32) – Address at which to perform command.

  • FORMAT (ClassVar[str]) – Format string for struct which specifies types and layout of the data fields.

Note

No error is raised if the key is incorrect. A failed WRITE_FLASH operation can be detected by comparing checksums of the written bytes and the flash area they were written to. A failed ERASE_FLASH operation can be detected by issuing a SELF_VERIFY command. If the erase succeeded, SELF_VERIFY should return VERIFY_FAIL.

Every packet sent to or from the bootloader has at least these four fields.

The bootloader never sends anything without first receiving a packet from the host application. After receiving a command packet, the bootloader must respond with exactly one packet in return. The response packet’s command field must be the same as that of the received command packet.

Command packets

Packets sent from the host application to the bootloader are called command packets. They have the same data layout as the basic packet specified above, plus an optional data field following the address field. The following commands are supported:

class mcbootflash.protocol.BootCommand(value)[source]

The MCC 16-bit bootloader supports these commands.

READ_VERSION = 0
READ_FLASH = 1
WRITE_FLASH = 2
ERASE_FLASH = 3
CALC_CHECKSUM = 8
RESET_DEVICE = 9
SELF_VERIFY = 10
GET_MEMORY_ADDRESS_RANGE = 11

Response packets

Replies from the bootloader come in two variations; responses to READ_VERSION and responses to other commands. Responses to READ_VERSION have the following format:

class mcbootflash.protocol.VersionResponsePacket(command: BootCommand, data_length: int = 0, unlock_sequence: int = 0, address: int = 0, version: int = 0, max_packet_length: int = 0, device_id: int = 0, erase_size: int = 0, write_size: int = 0)[source]

Response to a READ_VERSION command.

Layout:

| [Packet] | uint16  | uint16            | uint16    | uint16    | ...
| [Packet] | version | max_packet_length | (ignored) | device_id | ...

... | uint16    | uint16     | uint16     | uint32    | uint32    | uint32    |
... | (ignored) | erase_size | write_size | (ignored) | (ignored) | (ignored) |
Parameters
  • version (uint16) – Bootloader version number.

  • max_packet_length (int16) – Maximum number of bytes which can be sent to the bootloader per packet. Includes the size of the packet itself plus associated data.

  • device_id (uint16) – A device-specific identifier.

  • erase_size (uint16) – Size of a flash erase page in bytes. When erasing flash, the size of the memory area which should be erased is given in number of erase pages.

  • write_size (uint16) – Size of a write block in bytes. When writing to flash, the data must align with a write block.

Responses to all other commands have the following basic layout:

class mcbootflash.protocol.ResponsePacket(command: BootCommand, data_length: int = 0, unlock_sequence: int = 0, address: int = 0, success: BootResponse = BootResponse.UNDEFINED)[source]

Base class for most packets received from the bootloader.

Layout:

| [Packet] | uint8   |
| [Packet] | success |

The exception is READ_VERSION, in response to which a VersionResponsePacket is received instead.

Parameters

success (BootResponse) – Success or failure status of the command this packet is sent in response to.

The success field has one of the following values:

class mcbootflash.protocol.BootResponse(value)[source]

Sent by the bootloader in response to a command.

UNDEFINED = 0
SUCCESS = 1
UNSUPPORTED_COMMAND = 255
BAD_ADDRESS = 254
BAD_LENGTH = 253
VERIFY_FAIL = 252

Some commands (GET_MEMORY_ADDRESS_RANGE and CALCULATE_CHECKSUM) send additional data following the success field:

class mcbootflash.protocol.MemoryRangePacket(command: BootCommand, data_length: int = 0, unlock_sequence: int = 0, address: int = 0, success: BootResponse = BootResponse.UNDEFINED, program_start: int = 0, program_end: int = 0)[source]

Response to GET_MEMORY_RANGE command.

Layout:

| [ResponsePacket] | uint32        | uint32      |
| [ResponsePacket] | program_start | program_end |
Parameters
  • program_start (int) – Low end of address space to which application firmware can be flashed.

  • program_end (int) – High end of address space to which application firmware can be flashed.

class mcbootflash.protocol.ChecksumPacket(command: BootCommand, data_length: int = 0, unlock_sequence: int = 0, address: int = 0, success: BootResponse = BootResponse.UNDEFINED, checksum: int = 0)[source]

Response to CALCULATE_CHECKSUM command.

Layout:

| [ResponsePacket] | uint16   |
| [ResponsePacket] | checksum |
Parameters

checksum (int) – Checksum of data_length bytes starting from address.

Program flowchart

Blue arrows/bubbles indicate normal program flow, red arrows/bubbles indicate errors.

_images/session.gif

Note

* If SELF_VERIFY returns SUCCESS immediately after an ERASE_FLASH command, the erase failed. Normal execution flow therefore requires a response of VERIFY_FAIL.