Program to update the D7A modem's firmware.
Dependencies: modem_ref_helper DebouncedInterrupt
Diff: cup.h
- Revision:
- 0:82a60d86ab2e
- Child:
- 1:765933092750
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/cup.h Wed Oct 26 10:03:59 2016 +0000 @@ -0,0 +1,105 @@ +#include "mbed.h" +#include "d7a.h" +#include "bin.h" + +#define CUP_CFG_FID (126) +#define CUP_CODE_FID (127) + + +#define D7A_READ(_ret, _fid, _offset, _size, _root_key) do{\ + d7a_msg_t** _msg = d7a_read((_fid), (_offset), (_size), (_root_key));\ + ASSERT(_msg[0]->err >= D7A_ERR_NONE, "READ failed. err %d\r\n", _msg[0]->err);\ + ASSERT(_msg[0]->data, "READ failed. No data in response\r\n");\ + ASSERT(_msg[0]->data->offset == 0, "READ failed. Wrong data offset %d/%d\r\n", _msg[0]->data->offset, (_offset));\ + ASSERT(_msg[0]->data->length == (_size), "READ failed. Wrong data length %d/%d\r\n", _msg[0]->data->length, (_size));\ + memcpy((_ret), _msg[0]->data->buf, (_size));\ + d7a_free_msg(_msg);\ +} while (0) + +#define D7A_WRITE(_data, _fid, _offset, _size, _root_key) do{\ + d7a_msg_t** _msg = d7a_write((_fid), (_offset), (_size), (_data), (_root_key));\ + ASSERT(_msg[0]->err == D7A_ERR_NONE, "WRITE failed. err %d\r\n", _msg[0]->err);\ + d7a_free_msg(_msg);\ +} while (0) + +#define D7A_FLUSH(_fid, _root_key) do{\ + d7a_msg_t** _msg = d7a_flush((_fid), (_root_key));\ + ASSERT(_msg[0]->err >= D7A_ERR_NONE, "FLUSH failed. err %d\r\n", _msg[0]->err);\ + d7a_free_msg(_msg);\ +} while (0) + +//------------------------------------------------------------------ +// CUP Package files structure: +// | SIZE | ADDR | BINARY | PAD | CRC | Next Archive +// | 4B | 4B | XB | 0-3 B | 4B | ... +// | | | ... +// |<------------------CRC----------------------->| | ... +// |<-----------------------SIZE------------------------>| ... +// +// Archive must be word-aligned +// Archives can be concatenated +// ADDR is the destination address of the installed archive +// SIZE accounts for whole archive (including itself) +// Binary size must be multiple of word (i.e pad=4) +// CRC calculated on whole archive (obviously excluding itself) +// Values (size,addr) are stored little-endian + +#define CUP_SIZE_SIZE sizeof(uint32_t) +#define CUP_ADDR_SIZE sizeof(uint32_t) +#define CUP_CRC_SIZE sizeof(uint32_t) +#define CUP_WORD_SIZE (4) + +extern const uint8_t root_key[D7A_ROOT_KEY_SIZE]; + +//====================================================================== +// cup_cfg_t +//---------------------------------------------------------------------- +/// @brief This is the structure of the CUP Config FILE. +/// This file _MUST_ always be located a the same place (EEPROM +/// Origin) as BOOT/CUP access it in a hardcoded way. +/// !! Do NOT touch this except if you're a CUP Master !! +//====================================================================== +TYPEDEF_STRUCT_PACKED +{ + // The CUP Command + uint16_t cmd; + // Number of Archives to be CUP'ed + uint16_t arch_nb; + // This field has 2 meanings: + // - when read-out it gives start address of CUP-Code file + // - when written (for a CUP start) it gives the offset (in bytes) at + // which the first archive is stored in CUP-Code file + uint32_t src_offset; + // CRC32 of the arch_nb concatenated archives starting at offset + uint32_t signature; + // TODO: Deciphering key. For now CUP MAX size + uint32_t key; + // Debug / Uart config + uint32_t dbg_cfg; +} cup_cfg_t; + +class CUP_Archive +{ + private: + + const uint8_t* const data; + + public: + + const uint32_t data_size; + const uint32_t signature; + const uint32_t nb_archives; + const uint32_t word_size; + const uint8_t fw_id; + const uint8_t fw_major; + const uint8_t fw_minor; + const uint16_t fw_patch; + const uint32_t fw_hash; + const uint32_t hw_version; + + CUP_Archive(void); + + void start_update(uint32_t src_offset); +}; + + \ No newline at end of file