Index: firmware/App/BLCommon.h =================================================================== diff -u -rf2652e85c8676d0356fea2690cfd9cac716ca795 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/BLCommon.h (.../BLCommon.h) (revision f2652e85c8676d0356fea2690cfd9cac716ca795) +++ firmware/App/BLCommon.h (.../BLCommon.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * BLCommon.h - * - * Created on: Aug 1, 2024 - * Author: fw - */ #ifndef __BLCOMMON_H__ #define __BLCOMMON_H__ Index: firmware/App/Common.h =================================================================== diff -u -rb8160225a28a2ba4d6dff4d0433e55465c737a14 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Common.h (.../Common.h) (revision b8160225a28a2ba4d6dff4d0433e55465c737a14) +++ firmware/App/Common.h (.../Common.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,87 +1,96 @@ -/* - * Common.h - * - * Created on: Aug 5, 2024 - * Author: fw - */ #ifndef __COMMON_H__ #define __COMMON_H__ #include "BLCommon.h" -#define NUM_OF_FW_STACKS 3 -#define CAN_MESSAGE_PAYLOAD_SIZE 8 -#define FIRMWARE_START_ADDRESS 0x00010000 -#define FIRMWARE_CRC_TABLE_ADDRESS 0x10020 ///< The starting address of CRC table for firmware image. -#define SW_UPDATE_FLASH_BUFFER_SIZE 256 -#define MASK_OFF_MSB 0x00FF ///< Bits to mask off the most significant byte of a 2-byte word -#define MASK_OFF_LSB 0xFF00 ///< Bits to mask off the least significant byte of a 2-byte word -#define SHIFT_8_BITS_FOR_BYTE_SHIFT 8 ///< Number of bits to shift in order to shift a byte -#define MASK_OFF_NIBBLE_MSB 0x0F ///< Bits to mask off the most significant nibble of a byte +/** + * @defgroup CommonHeader CommonHeader + * @brief Provides commonly used definitions and macros. + * + * @addtogroup CommonHeader + * @{ + */ -#define NUM_OF_CMD_CAN_FRAMES 1 +// ********** public definitions ********** +#define NUM_OF_FW_STACKS 3 ///< Number of firmware stacks (TD, DD, RO). +#define CAN_MESSAGE_PAYLOAD_SIZE 8 ///< CAN message payload size in bytes. +#define FIRMWARE_START_ADDRESS 0x00010000 ///< Firmware start address. +#define FIRMWARE_CRC_TABLE_ADDRESS 0x10020 ///< The starting address of CRC table for firmware image. +#define SW_UPDATE_FLASH_BUFFER_SIZE 256 ///< Software update flash buffer bytes. +#define MASK_OFF_MSB 0x00FF ///< Bits to mask off the most significant byte of a 2-byte word +#define MASK_OFF_LSB 0xFF00 ///< Bits to mask off the least significant byte of a 2-byte word +#define SHIFT_8_BITS_FOR_BYTE_SHIFT 8 ///< Number of bits to shift in order to shift a byte +#define MASK_OFF_NIBBLE_MSB 0x0F ///< Bits to mask off the most significant nibble of a byte -#define GET_LSB_OF_WORD(w) ((U08)((w) & MASK_OFF_MSB)) ///< Macro returns the least signficant byte of a 2-byte word -#define GET_MSB_OF_WORD(w) ((U08)(((w) >> SHIFT_8_BITS_FOR_BYTE_SHIFT) & MASK_OFF_MSB)) ///< Macro returns the most signficant byte of a 2-byte word -#define MAKE_WORD_OF_BYTES(h, l) ((((U16)(h) << SHIFT_8_BITS_FOR_BYTE_SHIFT) & MASK_OFF_LSB) | ((U16)(l) & MASK_OFF_MSB)) ///< Macro merges two bytes into a 2-byte word -#define INC_WRAP(v, l, u) ((v) >= (u) ? (l) : ((v) + 1)) ///< Macro increments a value and wraps to a minimum when a maximum is reached +#define NUM_OF_CMD_CAN_FRAMES 1 ///< Number of command CAN frames. +#define GET_LSB_OF_WORD(w) ((U08)((w) & MASK_OFF_MSB)) ///< Macro returns the least signficant byte of a 2-byte word. +#define GET_MSB_OF_WORD(w) ((U08)(((w) >> SHIFT_8_BITS_FOR_BYTE_SHIFT) & MASK_OFF_MSB)) ///< Macro returns the most signficant byte of a 2-byte word. +#define MAKE_WORD_OF_BYTES(h, l) ((((U16)(h) << SHIFT_8_BITS_FOR_BYTE_SHIFT) & MASK_OFF_LSB) \ + | ((U16)(l) & MASK_OFF_MSB)) ///< Macro merges two bytes into a 2-byte word. +#define INC_WRAP(v, l, u) ((v) >= (u) ? (l) : ((v) + 1)) ///< Macro increments a value and wraps to a minimum when a maximum is reached. + // **** Types **** -typedef float F32; ///< 32-bit floating point type -typedef double F64; ///< 64-bit floating point type -typedef long long S64; ///< 64-bit signed integer type -typedef unsigned int U32; ///< 32-bit unsigned integer type -typedef int S32; ///< 32-bit signed integer type -typedef unsigned short U16; ///< 16-bit unsigned integer type -typedef short S16; ///< 16-bit signed integer type -typedef unsigned char U08; ///< 8-bit unsigned integer type -typedef unsigned int BOOL; ///< 32-bit boolean type -typedef unsigned char BYTE; ///< 8-bit byte type +typedef float F32; ///< 32-bit floating point type. +typedef double F64; ///< 64-bit floating point type. +typedef long long S64; ///< 64-bit signed integer type. +typedef unsigned int U32; ///< 32-bit unsigned integer type. +typedef int S32; ///< 32-bit signed integer type. +typedef unsigned short U16; ///< 16-bit unsigned integer type. +typedef short S16; ///< 16-bit signed integer type. +typedef unsigned char U08; ///< 8-bit unsigned integer type. +typedef unsigned int BOOL; ///< 32-bit boolean type. +typedef unsigned char BYTE; ///< 8-bit byte type. +/// Bootloader operations modes enumeration typedef enum BL_Op_Modes { - MODE_STAND = 0, - MODE_UPDATE, - NUM_OF_MODES + MODE_STAND = 0, ///< Mode standby. + MODE_UPDATE, ///< Mode update. + NUM_OF_MODES ///< Number of modes. } BL_OP_MODE_T; +/// Mode standby states enumeration typedef enum SW_Mode_Standby_States { - STANDBY_CHECK_FOR_UPDATE_STATE = 0, - STANDBY_CHECK_FW_AND_FPGA_IMAGES_STATE, - STANDBY_IDLE_STATE, - NUM_OF_MODE_STANDBY_STATES + STANDBY_CHECK_FOR_UPDATE_STATE = 0, ///< Standby check for update state. + STANDBY_CHECK_FW_AND_FPGA_IMAGES_STATE, ///< Standby check firmware and FPGA images state. + STANDBY_IDLE_STATE, ///< Standby idle state. + NUM_OF_MODE_STANDBY_STATES ///< Number of standby states. } MODE_STANDBY_STATE_T; +/// Mode update states enumeration typedef enum SW_Mode_Update_States { - SW_UPDATE_UPDATE_STATE = 0, - SW_UPDATE_VERIFY_STATE, - SW_UPDATE_ABORT_STATE, - NUM_OF_MODE_SW_UPDATE_STATES + SW_UPDATE_UPDATE_STATE = 0, ///< Update update state. + SW_UPDATE_VERIFY_STATE, ///< Update verify state. + SW_UPDATE_ABORT_STATE, ///< Update abort state. + NUM_OF_MODE_SW_UPDATE_STATES ///< Number of update states. } MODE_SW_UPDATE_STATE_T; +/// Software update destinations enumeration typedef enum SW_Update_Destinations { - UPDATE_FIRMWARE = 0, - UPDATE_FPGA, - NUM_OF_UPDATE_DESTS + UPDATE_FIRMWARE = 0, ///< Update firmware. + UPDATE_FPGA, ///< Update FPGA. + NUM_OF_UPDATE_DESTS ///< Number of update destinations. } SW_UPDATE_DESINTATION_T; +/// Software update CAN mailboxes enumeration typedef enum SW_Update_CAN_Mail_Boxes { - SW_UPDATE_NOT_USED = 0, // 0 - SW_UPDATE_COMMAD, // 0x601 - SW_UPDATE_TD_UPDATE, // 0x602 - SW_UPDATE_DD_UPDATE, // 0x603 - SW_UPDATE_RO_UPDATE, // 0x604 - PLACE_HOLDER_TO_REMOVE_CAN, // 0x605 - SW_UPDATE_RESP, // 0x606 + SW_UPDATE_NOT_USED = 0, // 0 ///< Software update not used mailbox. + SW_UPDATE_COMMAD, // 0x601 ///< Software update command mailbox. + SW_UPDATE_TD_UPDATE, // 0x602 ///< Software update TD update mailbox. + SW_UPDATE_DD_UPDATE, // 0x603 ///< Software update DD update mailbox. + SW_UPDATE_RO_UPDATE, // 0x604 ///< Software update RO update mailbox. + PLACE_HOLDER_TO_REMOVE_CAN, // 0x605 // TODO remove + SW_UPDATE_RESP, // 0x606 ///< Software update respond mailbox. SW_TEST, // 0x607 // TODO remove - NUM_OF_SW_UPDATE_MBOXES, + NUM_OF_SW_UPDATE_MBOXES, ///< Number of software update mailboxes. } SW_UPDATE_CAN_MAIL_BOX_T; /*! @@ -108,31 +117,36 @@ If streaming encounters problems we use a command with Resync so that the FW will dump it's indexes and be ready for new data. */ +/// Software update commands enumeration typedef enum SW_Update_Commands { - UPDATE_CMD_START = 0, - UPDATE_CMD_ABORT, + UPDATE_CMD_START = 0, ///< Update command start. + UPDATE_CMD_ABORT, ///< Update command abort. UPDATE_CMD_RUNAPP, // TODO is this needed? - UPDATE_CMD_VERIFY, + UPDATE_CMD_VERIFY, ///< Update command verify. UPDATE_CMD_VERSION, // TODO is this needed? - UPDATE_CMD_VERIFIED, - UPDATE_CMD_RESYNC, - UPDATE_CMD_IDLE, - NUM_OF_UPDATE_CMDS + UPDATE_CMD_VERIFIED, // TODO is this needed? + UPDATE_CMD_RESYNC, ///< Update command resync. + UPDATE_CMD_IDLE, ///< Update command idle. + NUM_OF_UPDATE_CMDS ///< Number of update commands. } SW_UPDATE_CMD_T; +/// Acknowledge or not acknowledge enumeration typedef enum Ack_Nack { - NACK = 0, - ACK, - NUM_OF_ACK_NACK + NACK = 0, ///< Nack. + ACK, ///< Ack. + NUM_OF_ACK_NACK ///< Number of ack/nack states. } ACK_NACK_STATUS_T; +/// Software update corresponding stack mailbox static const SW_UPDATE_CAN_MAIL_BOX_T RECEIVE_MSG_ID[ NUM_OF_FW_STACKS ] = { - SW_UPDATE_TD_UPDATE, - SW_UPDATE_DD_UPDATE, - SW_UPDATE_RO_UPDATE + SW_UPDATE_TD_UPDATE, ///< Software update TD. + SW_UPDATE_DD_UPDATE, ///< Software update DD. + SW_UPDATE_RO_UPDATE ///< Software update RO. }; +/**@}*/ + #endif Index: firmware/App/Modes/ModeStandby.c =================================================================== diff -u -rfc99f47309c9d96f73a2d4696b42d6d302f334a7 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/ModeStandby.c (.../ModeStandby.c) (revision fc99f47309c9d96f73a2d4696b42d6d302f334a7) +++ firmware/App/Modes/ModeStandby.c (.../ModeStandby.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * ModeStandby.c - * - * Created on: Aug 7, 2024 - * Author: fw - */ #include // For memcpy and memset @@ -18,32 +12,62 @@ #include "Timers.h" #include "Utilities.h" +/** + * @addtogroup BLStandbyMode + * @{ + */ -#define WAIT_FOR_UPDATE_FROM_UI_MS 1000 +// ********** private definitions ********** -static MODE_STANDBY_STATE_T standbyCurrentState; -static U32 waitForUpdateMsgStartTimeMS; +#define WAIT_FOR_UPDATE_FROM_UI_MS 1000 ///< Wait for update timeout in milliseconds. +// ********** private data ********** + +static MODE_STANDBY_STATE_T standbyCurrentState; ///< Standby current state. +static U32 waitForUpdateMsgStartTimeMS; ///< Wait for update start time in milliseconds. + +// ********** private function prototypes ********** + static MODE_STANDBY_STATE_T handleStandbyModeCheckForUpdateState( void ); static MODE_STANDBY_STATE_T handleStandbyModeCheckFWAndFPGAImages( void ); static MODE_STANDBY_STATE_T handleStandbyModeIdleState( void ); static void jumpToApplication( void ); - +/*********************************************************************//** + * @brief + * The initStandbyMode function initializes the standby mode. + * @details \b Inputs: none + * @details \b Outputs: standbyCurrentState, waitForUpdateMsgStartTimeMS + * @return none + *************************************************************************/ void initStandbyMode( void ) { standbyCurrentState = STANDBY_CHECK_FOR_UPDATE_STATE; waitForUpdateMsgStartTimeMS = getMSTimerCount(); } +/*********************************************************************//** + * @brief + * The transitionToStandbyMode function prepares for transition to Standby Mode. + * @details \b Inputs: none + * @details \b Outputs: Standby Mode unit re-initialized + * @return none + *************************************************************************/ U32 transitionToStandbyMode( void ) { initStandbyMode(); return 0; } +/*********************************************************************//** + * @brief + * The execStandbyMode function executes the Standby Mode state machine. + * @details \b Inputs: standbyCurrentState + * @details \b Outputs: standbyCurrentState + * @return current state (sub-mode) + *************************************************************************/ U32 execStandbyMode( void ) { // If the bootloader is the standby mode and and update request is received at any time, request a transition to update mode @@ -76,7 +100,17 @@ return standbyCurrentState; } - +/*********************************************************************//** + * @brief + * The handleStandbyModeCheckForUpdateState function handles the standby + * check for update state. + * This state waits for a software update command (i.e. verify or abort) and + * then transitions accordingly. Also, if the wait for update has timed out + * it transitions to the verifying firmware and FPGA images. + * @details \b Inputs: waitForUpdateMsgStartTimeMS + * @details \b Outputs: none + * @return next state of the standby mode state machine + *************************************************************************/ static MODE_STANDBY_STATE_T handleStandbyModeCheckForUpdateState( void ) { MODE_STANDBY_STATE_T state = STANDBY_CHECK_FOR_UPDATE_STATE; @@ -104,6 +138,16 @@ return state; } +/*********************************************************************//** + * @brief + * The handleStandbyModeCheckFWAndFPGAImages function handles the standby + * check firmware and FPGA images state. + * This state checks the integrity of the firmware as well as the FPGA header + * to make sure the images are valid. + * @details \b Inputs: waitForUpdateMsgStartTimeMS + * @details \b Outputs: none + * @return next state of the standby mode state machine + *************************************************************************/ static MODE_STANDBY_STATE_T handleStandbyModeCheckFWAndFPGAImages( void ) { MODE_STANDBY_STATE_T state = STANDBY_CHECK_FW_AND_FPGA_IMAGES_STATE; @@ -139,6 +183,14 @@ return state; } +/*********************************************************************//** + * @brief + * The handleStandbyModeIdleState function handles the standby idle state. + * This state waits until a new update request arrives. + * @details \b Inputs: none + * @details \b Outputs: none + * @return next state of the standby mode state machine + *************************************************************************/ static MODE_STANDBY_STATE_T handleStandbyModeIdleState( void ) { MODE_STANDBY_STATE_T state = STANDBY_IDLE_STATE; @@ -149,6 +201,15 @@ return state; } +/*********************************************************************//** + * @brief + * The jumpToApplication function handles the jump to application commands. + * This function, disables interrupts that were used in the bootloader and + * then it jumps to the fimrware start address. + * @details \b Inputs: none + * @details \b Outputs: none + * @return none + *************************************************************************/ static void jumpToApplication( void ) { U32 jumpAddress = (U32)FIRMWARE_START_ADDRESS; @@ -167,3 +228,5 @@ while(1); } +/**@}*/ + Index: firmware/App/Modes/ModeStandby.h =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/ModeStandby.h (.../ModeStandby.h) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Modes/ModeStandby.h (.../ModeStandby.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,19 +1,28 @@ -/* - * ModeStandby.h - * - * Created on: Aug 7, 2024 - * Author: fw - */ #ifndef __MODESTANDBY_H__ #define __MODESTANDBY_H__ #include "BLCommon.h" +/** + * @defgroup BLStandbyMode BLStandbyMode + * @brief Standby mode unit. Manages the Standby mode functions via a state + * machine. + * + * @addtogroup BLStandbyMode + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initStandbyMode( void ); U32 transitionToStandbyMode( void ); U32 execStandbyMode( void ); +/**@}*/ + #endif Index: firmware/App/Modes/ModeUpdate.c =================================================================== diff -u -rfc99f47309c9d96f73a2d4696b42d6d302f334a7 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/ModeUpdate.c (.../ModeUpdate.c) (revision fc99f47309c9d96f73a2d4696b42d6d302f334a7) +++ firmware/App/Modes/ModeUpdate.c (.../ModeUpdate.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * ModeUpdate.c - * - * Created on: Jul 31, 2024 - * Author: fw - */ #include "CommBuffers.h" #include "Download.h" @@ -12,17 +6,42 @@ #include "NVDataMgmt.h" #include "OperationModes.h" +/** + * @addtogroup UpdateMode + * @{ + */ + +// ********** private definitions ********** + +// ********** private data ********** + static MODE_SW_UPDATE_STATE_T updateCurrentState; +// ********** private function prototypes ********** + static MODE_SW_UPDATE_STATE_T handleUpdateModeUpdateState( void ); static MODE_SW_UPDATE_STATE_T handleUpdateModeVerifyState( void ); static MODE_SW_UPDATE_STATE_T handleUpdateModeAbortState( void ); +/*********************************************************************//** + * @brief + * The initUpdateMode function initializes the Update Mode Unit. + * @details \b Inputs: none + * @details \b Outputs: updateCurrentState + * @return none + *************************************************************************/ void initUpdateMode( void ) { updateCurrentState = SW_UPDATE_UPDATE_STATE; } +/*********************************************************************//** + * @brief + * The transitionToUpdateMode function prepares for transition to Update Mode. + * @details \b Inputs: none + * @details \b Outputs: Standby Mode unit re-initialized + * @return none + *************************************************************************/ U32 transitionToUpdateMode( void ) { initUpdateMode(); @@ -35,6 +54,13 @@ return 0; } +/*********************************************************************//** + * @brief + * The execUpdateMode function executes the Update Mode state machine. + * @details \b Inputs: updateCurrentState + * @details \b Outputs: updateCurrentState + * @return current state (sub-mode) + *************************************************************************/ U32 execUpdateMode( void ) { switch( updateCurrentState ) @@ -59,7 +85,14 @@ return 0; } - +/*********************************************************************//** + * @brief + * The handleUpdateModeUpdateState function handles the update mode update state. + * This state checks for the SW update command to transition to the proper state. + * @details \b Inputs: none + * @details \b Outputs: none + * @return next state of the update mode state machine + *************************************************************************/ static MODE_SW_UPDATE_STATE_T handleUpdateModeUpdateState( void ) { MODE_SW_UPDATE_STATE_T state = SW_UPDATE_UPDATE_STATE; @@ -82,6 +115,17 @@ return state; } +/*********************************************************************//** + * @brief + * The handleUpdateModeVerifyState function handles the update mode verify state. + * This state checks for the destination of the current update which can be + * either firmware or FPGA. If the update destination was FPGA it makes sure + * the FPGA update has been completed and then transitions to standby mode. + * If the update destination was firmware, it transitions to standby mode. + * @details \b Inputs: none + * @details \b Outputs: none + * @return next state of the update mode state machine + *************************************************************************/ static MODE_SW_UPDATE_STATE_T handleUpdateModeVerifyState( void ) { MODE_SW_UPDATE_STATE_T state = SW_UPDATE_VERIFY_STATE; @@ -107,6 +151,14 @@ return state; } +/*********************************************************************//** + * @brief + * The handleUpdateModeAbortState function handles the update mode abort state. + * This state transitions to standby mode upon requesting to abort the update. + * @details \b Inputs: none + * @details \b Outputs: none + * @return next state of the update mode state machine + *************************************************************************/ static MODE_SW_UPDATE_STATE_T handleUpdateModeAbortState( void ) { MODE_SW_UPDATE_STATE_T state = SW_UPDATE_ABORT_STATE; @@ -116,9 +168,4 @@ return state; } - - - - - - +/**@}*/ Index: firmware/App/Modes/ModeUpdate.h =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/ModeUpdate.h (.../ModeUpdate.h) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Modes/ModeUpdate.h (.../ModeUpdate.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,19 +1,28 @@ -/* - * ModeUpdate.h - * - * Created on: Jul 31, 2024 - * Author: fw - */ #ifndef _MODEUPDATE_H__ #define _MODEUPDATE_H__ #include "BLCommon.h" +/** + * @defgroup UpdateMode UpdateMode + * @brief Update mode unit. Manages the Update mode functions via a state + * machine. + * + * @addtogroup UpdateMode + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initUpdateMode( void ); U32 transitionToUpdateMode( void ); U32 execUpdateMode( void ); +/**@}*/ + #endif Index: firmware/App/Modes/OperationModes.c =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/OperationModes.c (.../OperationModes.c) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Modes/OperationModes.c (.../OperationModes.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,21 +1,32 @@ -/* - * OperationModes.c - * - * Created on: Aug 9, 2024 - * Author: fw - */ #include "ModeStandby.h" #include "ModeUpdate.h" #include "OperationModes.h" +/** + * @addtogroup BLOperationModes + * @{ + */ +// ********** private definitions ********** + +// ********** private data ********** + static BL_OP_MODE_T currentMode; ///< The currently active state of the active mode. -static BL_OP_MODE_T previousMode; -static BL_OP_MODE_T requestedMode; +static BL_OP_MODE_T previousMode; ///< Previous state of the operations mode. +static BL_OP_MODE_T requestedMode; ///< Request a new mode. +// ********** private function prototypes ********** + static void transitionToNewOperationMode( BL_OP_MODE_T newMode ); +/*********************************************************************//** + * @brief + * The initOperationModes function initializes the Operation Modes unit. + * @details \b Inputs: none + * @details \b Outputs: Operation Modes unit initialized. + * @return none + *************************************************************************/ void initOperationModes( void ) { currentMode = MODE_STAND; @@ -26,6 +37,13 @@ initUpdateMode(); } +/*********************************************************************//** + * @brief + * The execOperationModes function executes the Operation Modes state machine. + * @details \b Inputs: previousMode, currentMode, requestedMode + * @details \b Outputs: previousMode, currentMode, requestedMode + * @return none + *************************************************************************/ void execOperationModes( void ) { if ( requestedMode != currentMode ) @@ -52,6 +70,16 @@ } } +/*********************************************************************//** + * @brief + * The requestNewOperationMode function requests transition to a new + * operation mode. The request will be arbitrated when the state machine + * is next executed. + * @details \b Inputs: none + * @details \b Outputs: requestedMode + * @param new mode request + * @return none + *************************************************************************/ void requestNewOperationMode( BL_OP_MODE_T newMode ) { if ( newMode < NUM_OF_MODES ) @@ -60,7 +88,15 @@ } } - +/*********************************************************************//** + * @brief + * The transitionToNewOperationMode function calls the transition to function + * for a new operation mode that we are transitioning to. + * @details \b Inputs: none + * @details \b Outputs: transition function called for new mode + * @param new mode that is transitioning to. + * @return none + *************************************************************************/ static void transitionToNewOperationMode( BL_OP_MODE_T newMode ) { switch ( newMode ) @@ -79,11 +115,4 @@ } } - - - - - - - - +/**@}*/ Index: firmware/App/Modes/OperationModes.h =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Modes/OperationModes.h (.../OperationModes.h) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Modes/OperationModes.h (.../OperationModes.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,19 +1,25 @@ -/* - * OperationModes.h - * - * Created on: Aug 9, 2024 - * Author: fw - */ #ifndef __OPERATIONMODES_H__ #define __OPERATIONMODES_H__ #include "BLCommon.h" +/** + * @defgroup BLOperationModes BLOperationModes + * @brief Operation Modes unit. + * + * @addtogroup BLOperationModes + * @{ + */ + +// ********** public definitions ********** + void initOperationModes( void ); void execOperationModes( void ); void requestNewOperationMode( BL_OP_MODE_T newMode ); +/**@}*/ + #endif Index: firmware/App/Services/Comm.c =================================================================== diff -u -rba60692a9ecaf59cb5cb8490f4276917f43bcd01 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Comm.c (.../Comm.c) (revision ba60692a9ecaf59cb5cb8490f4276917f43bcd01) +++ firmware/App/Services/Comm.c (.../Comm.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,25 +1,52 @@ -/* - * Comm.c - * - * Created on: Aug 19, 2024 - * Author: fw - */ #include "sci.h" #include "sys_dma.h" #include "Comm.h" +/** + * @addtogroup CommInterrupts + * @{ + */ + +// ********** private definitions ********** + +// ********** private data ********** + +/*********************************************************************//** + * @brief + * The setSCI2DMAReceiveInterrupt function enables DMA receive interrupts + * for the SCI2 peripheral. + * @details Inputs: none + * @details Outputs: DMA receive interrupt is enabled. + * @return none + *************************************************************************/ void setSCI2DMAReceiveInterrupt( void ) { scilinREG->SETINT = SCI_DMA_RECEIVE_INT; } +/*********************************************************************//** + * @brief + * The setSCI2DMATransmitInterrupt function enables DMA transmit interrupts + * for the SCI2 peripheral. + * @details Inputs: none + * @details Outputs: DMA transmit interrupt is enabled. + * @return none + *************************************************************************/ void setSCI2DMATransmitInterrupt( void ) { scilinREG->SETINT = SCI_DMA_TRANSMIT_INT; } +/*********************************************************************//** + * @brief + * The clearSCI2DMAReceiveInterrupt function disables DMA receive interrupts + * for the SCI2 peripheral. + * @details Inputs: none + * @details Outputs: DMA receive interrupt is disabled. + * @return none + *************************************************************************/ void clearSCI2DMAReceiveInterrupt( void ) { scilinREG->CLEARINT = SCI_DMA_RECEIVE_INT; Index: firmware/App/Services/Comm.h =================================================================== diff -u -rba60692a9ecaf59cb5cb8490f4276917f43bcd01 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Comm.h (.../Comm.h) (revision ba60692a9ecaf59cb5cb8490f4276917f43bcd01) +++ firmware/App/Services/Comm.h (.../Comm.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,20 @@ -/* - * Comm.h - * - * Created on: Aug 19, 2024 - * Author: fw - */ #ifndef __COMM_H__ #define __COMM_H__ #include "BLCommon.h" +/** + * @defgroup CommInterrupts CommInterrupts + * @brief The communication unit provides low level comm signal, + * status, and some interrupt handling functions. + * + * @addtogroup CommInterrupts + * @{ + */ + +// ********** public definitions ********** + #define SCI_DMA_TRANSMIT_INT 0x00010000 ///< Bit mask for setting/clearing serial DMA transmit interrupts. #define SCI_DMA_RECEIVE_INT 0x00060000 ///< Bit mask for setting/clearing serial DMA receive interrupts. @@ -18,4 +23,6 @@ void clearSCI2DMAReceiveInterrupt( void ); void clearSCI2DMATransmitInterrupt( void ); +/**@}*/ + #endif Index: firmware/App/Services/CommBuffers.c =================================================================== diff -u -re8511af1e4e9d91cfd3378471869fb0246110870 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/CommBuffers.c (.../CommBuffers.c) (revision e8511af1e4e9d91cfd3378471869fb0246110870) +++ firmware/App/Services/CommBuffers.c (.../CommBuffers.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,27 +1,38 @@ -/* - * CommBuffers.c - * - * Created on: Aug 2, 2024 - * Author: fw - */ #include // For memcpy #include "CommBuffers.h" #include "Utilities.h" -#define MAX_NUM_OF_CAN_BYTES ( SW_UPDATE_FLASH_BUFFER_SIZE + CAN_MESSAGE_PAYLOAD_SIZE ) +/** + * @addtogroup CommBuffers + * @{ + */ +// ********** private definitions ********** + +#define MAX_NUM_OF_CAN_BYTES ( SW_UPDATE_FLASH_BUFFER_SIZE + CAN_MESSAGE_PAYLOAD_SIZE ) ///< Maximum number of CAN bytes. + +// ********** private data ********** + +/// Software update buffer structure typedef struct { - U32 SWUpdateFrameCount; - U08 SWUpdateBuffer[ MAX_NUM_OF_CAN_BYTES ]; + U32 SWUpdateFrameCount; ///< Software update frame count. + U08 SWUpdateBuffer[ MAX_NUM_OF_CAN_BYTES ]; ///< Software update buffer. } SW_UPDATE_BUFFER_T; +static SW_UPDATE_BUFFER_T SWUpdateBuffer[ NUM_OF_SW_UPDATE_MBOXES ]; ///< Software update buffer array. -static SW_UPDATE_BUFFER_T SWUpdateBuffer[ NUM_OF_SW_UPDATE_MBOXES ]; +// ********** private function prototypes ******** - +/*********************************************************************//** + * @brief + * The initCommBuffers function initializes the CommBuffers unit. + * @details Inputs: none + * @details Outputs: CommBuffers unit initialized. + * @return none + *************************************************************************/ void initCommBuffers( void ) { SW_UPDATE_CAN_MAIL_BOX_T mailBox; @@ -32,6 +43,20 @@ } } +/*********************************************************************//** + * @brief + * The addToCommBuffer function adds data of specified length to a given + * communication buffer. + * @note This function will add to the active side of the double buffer. + * @note This function is thread safe. IRQ interrupts are disabled during + * buffer operations. + * @details Inputs: SWUpdateBuffer[] + * @details Outputs: SWUpdateBuffer[] + * @param mailbox ID of buffer to add data to + * @param data Pointer to byte array containing data to add to buffer + * @param len Length of data (in bytes) + * @return TRUE if data added to buffer successfully, FALSE if not + *************************************************************************/ BOOL addToCommBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox, U08* data, U32 len ) { BOOL status = FALSE; @@ -41,11 +66,15 @@ _disable_IRQ(); U32 currentFrameCount = SWUpdateBuffer[ mailBox ].SWUpdateFrameCount; + // Check if the number of bytes is less than the allowed bytes in the mailbox buffer. if ( ( currentFrameCount * CAN_MESSAGE_PAYLOAD_SIZE ) <= MAX_NUM_OF_CAN_BYTES ) { U32 currentBufferIndex = currentFrameCount * len; + // Copy the received can frame into the buffer memcpy( SWUpdateBuffer[ mailBox ].SWUpdateBuffer + currentBufferIndex, data, len ); + + // Increment the current frame count SWUpdateBuffer[ mailBox ].SWUpdateFrameCount += 1; status = TRUE; } @@ -55,6 +84,22 @@ return status; } +/*********************************************************************//** + * @brief + * The getFromCommBuffer function fills a given byte array with a specified + * number of bytes from a given buffer and returns the number of bytes + * retrieved from the buffer. + * @note This function will draw from the inactive side of the double buffer + * and, if needed, switch double buffers to draw the rest of the requested data. + * @note This function is thread safe. IRQ interrupts are disabled during buffer + * operations. + * @details Inputs: SWUpdateBuffer[] + * @details Outputs: none + * @param mailbox ID of buffer to retrieve data from + * @param data Pointer to byte array to populate with buffer data + * @param len Number of bytes to retrieve from buffer into given byte array. + * @return the number of bytes retrieved. + *************************************************************************/ BOOL getCommBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox, U08* data, U32 len ) { BOOL status = FALSE; @@ -70,6 +115,16 @@ return status; } +/*********************************************************************//** + * @brief + * The getNumberOfBytesInBuffer function determines how many bytes + * are currently contained in a given comm buffer. Both sides of the + * double buffers are considered for this. + * @details Inputs: SWUpdateBuffer[] + * @details Outputs: none + * @param mailbox ID of buffer to get byte count for + * @return the number of bytes currently in the given comm buffer. + *************************************************************************/ S32 getNumberOfBytesInBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) { S32 bytes = -1; @@ -82,6 +137,16 @@ return bytes; } +/*********************************************************************//** + * @brief + * The clearBuffer function clears (empties) a given buffer. + * @note This function is thread safe. IRQ interrupts are disabled while + * buffers are being cleared. + * @details Inputs: none + * @details Outputs: given buffer is cleared. + * @param buffer ID of the buffer to clear + * @return none + *************************************************************************/ void clearCommBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) { _disable_IRQ(); @@ -92,8 +157,7 @@ _enable_IRQ(); } - // ********** private functions ********** +/**@}*/ - Index: firmware/App/Services/CommBuffers.h =================================================================== diff -u -r893caf9f58a08a2bd31068806e09603041d64add -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/CommBuffers.h (.../CommBuffers.h) (revision 893caf9f58a08a2bd31068806e09603041d64add) +++ firmware/App/Services/CommBuffers.h (.../CommBuffers.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,23 @@ -/* - * CommBuffers.h - * - * Created on: Aug 2, 2024 - * Author: fw - */ #ifndef __COMMBUFFERS_H__ #define __COMMBUFFERS_H__ #include "BLCommon.h" +/** + * @defgroup CommBuffers CommBuffers + * @brief The communication buffers unit provides buffering services for + * incoming and outgoing CAN data. A separate buffer is provided for each + * CAN ID (channel) so that frame order is maintained for a given channel. + * + * @addtogroup CommBuffers + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initCommBuffers( void ); BOOL addToCommBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox, U08* data, U32 len ); @@ -20,4 +28,6 @@ void clearCommBuffer( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); +/**@}*/ + #endif Index: firmware/App/Services/CopyFlashAPI2RAM.asm =================================================================== diff -u -rda12d1065b9bc93d30500255d8b986f00d1bdd69 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/CopyFlashAPI2RAM.asm (.../CopyFlashAPI2RAM.asm) (revision da12d1065b9bc93d30500255d8b986f00d1bdd69) +++ firmware/App/Services/CopyFlashAPI2RAM.asm (.../CopyFlashAPI2RAM.asm) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -2,6 +2,7 @@ ; ; Copy the Flash API from flash to RAM. ; +;------------------------------------------------------------------------------- .def _copyAPI2RAM_ .asmfunc Index: firmware/App/Services/Download.c =================================================================== diff -u -rb8160225a28a2ba4d6dff4d0433e55465c737a14 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Download.c (.../Download.c) (revision b8160225a28a2ba4d6dff4d0433e55465c737a14) +++ firmware/App/Services/Download.c (.../Download.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * Download.c - * - * Created on: Aug 21, 2024 - * Author: fw - */ #include "can.h" // TODO remove for testing only @@ -16,50 +10,71 @@ #include "SystemComm.h" #include "Utilities.h" -#define SW_UPDATE_FINAL_MSG_INDEX 0xFFFF -#define SHIFT_BITS_TO_GET_TARGET 4 +/** + * @addtogroup Download + * @{ + */ -static const U32 NUM_OF_CAN_BYTES_FOR_UPDATE = SW_UPDATE_FLASH_BUFFER_SIZE + CAN_MESSAGE_PAYLOAD_SIZE; +// ********** private definitions ********** +#define SW_UPDATE_FINAL_MSG_INDEX 0xFFFF ///< Software update final message index. +#define SHIFT_BITS_TO_GET_TARGET 4 ///< Shift bits by 4 to get the update target. + +// ********** private data ********** + +static const U32 NUM_OF_CAN_BYTES_FOR_UPDATE = SW_UPDATE_FLASH_BUFFER_SIZE + CAN_MESSAGE_PAYLOAD_SIZE; ///< Number of CAN bytes for update. + +/// Software update response status structure typedef struct { - U08 msgID; - U08 msgAckNackStatus; - U16 cyberRandom; - U32 msgCRC; + U08 msgID; ///< Message ID. + U08 msgAckNackStatus; ///< Message ack or nack status. + U16 cyberRandom; ///< Message cyber random. + U32 msgCRC; ///< Message CRC. } SW_UPDATE_RESP_STATUS_T; +/// Software update command status structure typedef struct { - U08 msgID; - U08 updateCmd; - U16 cyberRandom; - U32 msgCRC; + U08 msgID; ///< Message ID. + U08 updateCmd; ///< Update command. + U16 cyberRandom; ///< Cyber random. + U32 msgCRC; ///< Message CRC. } SW_UPDATE_CMD_STATUS_T; +/// Software update receive update status structure typedef struct { - U08 msgID; - U08 updateDest; - U16 updatePayloadLen; - U32 msgCRC; - U08 SWUpdateBuffer[ SW_UPDATE_FLASH_BUFFER_SIZE ]; + U08 msgID; ///< Message ID. + U08 updateDest; ///< Update destination (FW, FPGA). + U16 updatePayloadLen; ///< Update payload length in bytes. + U32 msgCRC; ///< Message CRC. + U08 SWUpdateBuffer[ SW_UPDATE_FLASH_BUFFER_SIZE ]; ///< Software update buffer. } SW_UPDATE_RCV_STATUS_T; -static SW_UPDATE_RCV_STATUS_T SWUpdateRCVStatus; -static SW_UPDATE_CMD_T SWUpdateCommandState; -static SW_UPDATE_CAN_MAIL_BOX_T thisStackMailBox; -static U32 sizeToWrite; +static SW_UPDATE_RCV_STATUS_T SWUpdateRCVStatus; ///< Software update receive status. +static SW_UPDATE_CMD_T SWUpdateCommandState; ///< Software update command state. +static SW_UPDATE_CAN_MAIL_BOX_T thisStackMailBox; ///< The mailbox of this stack. +static U32 sizeToWrite; ///< Size to write to destination. -static U32 REMOVETHEVAR = 0; +static U32 REMOVETHEVAR = 0; // TODO remove -static void processIncomingCmdMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); -static void processIncomingUpdateMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); +// ********** private function prototypes ********** + +static void handleIncomingCmdMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); +static void handleIncomingUpdateMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); static void prepareResponseMessage( U08 respOfMsgID, ACK_NACK_STATUS_T ackNack, SW_UPDATE_RESP_STATUS_T* respBuffer ); static void clearSWUpdateBuffer( void ); static ACK_NACK_STATUS_T handleFirmwareUpdate( void ); static ACK_NACK_STATUS_T handleFPGAUpdate( void ); +/*********************************************************************//** + * @brief + * The initDownload function initializes the download unit. + * @details \b Inputs: none + * @details \b Outputs: thisStackMailBox + * @return none + *************************************************************************/ void initDownload( void ) { thisStackMailBox = RECEIVE_MSG_ID[ BL_STACK_ID ]; @@ -68,36 +83,74 @@ clearSWUpdateCommandState(); } +/*********************************************************************//** + * @brief + * The execDownload function executes the download state machine. + * @details \b Inputs: none + * @details \b Outputs: none + * @return none TODO change the design to a state machine + *************************************************************************/ void execDownload( void ) { // TODO make this a state machine - processIncomingCmdMessage( SW_UPDATE_COMMAD ); - processIncomingUpdateMessage( thisStackMailBox ); + handleIncomingCmdMessage( SW_UPDATE_COMMAD ); + handleIncomingUpdateMessage( thisStackMailBox ); } +/*********************************************************************//** + * @brief + * The getSWUpdateCommandState function returns the current software update + * command state. + * @details \b Inputs: SWUpdateCommandState + * @details \b Outputs: none + * @return current software update command state + *************************************************************************/ SW_UPDATE_CMD_T getSWUpdateCommandState( void ) { return SWUpdateCommandState; } +/*********************************************************************//** + * @brief + * The getSWUpdateDestination function returns the current software update + * destination (firmware or FPGA). + * @details \b Inputs: SWUpdateRCVStatus + * @details \b Outputs: none + * @return current software update destination + *************************************************************************/ SW_UPDATE_DESINTATION_T getSWUpdateDestination( void ) { return (SW_UPDATE_DESINTATION_T)SWUpdateRCVStatus.updateDest; } +/*********************************************************************//** + * @brief + * The clearSWUpdateCommandState function clears the software update command + * state to idle state. + * @details \b Inputs: none + * @details \b Outputs: SWUpdateCommandState + * @return none + *************************************************************************/ void clearSWUpdateCommandState( void ) { SWUpdateCommandState = UPDATE_CMD_IDLE; } +/*********************************************************************//** + * @brief + * The sendFPGAAckNackStatus function sends the ack or nack status to the + * application. + * @details \b Inputs: SWUpdateRCVStatus, thisStackMailBox + * @details \b Outputs: none + * @param ack or nack status to be sent + * @return none + *************************************************************************/ void sendFPGAAckNackStatus( ACK_NACK_STATUS_T ackNackStatus ) { SW_UPDATE_RESP_STATUS_T resp; - BOOL status = FALSE; // TODO do we need this? - prepareResponseMessage( SWUpdateRCVStatus.msgID, ackNackStatus, &resp ); - status = sendAckNackStatusFromFirmware( (U08*)&resp ); + sendAckNackStatusFromFirmware( (U08*)&resp ); clearCommBuffer( thisStackMailBox ); } @@ -108,12 +161,24 @@ // ********** private functions ********** -static void processIncomingCmdMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) +/*********************************************************************//** + * @brief + * The handleIncomingCmdMessage function handles the incoming command message + * from the CAN bus. Once the entire message has been received, it is processed + * and the corresponding destination is informed that an update is available. + * @details \b Inputs: SWUpdateCmdStatus + * @details \b Outputs: SWUpdateCmdStatus + * @param mailbox of the buffer that has been received + * @return none + *************************************************************************/ +static void handleIncomingCmdMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) { + // Peek into the number of bytes received for the command buffer S32 bytesInBuffer = getNumberOfBytesInBuffer( mailBox ); if ( bytesInBuffer == CAN_MESSAGE_PAYLOAD_SIZE ) { + // If the command buffer has been received, get it from the comm buffer and process it SW_UPDATE_CMD_STATUS_T SWUpdateCmdStatus; SW_UPDATE_RESP_STATUS_T resp; @@ -125,6 +190,7 @@ U08 msgID = SWUpdateCmdStatus.msgID; SW_UPDATE_DESINTATION_T dest = (SW_UPDATE_DESINTATION_T)( SWUpdateCmdStatus.updateCmd >> SHIFT_BITS_TO_GET_TARGET ); // TODO add more logic for other stacks + // Calculate the CRC of the message and ack or nack based on the matching of the CRCs calcCRC = crc32( calcCRC, (U08*)&SWUpdateCmdStatus, sizeof( SW_UPDATE_CMD_STATUS_T ) - sizeof( U32 ) ); hasCRCPassed = ( SWUpdateCmdStatus.msgCRC == calcCRC ? TRUE : FALSE ); @@ -139,18 +205,31 @@ if ( UPDATE_FPGA == dest ) { + // If the update destination is FPGA, signal FPGA to prepare for the update. signalFPGAToPrepareForUpdate(); } } + // Send the result of the command received prepareResponseMessage( msgID, ackStatus, &resp ); sendAckNackStatusFromFirmware( (U08*)&resp ); clearCommBuffer( mailBox ); } } -static void processIncomingUpdateMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) +/*********************************************************************//** + * @brief + * The handleIncomingUpdateMessage function handles the incoming update message + * from the CAN bus. Once the entire update message has been received, it then + * is sent to the corresponding destination that is under update. + * @details \b Inputs: SWUpdateRCVStatus + * @details \b Outputs: SWUpdateRCVStatus + * @param mailbox of the buffer that has been received + * @return none + *************************************************************************/ +static void handleIncomingUpdateMessage( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) { + // Peek into the comm buffer to see if the entire data has been received S32 bytesInBuffer = getNumberOfBytesInBuffer( mailBox ); if ( bytesInBuffer == NUM_OF_CAN_BYTES_FOR_UPDATE ) @@ -165,9 +244,11 @@ getCommBuffer( mailBox, (U08*)&SWUpdateRCVStatus, NUM_OF_CAN_BYTES_FOR_UPDATE ); + // Create a local buffer and copy the header into the buffer excluding the CRC so only 4 bytes of ID, Destination, and payload length memcpy( bufferWithNoCRC, (U08*)&SWUpdateRCVStatus, sizeof( U32 ) ); + // Copy the entire update buffer that is going either to firmware or FPGA into the local buffer. memcpy( &bufferWithNoCRC[ sizeof( U32 ) ], SWUpdateRCVStatus.SWUpdateBuffer, sizeof( SWUpdateRCVStatus.SWUpdateBuffer ) ); - + // Calculate the CRC of the local copied buffer and compare it against the message CRC calcCRC = crc32( calcCRC, bufferWithNoCRC, sizeof( bufferWithNoCRC ) ); hasCRCPassed = ( SWUpdateRCVStatus.msgCRC == calcCRC ? TRUE : FALSE ); @@ -177,6 +258,7 @@ if ( TRUE == hasCRCPassed ) { + // CRC passed, call the corresponding the handlers to update either FPGA or firmware switch ( SWUpdateRCVStatus.updateDest ) { case UPDATE_FIRMWARE: @@ -193,13 +275,27 @@ } } + // TODo send nack if the CRC failed + //prepareResponseMessage( SWUpdateRCVStatus.msgID, ackNackStatus, &resp ); //status = sendAckNackStatusFromFirmware( (U08*)&resp ); // TODO do we have to retry if send failed? clearCommBuffer( mailBox ); // TODo does this need to be here? How about resync? //clearSWUpdateBuffer(); // TODO uncomment } } +/*********************************************************************//** + * @brief + * The prepareResponseMessage function prepares the message body that is + * used to respond to the updater app. + * @details \b Inputs: none + * @details \b Outputs: none + * @param message ID that is being responded for + * @param ack nack status + * @param response buffer which is the pointer to the buffer that is used + * to be sent to the app + * @return none + *************************************************************************/ static void prepareResponseMessage( U08 respOfMsgID, ACK_NACK_STATUS_T ackNack, SW_UPDATE_RESP_STATUS_T* respBuffer ) { U32 calcCRC = 0; @@ -210,11 +306,27 @@ respBuffer->msgCRC = crc32( calcCRC, (U08*)&respBuffer, sizeof( SW_UPDATE_RESP_STATUS_T ) - sizeof( U32 ) ); } +/*********************************************************************//** + * @brief + * The clearSWUpdateBuffer function clears the software update buffer. + * @details \b Inputs: none + * @details \b Outputs: SWUpdateRCVStatus + * @return none + *************************************************************************/ static void clearSWUpdateBuffer( void ) { memset( &SWUpdateRCVStatus, 0x0, sizeof( SW_UPDATE_RCV_STATUS_T ) ); } +/*********************************************************************//** + * @brief + * The handleFirmwareUpdate function handles the firmware update data. This + * function checks that the message is not the final message and then signal + * the non-volatile memory to update the flash. + * @details \b Inputs: SWUpdateRCVStatus + * @details \b Outputs: none + * @return Ack if the write was successful otherwise, Nack + *************************************************************************/ static ACK_NACK_STATUS_T handleFirmwareUpdate( void ) { SW_UPDATE_RESP_STATUS_T resp; @@ -237,10 +349,21 @@ return ackStatus; } +/*********************************************************************//** + * @brief + * The handleFPGAUpdate function handles the FPGA update data. This + * function checks that the message is not the final message and then signals + * the FPGA driver to update the FPGA. + * @details \b Inputs: SWUpdateRCVStatus + * @details \b Outputs: none + * @return Ack if the write was successful otherwise, Nack + *************************************************************************/ static ACK_NACK_STATUS_T handleFPGAUpdate( void ) { ACK_NACK_STATUS_T ackStatus = NACK; + // TODO why the firmware handler is slightly different? Make them consistent. + if ( SWUpdateRCVStatus.updatePayloadLen != SW_UPDATE_FINAL_MSG_INDEX ) { sizeToWrite = SWUpdateRCVStatus.updatePayloadLen; Index: firmware/App/Services/Download.h =================================================================== diff -u -rfc99f47309c9d96f73a2d4696b42d6d302f334a7 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Download.h (.../Download.h) (revision fc99f47309c9d96f73a2d4696b42d6d302f334a7) +++ firmware/App/Services/Download.h (.../Download.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,22 @@ -/* - * Download.h - * - * Created on: Aug 21, 2024 - * Author: fw - */ #ifndef __DOWNLOAD_H__ #define __DOWNLOAD_H__ #include "BLCommon.h" +/** + * @defgroup Download Download + * @brief Download unit. Manages receiving bytes and passing it to the + * drivers to update. + * + * @addtogroup Download + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initDownload( void ); void execDownload( void ); @@ -22,6 +29,8 @@ void sendFPGAAckNackStatus( ACK_NACK_STATUS_T ackNackStatus ); -U08 getTempRemoveMSGID(); +U08 getTempRemoveMSGID(); // TODO remove or make is permanent +/**@}*/ + #endif Index: firmware/App/Services/FPGA.c =================================================================== diff -u -rb8160225a28a2ba4d6dff4d0433e55465c737a14 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/FPGA.c (.../FPGA.c) (revision b8160225a28a2ba4d6dff4d0433e55465c737a14) +++ firmware/App/Services/FPGA.c (.../FPGA.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * FPGA.c - * - * Created on: Aug 15, 2024 - * Author: fw - */ #include // For memcpy and memset @@ -17,129 +11,144 @@ #include "SystemComm.h" #include "Utilities.h" -#define QUEUE_MAX_SIZE 20 ///< Max queue size. -#define FPGA_PAGE_SIZE 256 ///< FPGA register pages are 256 bytes. -#define FPGA_MAX_READ_SIZE ( FPGA_PAGE_SIZE - 1 ) -#define FPGA_WRITE_CMD_BUFFER_LEN ( FPGA_PAGE_SIZE + 8 ) ///< FPGA write command buffer byte length. -#define FPGA_READ_CMD_BUFFER_LEN 8 ///< FPGA read command buffer byte length. -#define FPGA_WRITE_RSP_BUFFER_LEN 8 ///< FPGA write command response buffer byte length. -#define FPGA_READ_RSP_BUFFER_LEN ( FPGA_PAGE_SIZE + 8 ) ///< FPGA read command response buffer byte length. +/** + * @addtogroup FPGA + * @{ + */ -#define SCI2_RECEIVE_DMA_REQUEST 28 ///< Serial port 2 receive DMA request line. -#define SCI2_TRANSMIT_DMA_REQUEST 29 ///< Serial port 2 transmit DMA request line. +// ********** private definitions ********** -#define FPGA_CRC_LEN 2 ///< FPGA CRC byte length. -#define FPGA_WRITE_CMD_HDR_LEN 4 ///< FPGA write command header byte length. -#define FPGA_WRITE_RSP_HDR_LEN 3 ///< FPGA write command response header byte length. +#define QUEUE_MAX_SIZE 20 ///< Max queue size. +#define FPGA_PAGE_SIZE 256 ///< FPGA register pages are 256 bytes. +#define FPGA_MAX_READ_SIZE ( FPGA_PAGE_SIZE - 1 ) ///< FGPA max read size. +#define FPGA_WRITE_CMD_BUFFER_LEN ( FPGA_PAGE_SIZE + 8 ) ///< FPGA write command buffer byte length. +#define FPGA_READ_CMD_BUFFER_LEN 8 ///< FPGA read command buffer byte length. +#define FPGA_WRITE_RSP_BUFFER_LEN 8 ///< FPGA write command response buffer byte length. +#define FPGA_READ_RSP_BUFFER_LEN ( FPGA_PAGE_SIZE + 8 ) ///< FPGA read command response buffer byte length. -#define FPGA_WRITE_CMD_CODE 0x55 ///< FPGA write command code. -#define FPGA_WRITE_CMD_ACK 0xA5 ///< FPGA write command ACK code. -#define FPGA_READ_CMD_CODE 0x5A ///< FPGA read command code. -#define FPGA_READ_CMD_ACK 0xAA ///< FPGA read command ACK code. -#define FPGA_HEADER_START_ADDR 0x0000 ///< Start address for FPGA header data. -#define FPGA_BULK_READ_START_ADDR 0x0100 ///< Start address for FPGA continuous priority reads. -#define FPGA_WRITE_START_ADDR 0x000B ///< Start address for FPGA continuous priority writes. // TODO does this vary? +#define SCI2_RECEIVE_DMA_REQUEST 28 ///< Serial port 2 receive DMA request line. +#define SCI2_TRANSMIT_DMA_REQUEST 29 ///< Serial port 2 transmit DMA request line. + +#define FPGA_CRC_LEN 2 ///< FPGA CRC byte length. +#define FPGA_WRITE_CMD_HDR_LEN 4 ///< FPGA write command header byte length. +#define FPGA_WRITE_RSP_HDR_LEN 3 ///< FPGA write command response header byte length. + +#define FPGA_WRITE_CMD_CODE 0x55 ///< FPGA write command code. +#define FPGA_WRITE_CMD_ACK 0xA5 ///< FPGA write command ACK code. +#define FPGA_READ_CMD_CODE 0x5A ///< FPGA read command code. +#define FPGA_READ_CMD_ACK 0xAA ///< FPGA read command ACK code. +#define FPGA_HEADER_START_ADDR 0x0000 ///< Start address for FPGA header data. +#define FPGA_BULK_READ_START_ADDR 0x0100 ///< Start address for FPGA continuous priority reads. +#define FPGA_WRITE_START_ADDR 0x000B ///< Start address for FPGA continuous priority writes. // TODO does this vary? #define FPGA_FLASH_CONTROL_REG_ADDR 0x090E -#define FPGA_FLASH_STATUS_REG_ADDR 0x0900 ///< FPGA flash status register address. // TODO remvoe -#define FPGA_FIFO_COUNT_REG_ADDR 0x0902 ///< FPGA FIFO count register address. // TODO remvoe -#define FPGA_FLASH_DATA_REG_ADDR 0x0A00 ///< FPGA flash data register address. // TODO remvoe -#define FPGA_MULTI_BOOT_STATUS_ADDR 0x0900 ///< FPGA multi boot status register address. -#define FPGA_ICAP2_REG_ADDR 0x0909 ///< FPGA ICAP 2 command register address. +#define FPGA_FLASH_STATUS_REG_ADDR 0x0900 ///< FPGA flash status register address. // TODO remvoe +#define FPGA_FIFO_COUNT_REG_ADDR 0x0902 ///< FPGA FIFO count register address. // TODO remvoe +#define FPGA_FLASH_DATA_REG_ADDR 0x0A00 ///< FPGA flash data register address. // TODO remvoe +#define FPGA_MULTI_BOOT_STATUS_ADDR 0x0900 ///< FPGA multi boot status register address. +#define FPGA_ICAP2_REG_ADDR 0x0909 ///< FPGA ICAP 2 command register address. -#define FPGA_UPDATE_REGISTER_ADDR ( FPGA_WRITE_START_ADDR + 4 ) -#define FPGA_READ_CMD_HDR_LEN 4 ///< FPGA read command header byte length. -#define FPGA_READ_RSP_HDR_LEN 3 ///< FPGA read command response header byte length. -#define FPGA_UPDATE_REQUEST_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) // TODO Get this value from Noe, make sure the index is the same in all of the stacks -#define FPGA_FLASH_STATUS_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) -#define FPGA_FIFO_COUNT_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) +#define FPGA_UPDATE_REGISTER_ADDR ( FPGA_WRITE_START_ADDR + 4 ) ///< FPGA update register address. +#define FPGA_READ_CMD_HDR_LEN 4 ///< FPGA read command header byte length. +#define FPGA_READ_RSP_HDR_LEN 3 ///< FPGA read command response header byte length. +#define FPGA_UPDATE_REQUEST_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) ///< FPGA update request index. // TODO Get this value from Noe, make sure the index is the same in all of the stacks +#define FPGA_FLASH_STATUS_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) ///< FPGA flash status index. +#define FPGA_FIFO_COUNT_INDEX ( FPGA_READ_RSP_HDR_LEN + 1 ) ///< FPGA FIFO count index. -#define UPDATE_REQUESTED_VALUE 1 +#define UPDATE_REQUESTED_VALUE 1 ///< The value that indicates and update has been requested. -#define FPGA_FIFO_SIZE_BYTES 1024 -#define FPGA_FIFO_COUNT_MASK 0x03FF +#define FPGA_FIFO_SIZE_BYTES 1024 ///< FPGA FIFO size in bytes. +#define FPGA_FIFO_COUNT_MASK 0x03FF ///< FPGA FIFO count in FIFO mask. -#define FPGA_ERASE_FIFO_CMD_OK ( 1 << 11 ) -#define FPGA_FLASH_STATUS_OK ( 1 << 15 ) +#define FPGA_ERASE_FIFO_CMD_OK ( 1 << 11 ) ///< FPGA erase FIFO command status ok value. +#define FPGA_FLASH_STATUS_OK ( 1 << 15 ) ///< FPGA flash status status ok value. -#define FPGA_PRE_SELF_CONFIG_TIMEOUT_MS 10000 +#define FPGA_PRE_SELF_CONFIG_TIMEOUT_MS 10000 ///< FPGA pre self configure timeout in milliseconds. +/// FPGA communication status enumeration typedef enum { - FPGA_COMM_IDLE = 0, - FPGA_COMM_READ_IN_PROGRESS, - FPGA_COMM_READ_RESP_RECEIVED, - FPGA_COMM_WRITE_IN_PROGRESS, - FPGA_COMM_WRITE_RESP_RECEIVED, - NUM_OF_FPGA_COMM_STATUS + FPGA_COMM_IDLE = 0, ///< FPGA communication idle. + FPGA_COMM_READ_IN_PROGRESS, ///< FPGA communication read in progress. + FPGA_COMM_READ_RESP_RECEIVED, ///< FPGA communication read response received. + FPGA_COMM_WRITE_IN_PROGRESS, ///< FPGA communication write in progress. + FPGA_COMM_WRITE_RESP_RECEIVED, ///< FPGA communication write response received. + NUM_OF_FPGA_COMM_STATUS ///< Number of FPGA communication status. } FPGA_COMM_STATE_T; +/// FPGA queue jobs enumeration typedef enum { - FPGA_READ_HEADER = 0, - FPGA_READ_UPDATE_REG, - FPGA_WRITE_UPDATE_REG, - FPGA_RESET_FLASH, - FPGA_ERASE_FIFO, - FPGA_ENABLE_FLASH, - FPGA_READ_MULTI_BOOT_STATUS, - FPGA_FLASH_WRITE_DATA, - FPGA_SELF_CONFIGURE, - NUM_OF_FPGA_JOBS, + FPGA_READ_HEADER = 0, ///< FPGA read header. + FPGA_READ_UPDATE_REG, ///< FPGA read update request register. + FPGA_WRITE_UPDATE_REG, ///< FPGA write to update request register. + FPGA_RESET_FLASH, ///< FPGA reset flash. + FPGA_ERASE_FIFO, ///< FPGA erase FIFO. + FPGA_ENABLE_FLASH, ///< FPGA enable flash. + FPGA_READ_MULTI_BOOT_STATUS, ///< FPGA read multi-boot status. + FPGA_FLASH_WRITE_DATA, ///< FPGA write flash data. + FPGA_SELF_CONFIGURE, ///< FPGA self configure. + NUM_OF_FPGA_JOBS, ///< Number of the FPGA jobs. } FPGA_JOBS_T; +/// FPGA state machine states enumeration typedef enum { - FPGA_IDLE_STATE = 0, - FPGA_WRITE_TO_FPGA_STATE, - FPGA_RCV_WRITE_RESP_FROM_FPGA_STATE, - FPGA_READ_FROM_FPGA_STATE, - FPGA_RCV_READ_RESP_FROM_FPGA_STATE, - NUM_OF_FPGA_STATES + FPGA_IDLE_STATE = 0, ///< FPGA idle state. + FPGA_WRITE_TO_FPGA_STATE, ///< FPGA write to FPGA state. + FPGA_RCV_WRITE_RESP_FROM_FPGA_STATE, ///< FPGA receive write response from FPGA state. + FPGA_READ_FROM_FPGA_STATE, ///< FPGA read from FPGA state. + FPGA_RCV_READ_RESP_FROM_FPGA_STATE, ///< FPGA received read response from FPGA state. + NUM_OF_FPGA_STATES ///< Number of FPGA states. } FPGA_STATE_T; #pragma pack(push,1) +/// FPGA queue job specification structure typedef struct { - U16 fpgaJobAddress; - U16 fpgaJobSize; - U08* fpgaWriteStartAddress; - U08 fpgaIsJobWrite; + U16 fpgaJobAddress; ///< FPGA job address. + U16 fpgaJobSize; ///< FPGA job size. + U08* fpgaWriteStartAddress; ///< FPGA write buffer start address. + U08 fpgaIsJobWrite; ///< FPGA boolean flag to indicate this is a write job or not. } FPGA_JOB_SPECS_T; +/// FPGA jobs queue status structure typedef struct { - U08 fpgaJobsQueue[ QUEUE_MAX_SIZE ]; - U08 fpgaJobRearIndex; - U08 fpgaJobFrontIndex; - U08 fpgaJobsQueueCount; - U08 fpgaCurrentJob; - FPGA_COMM_STATE_T fpgaCommRead; - FPGA_COMM_STATE_T fpgaCommWrite; + U08 fpgaJobsQueue[ QUEUE_MAX_SIZE ]; ///< FPGA jobs queue. + U08 fpgaJobRearIndex; ///< FPGA job queue rear index. + U08 fpgaJobFrontIndex; ///< FPGA job queue front index. + U08 fpgaJobsQueueCount; ///< FPGA job queue count. + U08 fpgaCurrentJob; ///< FPGA queue current job. + FPGA_COMM_STATE_T fpgaCommRead; ///< FPGA DMA read command state. + FPGA_COMM_STATE_T fpgaCommWrite; ///< FPGA DMA write command state. } FPGA_JOBS_Q_STATUS_T; +/// FPGA flash status structure typedef struct { - BOOL hasUpdateRegsBeenRqstd; - U16 fifoRemainingCount; - BOOL isFlashEraseOk; - BOOL isFlashStatusOk; - BOOL isFPGAFlashComplete; - U16 flashStatusBits; - U32 preSelfConfigureStartTimeMS; - U32 startTime; + BOOL hasUpdateRegsBeenRqstd; ///< Flag to indicate whether update registers request has been requested. + U16 fifoRemainingCount; ///< FIFO empty space remaining count. + BOOL isFIFOEraseOk; ///< Flag to indicate whether FIFO has been erased or not. + BOOL isFlashStatusOk; ///< Flag to indicate whether flash status is okay or not. + BOOL isFPGAFlashComplete; ///< Flag to indicate whether flash update has been completed. + U16 flashStatusBits; ///< Flash status. + U32 preSelfConfigureStartTimeMS; ///< Pre self configure start time in milliseconds. + U32 startTime; ///< Start time in milliseconds. } FPGA_FLASH_STATUS_T; /// Record structure for FPGA header read. typedef struct { - U08 fpgaId; ///< Reg 0. FPGA ID code. Checked against expected value at power up to verify basic FPGA communication and operation. - U08 fpgaRev; ///< Reg 1. FPGA revision (minor) being reported. - U08 fpgaRevMajor; ///< Reg 2. FPGA revision (major) being reported. - U08 fpgaRevLab; ///< Reg 3. FPGA revision (lab) being reported. - U16 fpgaStatus; ///< Reg 4. FPGA status register. + U08 fpgaId; ///< Reg 0. FPGA ID code. Checked against expected value at power up to verify basic FPGA communication and operation. + U08 fpgaRev; ///< Reg 1. FPGA revision (minor) being reported. + U08 fpgaRevMajor; ///< Reg 2. FPGA revision (major) being reported. + U08 fpgaRevLab; ///< Reg 3. FPGA revision (lab) being reported. + U16 fpgaStatus; ///< Reg 4. FPGA status register. } FPGA_HEADER_T; // Read only on FPGA #pragma pack(pop) +// ********** private data ********** + // FPGA comm buffers static U08 fpgaWriteCmdBuffer[ FPGA_WRITE_CMD_BUFFER_LEN ]; ///< FPGA write command buffer. Holds the next FPGA write command to be transmitted. static U08 fpgaReadCmdBuffer[ FPGA_READ_CMD_BUFFER_LEN ]; ///< FPGA read command buffer. Holds the next FPGA read command to be transmitted. @@ -152,25 +161,27 @@ static g_dmaCTRL fpgaDMAReadControlRecord; ///< DMA record for controlling a DMA read command transmission from buffer. static g_dmaCTRL fpgaDMAReadRespControlRecord; ///< DMA record for controlling a DMA read command reception to buffer. -static FPGA_HEADER_T fpgaHeader; ///< Record of last received FPGA header data. -static FPGA_STATE_T fpgaState; -static U08 fpgaUpdateRegisterStatus; -static FPGA_JOBS_Q_STATUS_T fpgaJobsQStatus; -static FPGA_FLASH_STATUS_T fpgaFlashStatus; -static U08 fpgaDataToWriteBuffer[ SW_UPDATE_FLASH_BUFFER_SIZE ]; -static U32 fpgaDataLenToWrite; +static FPGA_HEADER_T fpgaHeader; ///< Record of last received FPGA header data. +static FPGA_STATE_T fpgaState; ///< FPGA current state. +static U08 fpgaUpdateRegisterStatus; ///< FPGA update register status. +static FPGA_JOBS_Q_STATUS_T fpgaJobsQStatus; ///< FPGA jobs queue status. +static FPGA_FLASH_STATUS_T fpgaFlashStatus; ///< FPGA flash status. +static U08 fpgaDataToWriteBuffer[ SW_UPDATE_FLASH_BUFFER_SIZE ]; ///< FPGA data to write to FPGA flash buffer. +static U32 fpgaDataLenToWrite; ///< FPGA data length to write to FPGA. static U32 TESTREMOVE = 0; // TODO remove static U32 countRemove = 0; // TODO remove -static U08 tempACkStatus = 0; +static U08 tempACkStatus = 0; // TODO remove +/// FPGA stack ID for TD, DD, RO. static const U08 STACK_FPGA_ID[ NUM_OF_FW_STACKS ] = { 0x5A, 0x61, 0xFF }; // TODO update with the real FPGA IDs -static const U16 DISABLE_UPDATE_REG_CMD = 5; // TODO what is this value? 0? -static const U08 FPGA_RESET_FLASH_CMD = 0x01; -static const U08 FPGA_ERASE_FIFO_CMD = 0x08; -static const U08 FPGA_ENABLE_FLASH_CMD = 0x00; -static const U08 FPGA_SELF_CONFIG_CMD = 0x03; +static const U16 DISABLE_UPDATE_REG_CMD = 5; ///< FPGA disable update register command. // TODO what is this value? 0? +static const U08 FPGA_RESET_FLASH_CMD = 0x01; ///< FPGA reset flash command. +static const U08 FPGA_ERASE_FIFO_CMD = 0x08; ///< FPGA erase FIFO command. +static const U08 FPGA_ENABLE_FLASH_CMD = 0x00; ///< FPGA enable flash command. +static const U08 FPGA_SELF_CONFIG_CMD = 0x03; ///< FPGA self configure command. +/// FPGA jobs specifications. static const FPGA_JOB_SPECS_T JOBS_SPECS[ NUM_OF_FPGA_JOBS ] = { { FPGA_HEADER_START_ADDR, sizeof( FPGA_HEADER_T ), 0, FALSE }, // FPGA_READ_HEADER { FPGA_BULK_READ_START_ADDR, FPGA_MAX_READ_SIZE, 0, FALSE }, // FPGA_READ_UPDATE_REG @@ -183,6 +194,8 @@ { FPGA_ICAP2_REG_ADDR, sizeof( U08 ), (U08*)&FPGA_SELF_CONFIG_CMD, TRUE } // FPGA_SELF_CONFIGURE }; +// ********** private function prototypes ********** + static void initDMA( void ); static void consumeUnexpectedData( void ); static void requestFlashRegistersStatus( void ); @@ -211,6 +224,13 @@ static FPGA_STATE_T handleFPGAReadFromFPGAState( void ); static FPGA_STATE_T handleFPGAReceiveReadRespFromFPGAState( void ); +/*********************************************************************//** + * @brief + * The initFPGA function initializes the FPGA unit. + * @details \b Inputs: none + * @details \b Outputs: FPGA unit initialized. + * @return none + *************************************************************************/ void initFPGA( void ) { memset( &fpgaHeader, 0x0, sizeof( FPGA_HEADER_T ) ); @@ -227,6 +247,13 @@ fpgaUpdateRegisterStatus = 0; } +/*********************************************************************//** + * @brief + * The execFPGA function the FPGA state machine. + * @details \b Inputs: fpgaState + * @details \b Outputs: fpgaState + * @return none + *************************************************************************/ void execFPGA( void ) { if ( TRUE == fpgaFlashStatus.hasUpdateRegsBeenRqstd ) @@ -275,6 +302,15 @@ } } +/*********************************************************************//** + * @brief + * The signalFPGAReceiptCompleted function increments a counter to indicate + * that another DMA receipt from the FPGA has completed and sets comm flags + * indicating pending response from FPGA is completed. + * @details \b Inputs: fpgaJobsQStatus + * @details \b Outputs: fpgaJobsQStatus + * @return none + *************************************************************************/ void signalFPGAReceiptCompleted( void ) { if ( FPGA_COMM_WRITE_IN_PROGRESS == fpgaJobsQStatus.fpgaCommWrite ) @@ -288,6 +324,14 @@ } } +/*********************************************************************//** + * @brief + * The hasUpdateBeenRequested function checks whether an update has been + * requested through the FPGA read registers. + * @details \b Inputs: fpgaState, fpgaUpdateRegisterStatus + * @details \b Outputs: fpgaUpdateRegisterStatus + * @return TRUE if an update has been requested otherwise, FALSE + *************************************************************************/ BOOL hasUpdateBeenRequested( void ) { BOOL status = FALSE; @@ -302,18 +346,41 @@ return status; } +/*********************************************************************//** + * @brief + * The isFPGAIDValid function checks whether the FPGA header is valid. + * @details \b Inputs: fpgaHeader + * @details \b Outputs: none + * @return TRUE if the FPGA header is valid otherwise, FALSE + *************************************************************************/ BOOL isFPGAIDValid( void ) { BOOL status = ( STACK_FPGA_ID[ BL_STACK_ID ] == fpgaHeader.fpgaId ? TRUE : FALSE ); return status; } +/*********************************************************************//** + * @brief + * The isFPGAFlashComplete function returns the status of FPGA flash. So + * TRUE if the flash is complete, otherwise, FALSE. + * @details \b Inputs: fpgaFlashStatus + * @details \b Outputs: none + * @return the status of the FPGA flash + *************************************************************************/ BOOL isFPGAFlashComplete( void ) { return fpgaFlashStatus.isFPGAFlashComplete; } +/*********************************************************************//** + * @brief + * The signalFPGAToPrepareForUpdate function enqueues the FPGA update + * initialization jobs if the queue is not full. + * @details \b Inputs: none + * @details \b Outputs: none + * @return none + *************************************************************************/ void signalFPGAToPrepareForUpdate( void ) { if ( FALSE == isQueueFull() ) @@ -324,6 +391,14 @@ } } +/*********************************************************************//** + * @brief + * The signalFPGAToWriteToFlash function enqueues the FPGA write to flash + * job if the queue is not full. + * @details \b Inputs: none + * @details \b Outputs: fpgaDataLenToWrite, fpgaDataToWriteBuffer + * @return none + *************************************************************************/ void signalFPGAToWriteToFlash( U08* data, U32 len ) { if ( FALSE == isQueueFull() ) @@ -337,6 +412,14 @@ } } +/*********************************************************************//** + * @brief + * The signalFPGAToSelfConfigure function enqueues the FPGA self configure + * job if the queue is not full. + * @details \b Inputs: none + * @details \b Outputs: fpgaFlashStatus + * @return none + *************************************************************************/ void signalFPGAToSelfConfigure( void ) { if ( FALSE == isQueueFull() ) @@ -349,6 +432,13 @@ // ********** private functions ********** +/*********************************************************************//** + * @brief + * The initDMA function initializes the DMA communication. + * @details \b Inputs: none + * @details \b Outputs: FPGA DMA unit initialized. + * @return none + *************************************************************************/ static void initDMA( void ) { // Enable interrupt notifications for FPGA serial port @@ -439,6 +529,14 @@ fpgaDMAReadRespControlRecord.FRSOFFSET = 0; // Not used } +/*********************************************************************//** + * @brief + * The consumeUnexpectedData function checks to see if a byte is sitting in + * the SCI2 received data register and consumes the byte if found. + * @details \b Inputs: SCI FLR register + * @details \b Outputs: SCI errors cleared, unexpected byte consumed + * @return none + *************************************************************************/ static void consumeUnexpectedData( void ) { // Clear any errors @@ -451,6 +549,14 @@ } } +/*********************************************************************//** + * @brief + * The requestFlashRegistersStatus function requests the FPGA flash readings + * status. + * @details \b Inputs: none + * @details \b Outputs: fpgaReadCmdBuffer[], fpgaJobsQStatus, fpgaFlashStatus + * @return none + *************************************************************************/ static void requestFlashRegistersStatus( void ) { U16 jobAddress = JOBS_SPECS[ FPGA_READ_MULTI_BOOT_STATUS ].fpgaJobAddress; @@ -476,6 +582,13 @@ startDMAReadCmd(); } +/*********************************************************************//** + * @brief + * The processFPGAFlashRegistersRead function processes the read flash readings. + * @details \b Inputs: fpgaReadResponseBuffer[] + * @details \b Outputs: fpgaFlashStatus + * @return none + *************************************************************************/ static void processFPGAFlashRegistersRead( void ) { if ( FPGA_READ_CMD_ACK == fpgaReadResponseBuffer[ 0 ] ) @@ -498,7 +611,7 @@ if ( ( flashStatus & FPGA_ERASE_FIFO_CMD_OK ) == FPGA_ERASE_FIFO_CMD_OK ) { - fpgaFlashStatus.isFlashEraseOk = TRUE; + fpgaFlashStatus.isFIFOEraseOk = TRUE; } if ( ( flashStatus & FPGA_FLASH_STATUS_OK ) == FPGA_FLASH_STATUS_OK ) @@ -509,6 +622,16 @@ } } +/*********************************************************************//** + * @brief + * The setupDMAForReadResp function sets the expected byte count for the + * next DMA read command response from the FPGA. + * @details \b Inputs: none + * @details \b Outputs: fpgaDMAReadRespControlRecord + * @param bytes2Receive number of expected bytes to be transmitted via + * DMA from the FPGA + * @return none + *************************************************************************/ static void setupDMAForReadResp( U32 bytes2Receive ) { // Verify # of bytes does not exceed buffer length @@ -518,6 +641,15 @@ } } +/*********************************************************************//** + * @brief + * The setupDMAForReadCmd function sets the byte count for the next DMA + * read command to the FPGA. + * @details \b Inputs: none + * @details \b Outputs: fpgaDMAReadControlRecord + * @param bytes2Transmit number of bytes to be transmitted via DMA to the FPGA + * @return none + *************************************************************************/ static void setupDMAForReadCmd( U32 bytes2Transmit ) { // Verify # of bytes does not exceed buffer length @@ -527,13 +659,30 @@ } } +/*********************************************************************//** + * @brief + * The startDMAReceiptOfReadResp function initiates readiness of the DMA + * receiver for the next DMA read command response from the FPGA. + * @details \b Inputs: fpgaDMAReadRespControlRecord + * @details \b Outputs: DMA read command response is ready to be received + * from the FPGA + * @return none + *************************************************************************/ static void startDMAReceiptOfReadResp( void ) { dmaSetCtrlPacket( DMA_CH0, fpgaDMAReadRespControlRecord ); dmaSetChEnable( DMA_CH0, DMA_HW ); setSCI2DMAReceiveInterrupt(); } +/*********************************************************************//** + * @brief + * The startDMAReadCmd function initiates the DMA transmit for the next + * DMA read command to the FPGA. + * @details \b Inputs: fpgaDMAReadControlRecord + * @details \b Outputs: DMA read command to FPGA is initiated + * @return none + *************************************************************************/ static void startDMAReadCmd( void ) { dmaSetCtrlPacket( DMA_CH2, fpgaDMAReadControlRecord ); @@ -607,13 +756,27 @@ setSCI2DMAReceiveInterrupt(); } - +/*********************************************************************//** + * @brief + * The resetFPGACommFlags function resets the various fpga comm flags and + * counters. + * @details \b Inputs: none + * @details \b Outputs: fpgaJobsQStatus + * @return none + *************************************************************************/ static void resetFPGACommFlags( void ) { fpgaJobsQStatus.fpgaCommRead = FPGA_COMM_IDLE; fpgaJobsQStatus.fpgaCommWrite = FPGA_COMM_IDLE; } +/*********************************************************************//** + * @brief + * The enqueue function enqueues a new job into the queue. + * @details \b Inputs: none + * @details \b Outputs: fpgaJobsQStatus + * @return none + *************************************************************************/ static void enqueue( FPGA_JOBS_T job ) { U08 currentRearIndex = fpgaJobsQStatus.fpgaJobRearIndex; @@ -624,6 +787,14 @@ fpgaJobsQStatus.fpgaJobRearIndex = INC_WRAP( currentRearIndex, 0, QUEUE_MAX_SIZE - 1 ); } +/*********************************************************************//** + * @brief + * The enqueue function dequeues a job from the queue. This function is thread + * safe. Prior to dequeuing a job, the IRQ interrupt is stopped. + * @details \b Inputs: fpgaJobsQStatus + * @details \b Outputs: fpgaJobsQStatus + * @return none + *************************************************************************/ static void dequeue( void ) { U08 tempIndex; @@ -646,6 +817,15 @@ _enable_IRQ(); } +/*********************************************************************//** + * @brief + * The peekFromQueue function just reports what is the next job in the queue. + * This function does not do the actual dequeue. This function is thread + * safe. Prior to peeking into the next job, the IRQ interrupt is stopped. + * @details \b Inputs: fpgaJobsQStatus + * @details \b Outputs: none + * @return the next job that is in the queue + *************************************************************************/ static FPGA_JOBS_T peekFromQueue( void ) { _disable_IRQ(); @@ -656,6 +836,13 @@ return nextJob; } +/*********************************************************************//** + * @brief + * The isQueueFull function checks whether the queue is full or not. + * @details \b Inputs: fpgaJobsQStatus + * @details \b Outputs: none + * @return TRUE if the queue is full otherwise, FALSE + *************************************************************************/ static BOOL isQueueFull( void ) { BOOL isFull = FALSE; @@ -668,6 +855,15 @@ return isFull; } +/*********************************************************************//** + * @brief + * The handleFPGAIdleState function handles the FPGA idle state. This state + * checks whether there are any jobs in the queue and processes them. This + * state also requests the flash update registers. + * @details \b Inputs: fpgaJobsQStatus, fpgaFlashStatus + * @details \b Outputs: none + * @return next state of the FPGA state machine + *************************************************************************/ static FPGA_STATE_T handleFPGAIdleState( void ) { FPGA_STATE_T state = FPGA_IDLE_STATE; @@ -678,16 +874,24 @@ if ( FPGA_FLASH_WRITE_DATA == peekFromQueue() ) { + // Check if the next job in the queue is a flash write. + // If there is a flash write, only dequeue it if: + // 1. There are at least 256 bytes available in the FIFO + // 2. The flash status is okay + // 3. The FIFO erase is okay if ( ( fpgaFlashStatus.fifoRemainingCount < SW_UPDATE_FLASH_BUFFER_SIZE ) || ( FALSE == fpgaFlashStatus.isFlashStatusOk ) || - ( FALSE == fpgaFlashStatus.isFlashEraseOk ) ) + ( FALSE == fpgaFlashStatus.isFIFOEraseOk ) ) { isDequeueAllowed = FALSE; } } if ( FPGA_SELF_CONFIGURE == peekFromQueue() ) { + // Check if the next job in the queue is the self configure. Then make sure: + // 1. The delay has timed out + // 2. The flash status is okay if ( ( FALSE == didTimeout( fpgaFlashStatus.preSelfConfigureStartTimeMS, FPGA_PRE_SELF_CONFIG_TIMEOUT_MS ) ) || ( FALSE == fpgaFlashStatus.isFlashStatusOk ) ) { @@ -698,7 +902,7 @@ if ( TRUE == isDequeueAllowed ) { dequeue(); - + // After dequeue based on the job specs transition to either write or read states state = ( FALSE == JOBS_SPECS[ fpgaJobsQStatus.fpgaCurrentJob ].fpgaIsJobWrite ? FPGA_READ_FROM_FPGA_STATE : FPGA_WRITE_TO_FPGA_STATE ); } } @@ -708,6 +912,15 @@ return state; } +/*********************************************************************//** + * @brief + * The handleFPGAWriteToFPGAState function handles the FPGA write to FPGA + * state. This state prepares the buffer to write to FPGA and sets the DMA + * to write to the FPGA. + * @details \b Inputs: fpgaJobsQStatus, fpgaDataLenToWrite + * @details \b Outputs: fpgaFlashStatus, fpgaWriteCmdBuffer[] + * @return next state of the FPGA state machine + *************************************************************************/ static FPGA_STATE_T handleFPGAWriteToFPGAState( void ) { FPGA_STATE_T state = FPGA_RCV_WRITE_RESP_FROM_FPGA_STATE; @@ -717,6 +930,7 @@ if ( ( fpgaDataLenToWrite != SW_UPDATE_FLASH_BUFFER_SIZE ) && ( FPGA_FLASH_WRITE_DATA == fpgaJobsQStatus.fpgaCurrentJob ) ) { + // Set the write length from the buffer length provided jobSize = (U16)fpgaDataLenToWrite; } @@ -757,6 +971,14 @@ return state; } +/*********************************************************************//** + * @brief + * The handleFPGAReceiveWriteRespFromFPGAState function handles the FPGA + * receive write to FPGA response. + * @details \b Inputs: fpgaJobsQStatus, fpgaWriteResponseBuffer[] + * @details \b Outputs: fpgaWriteResponseBuffer[] + * @return next state of the FPGA state machine + *************************************************************************/ static FPGA_STATE_T handleFPGAReceiveWriteRespFromFPGAState( void ) { FPGA_STATE_T state = FPGA_RCV_WRITE_RESP_FROM_FPGA_STATE; @@ -776,7 +998,7 @@ if ( FPGA_FLASH_WRITE_DATA == fpgaJobsQStatus.fpgaCurrentJob ) { sendFPGAAckNackStatus( ACK ); - tempACkStatus = ACK; + tempACkStatus = ACK; // TODO remove TESTREMOVE += fpgaDataLenToWrite;// TODO REMOVE countRemove += 1;// TODO REMOVE @@ -799,6 +1021,13 @@ return state; } +/*********************************************************************//** + * @brief + * The handleFPGAReadFromFPGAState function handles the FPGA read from FPGA. + * @details \b Inputs: none + * @details \b Outputs: fpgaReadCmdBuffer[], fpgaJobsQStatus, fpgaFlashStatus + * @return next state of the FPGA state machine + *************************************************************************/ static FPGA_STATE_T handleFPGAReadFromFPGAState( void ) { FPGA_STATE_T state = FPGA_RCV_READ_RESP_FROM_FPGA_STATE; @@ -827,6 +1056,15 @@ return state; } +/*********************************************************************//** + * @brief + * The handleFPGAReceiveReadRespFromFPGAState function handles the FPGA + * read response from FPGA. + * @details \b Inputs: fpgaJobsQStatus, fpgaReadResponseBuffer[] + * @details \b Outputs: fpgaReadResponseBuffer[], fpgaHeader, + * fpgaUpdateRegisterStatus + * @return next state of the FPGA state machine + *************************************************************************/ static FPGA_STATE_T handleFPGAReceiveReadRespFromFPGAState( void ) { FPGA_STATE_T state = FPGA_RCV_READ_RESP_FROM_FPGA_STATE; @@ -877,3 +1115,5 @@ return state; } +/**@}*/ + Index: firmware/App/Services/FPGA.h =================================================================== diff -u -rfc99f47309c9d96f73a2d4696b42d6d302f334a7 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/FPGA.h (.../FPGA.h) (revision fc99f47309c9d96f73a2d4696b42d6d302f334a7) +++ firmware/App/Services/FPGA.h (.../FPGA.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,27 @@ -/* - * FPGA.h - * - * Created on: Aug 15, 2024 - * Author: fw - */ #ifndef __FPGA_H__ #define __FPGA_H__ #include "BLCommon.h" +/** + * @defgroup FPGA FPGA + * @brief FPGA service unit. + * The FPGA unit manages communication between the bootloader and the FPGA via UART. + * This unit is driven by the Priority Task via calls to two FPGA executive functions: + * 1) Writes update data to the FPGA flash + * 2) Reads header, update register, FIFO count as well as the flash status + * This unit first reads the header record that includes the FPGA ID and revision and + * verifies the FPGA ID to check FPGA communication. + * + * @addtogroup FPGA + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initFPGA( void ); void execFPGA( void ); @@ -24,4 +36,6 @@ void signalFPGAToWriteToFlash( U08* data, U32 len ); void signalFPGAToSelfConfigure( void ); +/**@}*/ + #endif Index: firmware/App/Services/Interrupts.c =================================================================== diff -u -r012573b1913d1bfd2357acfadcad6bb20b295ad9 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Interrupts.c (.../Interrupts.c) (revision 012573b1913d1bfd2357acfadcad6bb20b295ad9) +++ firmware/App/Services/Interrupts.c (.../Interrupts.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * Interrupts.c - * - * Created on: Aug 1, 2024 - * Author: fw - */ #include "can.h" #include "rti.h" @@ -18,14 +12,41 @@ #include "TaskPriority.h" #include "TaskTimer.h" +/** + * @addtogroup Interrupts + * @{ + */ + +// ********** private definitions ********** + +// TODO do we need more error handling? (i.e. canErrorNotification) + +// ********** private data ********** + static BOOL sci2FEOEError; ///< FPGA serial frame or overrun flag; +// ********** private function prototypes ********** +/*********************************************************************//** + * @brief + * The initInterrupts function initializes the Interrupts unit. + * @details \b Inputs: none + * @details \b Outputs: Interrupts unit initialized. + * @return none + *************************************************************************/ void initInterrupts( void ) { sci2FEOEError = FALSE; } +/*********************************************************************//** + * @brief + * The getSci2FEOEError function returns the sci2FEOEError (OE - Overrun, + * FE - Framing Error) status and resets the status if TRUE + * @details \b Inputs: sci2FEOEError + * @details \b Outputs: none + * @return sci2 FE / OE error + *************************************************************************/ BOOL getSci2FEOEError( void ) { BOOL returnValue = sci2FEOEError; @@ -35,6 +56,14 @@ return returnValue; } +/*********************************************************************//** + * @brief + * The rtiNotification function handles real-time interrupt notifications. + * @details \b Inputs: none + * @details \b Outputs: Task associated with given notification is executed. + * @param notification ID of RTI timer that caused this interrupt + * @return none + *************************************************************************/ void rtiNotification( uint32 notification ) { switch ( notification ) @@ -58,6 +87,15 @@ } } +/*********************************************************************//** + * @brief + * The canMessageNotification function handles CAN message notifications. + * @details \b Inputs: none + * @details \b Outputs: CAN message notification handled. + * @param node ID of CAN controller that given notification came from. + * @param messageBox ID of CAN mailbox that triggered the message notification + * @return none + *************************************************************************/ void canMessageNotification( canBASE_t *node, uint32 messageBox ) { if ( node == canREG1 ) @@ -66,6 +104,16 @@ } } +/*********************************************************************//** + * @brief + * The sciNotification function handles UART communication error interrupts. + * Frame and Over-run errors are recorded and cleared. + * @details \b Inputs: none + * @details \b Outputs: sci2FEOEError, sci2FEOEError + * @param sci Pointer to the SCI peripheral that detected the error + * @param flags 32 bits of error flags + * @return none + *************************************************************************/ void sciNotification( sciBASE_t *sci, uint32 flags ) { #ifndef _VECTORCAST_ @@ -87,6 +135,17 @@ } } +/*********************************************************************//** + * @brief + * The dmaGroupANotification function handles communication DMA interrupts. + * @details \b Alarm: ALARM_ID_TD_SOFTWARE_FAULT if given DMA channel is + * invalid/unexpected. + * @details \b Inputs: none + * @details \b Outputs: DMA interrupt is handled. + * @param inttype type of DMA interrupt + * @param channel DMA channel that caused the interrupt + * @return none + *************************************************************************/ void dmaGroupANotification( dmaInterrupt_t inttype, uint32 channel ) { if ( inttype == BTC ) // Block transfer completed interrupt @@ -100,7 +159,6 @@ case DMA_CH2: // FPGA transmit channel clearSCI2DMATransmitInterrupt(); - //signalFPGATransmitCompleted(); // TODO in HD this increments a counter that is not used anywhere, why? break; default: @@ -110,4 +168,5 @@ } } +/**@}*/ Index: firmware/App/Services/Interrupts.h =================================================================== diff -u -rfc4f469fe234371e8f2b9a0625acc66faa6899de -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Interrupts.h (.../Interrupts.h) (revision fc4f469fe234371e8f2b9a0625acc66faa6899de) +++ firmware/App/Services/Interrupts.h (.../Interrupts.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,23 @@ -/* - * Interrupts.h - * - * Created on: Aug 1, 2024 - * Author: fw - */ #ifndef __INTERRUPTS_H__ #define __INTERRUPTS_H__ +/** + * @defgroup Interrupts Interrupts + * @brief Interrupts unit handles various peripheral interrupts. + * + * @addtogroup Interrupts + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initInterrupts( void ); BOOL getSci2FEOEError( void ); +/**@}*/ + #endif Index: firmware/App/Services/NVDataMgmt.c =================================================================== diff -u -r012573b1913d1bfd2357acfadcad6bb20b295ad9 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/NVDataMgmt.c (.../NVDataMgmt.c) (revision 012573b1913d1bfd2357acfadcad6bb20b295ad9) +++ firmware/App/Services/NVDataMgmt.c (.../NVDataMgmt.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * NVDataMgmt.c - * - * Created on: Aug 7, 2024 - * Author: fw - */ #include // For memcpy and memset @@ -12,39 +6,46 @@ #include "NVDataMgmt.h" +/** + * @addtogroup NVDataMgmt + * @{ + */ + /* * TODO * 1. Clean up the flash with the bad data packets */ -#define BANK0_NUM_OF_SECTORS 16 -#define FLOAT_TO_INT_ROUNDUP_OFFSET 0.5F ///< Offset to add to a floating point value for rounding rounding when converting to integer +// ********** private definitions ********** +#define BANK0_NUM_OF_SECTORS 16 ///< Bank0 number of sectors. +#define FLOAT_TO_INT_ROUNDUP_OFFSET 0.5F ///< Offset to add to a floating point value for rounding rounding when converting to integer. #define ROUNDED_HCLK_FREQ ((HCLK_FREQ) < 0.0F ? (S32)((HCLK_FREQ) - FLOAT_TO_INT_ROUNDUP_OFFSET) : \ (S32)((HCLK_FREQ) + FLOAT_TO_INT_ROUNDUP_OFFSET)) ///< Rounded HCLK for flash clock. /// EEPROM functions use the buffer length as the size of U32. So before send the length to any of FAPI functions, it should be divided by 4. #define EEPROM_OPS_SIZE_OF_CONVERTER 4 +#define NUM_OF_BYTES_WRITE_TO_FALSH 16 ///< Number of bytes to write. +#define NUM_OF_FIRMWARE_CRC_TABLE_BYTES 1 ///< Number of firmware CRC table bytes. +#define VALUE_OF_AN_ERASED_FLASH 0xFFFFFFFF ///< Value of an erased flash. -#define NUM_OF_BYTES_WRITE_TO_FALSH 16 - -#define NUM_OF_FIRMWARE_CRC_TABLE_BYTES 1 -#define VALUE_OF_AN_ERASED_FLASH 0xFFFFFFFF - +/// Flash write status structure typedef struct Flash_Write_Status { - BOOL hasFlashBeenErased; - U32 currentWriteAddress; + BOOL hasFlashBeenErased; ///< Boolean flag to indicate flash has been erased. + U32 currentWriteAddress; ///< Current write address in the flash memory. } SW_UPDATE_FALSH_STATUS_T; +/// Bank 0 sectors status structure typedef struct Sectors { - U32 startAddress; - U32 length; // number of 32-bit words - U32 bankNumber; - U32 sectorNumber; + U32 startAddress; ///< Start address. + U32 length; // number of 32-bit words ///< Length of data (word or 4 bytes). + U32 bankNumber; ///< Bank number. + U32 sectorNumber; ///< Sector number. } BANK0_SECTORS_T; +/// Bank sectors array const BANK0_SECTORS_T bank0Sectors[ BANK0_NUM_OF_SECTORS ]= { 0x00000000, 0x04000, 0, 0, @@ -65,29 +66,58 @@ 0x00120000, 0x20000, 0, 15 }; -static SW_UPDATE_FALSH_STATUS_T SWUpdateFlashStatus; +// ********** private data ********** +static SW_UPDATE_FALSH_STATUS_T SWUpdateFlashStatus; ///< Software update flash status. +// ********** private function prototypes ********** + static BOOL eraseFlashSectors( void ); static BOOL writeFlashSectors( U08* data ); - +/*********************************************************************//** + * @brief + * The initNVDataMgmt function initializes the module. + * @details \b Inputs: none + * @details \b Outputs: initializes flash bank 0. + * @return none + *************************************************************************/ void initNVDataMgmt( void ) { + // Setup the flash bank clock Fapi_initializeFlashBanks( ROUNDED_HCLK_FREQ ); + // Activate flash bank 0 Fapi_setActiveFlashBank( Fapi_FlashBank0 ); Fapi_enableMainBankSectors( 0xFFFF ); /* used for API 2.01*/ while( FAPI_CHECK_FSM_READY_BUSY != Fapi_Status_FsmReady ); clearSWUpdateNVStatus(); } +/*********************************************************************//** + * @brief + * The clearSWUpdateNVStatus function clears the variables that are used + * in software update. + * @details \b Inputs: none + * @details \b Outputs: SWUpdateFlashStatus + * @return none + *************************************************************************/ void clearSWUpdateNVStatus( void ) { SWUpdateFlashStatus.hasFlashBeenErased = FALSE; SWUpdateFlashStatus.currentWriteAddress = FIRMWARE_START_ADDRESS; } +/*********************************************************************//** + * @brief + * The handleUpdatingFlash function handles updating the flash. If the sectors + * have not been erased first, they are erased. + * @details \b Inputs: none + * @details \b Outputs: SWUpdateFlashStatus + * @param data to write pointer to the buffer that is going to be written + * to flash + * @return TRUE if the write and erase was successful otherwise, FALSE + *************************************************************************/ BOOL handleUpdatingFlash( U08* dataToWrite ) { BOOL status = FALSE; @@ -110,85 +140,108 @@ return status; } +/*********************************************************************//** + * @brief + * The isFWCRCTableValid function checks whether the firmware CRC table is + * valid or not. This function reads a word data starting from the firmware + * start address. Then it is verified to make sure it is not 0xFFFFFFFF. + * @details \b Inputs: none + * @details \b Outputs: none + * @return TRUE if the firmware CRC is valid otherwise, FALSE + *************************************************************************/ BOOL isFWCRCTableValid( void ) { Fapi_FlashStatusWordType crcVerifyReason; U32 erasedFlashedValue[ NUM_OF_FIRMWARE_CRC_TABLE_BYTES ]; BOOL crcVerifyStatus = FALSE; + // Create a buffer of 1 byte and write 0xFFFFFFFF to it memset( erasedFlashedValue, VALUE_OF_AN_ERASED_FLASH, sizeof( erasedFlashedValue ) ); + // Verify the value is not 0xFFFFFFFF reading from the firmware start address crcVerifyStatus = Fapi_doVerify( (U32*)FIRMWARE_CRC_TABLE_ADDRESS, NUM_OF_FIRMWARE_CRC_TABLE_BYTES, (U32*)&erasedFlashedValue, &crcVerifyReason ); + // Wait for the FAPI respond while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); // TODO timeout or count so we wont get stuck here for ever + // Check if the value of the provided buffer is the same as the what was found in the firmware start address crcVerifyStatus = ( Fapi_Status_Success == crcVerifyStatus ? FALSE : TRUE ); return crcVerifyStatus; } // ********** private functions ********** +/*********************************************************************//** + * @brief + * The eraseFlashSectors function erases the flash sectors. It starts from + * the sectors of the firmware start address and erases until the end of bank 0. + * @details \b Inputs: none + * @details \b Outputs: none + * @return TRUE if the erase was successful otherwise, FALSE + *************************************************************************/ static BOOL eraseFlashSectors( void ) { U08 i; - BOOL status = FALSE; + BOOL status = FALSE; - for ( i = 0; i < BANK0_NUM_OF_SECTORS; i++ ) - { - if ( bank0Sectors[ i ].startAddress >= FIRMWARE_START_ADDRESS ) - { - Fapi_issueAsyncCommandWithAddress( Fapi_EraseSector, (U32*)bank0Sectors[ i ].startAddress ); - while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); - while(FAPI_GET_FSM_STATUS != Fapi_Status_Success); - status |= TRUE; - } - } + for ( i = 0; i < BANK0_NUM_OF_SECTORS; i++ ) + { + if ( bank0Sectors[ i ].startAddress >= FIRMWARE_START_ADDRESS ) + { + Fapi_issueAsyncCommandWithAddress( Fapi_EraseSector, (U32*)bank0Sectors[ i ].startAddress ); + while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); + while(FAPI_GET_FSM_STATUS != Fapi_Status_Success); + status |= TRUE; + } + } - // TODO check the erased sectors + // TODO check the erased sectors - return status; + return status; } +/*********************************************************************//** + * @brief + * The writeFlashSectors function writes to a sector of the flash. + * @details \b Inputs: SWUpdateFlashStatus + * @details \b Outputs: none + * @return TRUE if the write was successful otherwise, FALSE + *************************************************************************/ static BOOL writeFlashSectors( U08* data ) { Fapi_FlashStatusWordType writeVerifyReason; Fapi_StatusType writeVerifyStatus; - U08 removeThis; U08 dataRead2Verify[ SW_UPDATE_FLASH_BUFFER_SIZE ]; BOOL status = FALSE; U08 bytesWritten = 0; U32 startAddress = SWUpdateFlashStatus.currentWriteAddress; - //for ( removeThis = 0; removeThis < SW_UPDATE_FLASH_BUFFER_SIZE; removeThis++ ) - //{ - // TODO this is temporary until the ROTTING is removed from the APP - // data[ removeThis ] = 0xFF & ( data[removeThis] - 27 ); - //} - memcpy( dataRead2Verify, data, SW_UPDATE_FLASH_BUFFER_SIZE ); + // Keep writing until the buffer is finished while ( bytesWritten < SW_UPDATE_FLASH_BUFFER_SIZE ) { Fapi_issueProgrammingCommand( (U32*)SWUpdateFlashStatus.currentWriteAddress, data, NUM_OF_BYTES_WRITE_TO_FALSH, 0x00, 0, Fapi_DataOnly ); while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); + // Update the write pointer. Update the current write address in the flash data += NUM_OF_BYTES_WRITE_TO_FALSH; SWUpdateFlashStatus.currentWriteAddress += NUM_OF_BYTES_WRITE_TO_FALSH; bytesWritten += NUM_OF_BYTES_WRITE_TO_FALSH; } writeVerifyStatus = Fapi_doVerify( (U32*)startAddress, ( SW_UPDATE_FLASH_BUFFER_SIZE / SW_UPDATE_FLASH_BUFFER_SIZE ), (U32*)&dataRead2Verify, &writeVerifyReason ); - while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); // TODO timeout or count so we wont get stuck here for ever + while( FAPI_CHECK_FSM_READY_BUSY == Fapi_Status_FsmBusy ); // TODO timeout or count so we wont get stuck here forever status = ( Fapi_Status_Success == writeVerifyStatus ? TRUE : FALSE ); return status; } +/**@}*/ - Index: firmware/App/Services/NVDataMgmt.h =================================================================== diff -u -r84f337383202622f14cd6148e26bab8f68333847 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/NVDataMgmt.h (.../NVDataMgmt.h) (revision 84f337383202622f14cd6148e26bab8f68333847) +++ firmware/App/Services/NVDataMgmt.h (.../NVDataMgmt.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,22 @@ -/* - * NVDataMgmt.h - * - * Created on: Aug 7, 2024 - * Author: fw - */ #ifndef __NVDATAMGMT_H__ #define __NVDATAMGMT_H__ #include "BLCommon.h" +/** + * @defgroup NVDataMgmt NVDataMgmt + * @brief Non-volatile data management module. Handles Bank 7 of the TI processor and the + * RAM of the RTC chip. + * + * @addtogroup NVDataMgmt + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initNVDataMgmt( void ); void clearSWUpdateNVStatus( void ); @@ -18,4 +25,6 @@ BOOL isFWCRCTableValid( void ); +/**@}*/ + #endif Index: firmware/App/Services/SystemComm.c =================================================================== diff -u -re8511af1e4e9d91cfd3378471869fb0246110870 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/SystemComm.c (.../SystemComm.c) (revision e8511af1e4e9d91cfd3378471869fb0246110870) +++ firmware/App/Services/SystemComm.c (.../SystemComm.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,21 +1,40 @@ -/* - * SysComm.c - * - * Created on: Aug 20, 2024 - * Author: fw - */ #include "can.h" #include "CommBuffers.h" #include "SystemComm.h" +/** + * @addtogroup SystemComm + * @{ + */ +// ********** private definitions ********** + +/*********************************************************************//** + * @brief + * The initSystemComm function initializes the SystemComm unit. + * @details \b Inputs: none + * @details \b Outputs: SystemComm unit variables initialized. + * @return none + *************************************************************************/ void initSystemComm( void ) { } +/*********************************************************************//** + * @brief + * The handleCANMsgInterrupt function handles a CAN frame interrupt from + * a given CAN mail box. + * This may have occurred because a CAN frame transmission has completed + * or because a CAN frame has been received. The appropriate handler is + * called. + * @details \b Inputs: none + * @details \b Outputs: message interrupt handled + * @param mailbox which CAN mail box triggered this interrupt + * @return none + *************************************************************************/ void handleCANMsgInterrupt( SW_UPDATE_CAN_MAIL_BOX_T mailBox ) { // TODO do we need check the range of the messages? @@ -52,6 +71,15 @@ } } +/*********************************************************************//** + * @brief + * The sendAckNackStatusFromFirmware function sends the ack or nack status + * of a received message. + * @details \b Inputs: none + * @details \b Outputs: none + * @param data pointer to the data to be sent + * @return TRUE if the CAN transmit was successful otherwise, FALSE + *************************************************************************/ BOOL sendAckNackStatusFromFirmware( U08* data ) { BOOL status = FALSE; @@ -64,10 +92,12 @@ return status; } -BOOL broadcastDataTestRemove( U08* data ) +BOOL broadcastDataTestRemove( U08* data ) // TODO remove { canTransmit( canREG1, (U32)SW_TEST, data ); return TRUE; } +/**@}*/ + Index: firmware/App/Services/SystemComm.h =================================================================== diff -u -re8511af1e4e9d91cfd3378471869fb0246110870 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/SystemComm.h (.../SystemComm.h) (revision e8511af1e4e9d91cfd3378471869fb0246110870) +++ firmware/App/Services/SystemComm.h (.../SystemComm.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,21 @@ -/* - * SysComm.h - * - * Created on: Aug 20, 2024 - * Author: fw - */ #ifndef __SYSCOMM_H__ #define __SYSCOMM_H__ #include "BLCommon.h" +/** + * @defgroup SystemComm SystemComm + * @brief System communication unit. Manages incoming and outgoing CAN frames. + * + * @addtogroup SystemComm + * @{ + */ + +// ********** public definitions ********** + +// ********** public function prototypes ********** + void initSystemComm( void ); void handleCANMsgInterrupt( SW_UPDATE_CAN_MAIL_BOX_T mailBox ); @@ -18,4 +24,6 @@ BOOL broadcastDataTestRemove( U08* data ); +/**@}*/ + #endif Index: firmware/App/Services/Timers.c =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Timers.c (.../Timers.c) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Services/Timers.c (.../Timers.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,12 +1,10 @@ -/* - * Timers.c - * - * Created on: Aug 1, 2024 - * Author: fw - */ #include "Timers.h" +/** + * @addtogroup Timers + * @{ + */ // ********** private definitions ********** @@ -16,9 +14,9 @@ /*********************************************************************//** * @brief - * The initTimers function initializes the Timers module. - * @details Inputs: msTimerCount - * @details Outputs: msTimerCount + * The initTimers function initializes the Timers unit. + * @details \b Inputs: none + * @details \b Outputs: msTimerCount * @return none *************************************************************************/ void initTimers( void ) @@ -29,8 +27,8 @@ /*********************************************************************//** * @brief * The incMSTimerCount function increments the ms timer count. - * @details Inputs: msTimerCount - * @details Outputs: msTimerCount + * @details \b Inputs: msTimerCount + * @details \b Outputs: msTimerCount * @return none *************************************************************************/ void incMSTimerCount( void ) @@ -41,9 +39,9 @@ /*********************************************************************//** * @brief * The getMSTimerCount function returns the current ms timer count. - * @details Inputs: msTimerCount - * @details Outputs: none - * @return msTimerCount as a U32 + * @details \b Inputs: msTimerCount + * @details \b Outputs: none + * @return The current 32-bit millisecond timer count. *************************************************************************/ U32 getMSTimerCount( void ) { @@ -54,8 +52,8 @@ * @brief * The didTimeout function determines whether a timeout has occurred between * a given start count and a given timeout period (in ms). - * @details Inputs: msTimerCount - * @details Outputs: none + * @details \b Inputs: msTimerCount + * @details \b Outputs: none * @param startMSCount the ms count at the start of the timeout period * @param timeoutPeriod the period for the timeout (in ms) * @return TRUE if a timeout has occurred, FALSE if not @@ -87,6 +85,4 @@ return result; } - - - +/**@}*/ Index: firmware/App/Services/Timers.h =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Timers.h (.../Timers.h) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Services/Timers.h (.../Timers.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,18 +1,25 @@ -/* - * Timers.h - * - * Created on: Aug 1, 2024 - * Author: fw - */ #ifndef __TIMERS_H__ #define __TIMERS_H__ #include "BLCommon.h" +/** + * @defgroup Timers Timers + * @brief Timers service unit. Provides timer utility functions based on + * a 1ms timer counter incremented by TaskTimer.c. + * + * @addtogroup Timers + * @{ + */ + +// ********** public function prototypes ********** + void initTimers( void ); void incMSTimerCount( void ); U32 getMSTimerCount( void ); BOOL didTimeout( U32 startMSCount, U32 timeoutPeriod ); +/**@}*/ + #endif Index: firmware/App/Services/Utilities.c =================================================================== diff -u -rb8160225a28a2ba4d6dff4d0433e55465c737a14 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Utilities.c (.../Utilities.c) (revision b8160225a28a2ba4d6dff4d0433e55465c737a14) +++ firmware/App/Services/Utilities.c (.../Utilities.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,9 +1,3 @@ -/* - * Utilities.c - * - * Created on: Aug 4, 2024 - * Author: fw - */ #ifndef _VECTORCAST_ // This header file is disabled in VectorCAST because this is a TI library and VectorCAST uses GNU 7.4 compiler for testing @@ -12,10 +6,18 @@ #include "Utilities.h" -#define INITIAL_CRC16_VAL 0xFFFF ///< Seed for 16-bit CRC function. -#define SHIFT_24_BITS 24 ///< Number of bits to shift in order to shift 3 bytes +/** + * @addtogroup Utilities + * @{ + */ +// ********** private definitions ********** +#define INITIAL_CRC16_VAL 0xFFFF ///< Seed for 16-bit CRC function. +#define SHIFT_24_BITS 24 ///< Number of bits to shift in order to shift 3 bytes. + +// ********** private data ********** + /// CRC-32 look-up table. const U32 CRC32_TABLE[] = { @@ -90,7 +92,15 @@ 0x6e17, 0x7e36, 0x4e55, 0x5e74, 0x2e93, 0x3eb2, 0x0ed1, 0x1ef0 }; - +/*********************************************************************//** + * @brief + * The runFWIntegrityTest function runs the firmware integrity test on the + * firmware that is in the flash. It returns whether the integrity passed or + * failed. + * @details \b Inputs: none + * @details \b Outputs: none + * @return TRUE if integrity test passed otherwise, FALSE + *************************************************************************/ BOOL runFWIntegrityTest( void ) { U32 remainingSize = 0; @@ -100,7 +110,7 @@ CRC_TABLE const * const crcTablePtr = (CRC_TABLE *)FIRMWARE_CRC_TABLE_ADDRESS; CRC_RECORD const * currentRecordPtr = &crcTablePtr->recs[ currentRecord ]; - BOOL integrityStatus = TRUE; + BOOL integrityStatus = TRUE; do { @@ -131,31 +141,52 @@ return integrityStatus; } -U16 crc16( U08 *address, U32 len ) +/*********************************************************************//** + * @brief + * The crc32 function calculates a 32-bit CRC for a given range of bytes + * in memory. Poly = 0x1EDC6F41. Not reflected. Initial value = 0x00000000. + * @details \b Inputs: CRC32_TABLE[] + * @details \b Outputs: none + * @param initialValue initial CRC seed value + * @param address pointer to start address of memory range to calculate CRC for + * @param len number of bytes in the memory range to calculate CRC for + * @return 32-bit CRC + *************************************************************************/ +U32 crc32( U32 initialValue, U08 *address, U32 len ) { - U16 crc = INITIAL_CRC16_VAL; + U32 crc = initialValue; while ( len-- > 0 ) { - crc = ( crc << SHIFT_8_BITS_FOR_BYTE_SHIFT ) ^ CRC16_TABLE[ *address ^ ( ( crc >> SHIFT_8_BITS_FOR_BYTE_SHIFT ) & MASK_OFF_MSB ) ]; + crc = ( crc << SHIFT_8_BITS_FOR_BYTE_SHIFT ) ^ CRC32_TABLE[ *address ^ ( crc >> SHIFT_24_BITS ) ]; address++; } return crc; } -U32 crc32( U32 initialValue, U08 *address, U32 len ) +/*********************************************************************//** + * @brief + * The crc16 function calculates a 16-bit CRC for a given range of bytes + * in memory. Poly = 0x1021. Not reflected. Initial value = 0xFFFF. + * @details \b Inputs: CRC16_TABLE[] + * @details \b Outputs: none + * @param address pointer to start address of memory range to calculate CRC for + * @param len number of bytes in the memory range to calculate CRC for + * @return 16-bit CRC + *************************************************************************/ +U16 crc16( U08 *address, U32 len ) { - U32 crc = initialValue; + U16 crc = INITIAL_CRC16_VAL; while ( len-- > 0 ) { - crc = ( crc << SHIFT_8_BITS_FOR_BYTE_SHIFT ) ^ CRC32_TABLE[ *address ^ ( crc >> SHIFT_24_BITS ) ]; + crc = ( crc << SHIFT_8_BITS_FOR_BYTE_SHIFT ) ^ CRC16_TABLE[ *address ^ ( ( crc >> SHIFT_8_BITS_FOR_BYTE_SHIFT ) & MASK_OFF_MSB ) ]; address++; } return crc; } +/**@}*/ - Index: firmware/App/Services/Utilities.h =================================================================== diff -u -rf100557efc2f7916054a63bbafb187d8017914d0 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Services/Utilities.h (.../Utilities.h) (revision f100557efc2f7916054a63bbafb187d8017914d0) +++ firmware/App/Services/Utilities.h (.../Utilities.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,23 +1,29 @@ -/* - * Utilities.h - * - * Created on: Aug 4, 2024 - * Author: fw - */ #ifndef __UTILITIES_H__ #define __UTILITIES_H__ #include "BLCommon.h" +/** + * @defgroup Utilities Utilities + * @brief Utilities unit contains various utility functions. + * + * @addtogroup Utilities + * @{ + */ + +// ********** public definitions ********** + #define MAX_CRC_CALC_DATA_SIZE 0x8000 ///< The maximum size of data for each CRC calculation. +// ********** public function prototypes ********** + BOOL runFWIntegrityTest( void ); -U16 crc16( U08 *address, U32 len ); - U32 crc32( U32 initialValue, U08 *address, U32 len ); +U16 crc16( U08 *address, U32 len ); +/**@}*/ #endif Index: firmware/App/Tasks/TaskBG.c =================================================================== diff -u -r893caf9f58a08a2bd31068806e09603041d64add -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskBG.c (.../TaskBG.c) (revision 893caf9f58a08a2bd31068806e09603041d64add) +++ firmware/App/Tasks/TaskBG.c (.../TaskBG.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,13 +1,23 @@ -/* - * TaskBG.c - * - * Created on: Jul 31, 2024 - * Author: fw - */ #include "Download.h" #include "TaskBG.h" +/** + * @addtogroup TaskBackground + * @{ + */ + +// ********** private definitions ********** + +// ********** private data ********** + +/*********************************************************************//** + * @brief + * The taskBackground function handles the idle Background Task loop. + * @details \b Inputs: none + * @details \b Outputs: Background task functions are called. + * @return none + *************************************************************************/ void taskBackground( void ) { #ifndef _VECTORCAST_ // Cannot have infinite loop in unit test tool @@ -18,3 +28,4 @@ } } +/**@}*/ Index: firmware/App/Tasks/TaskBG.h =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskBG.h (.../TaskBG.h) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Tasks/TaskBG.h (.../TaskBG.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,13 +1,22 @@ -/* - * TaskBG.h - * - * Created on: Jul 31, 2024 - * Author: fw - */ #ifndef __TASKBG_H__ #define __TASKBG_H__ +/** + * @defgroup TaskBackground TaskBackground + * @brief The background task is an infinite loop running in the background + * called by main() after initialization. The background task executes + * functions that may take a long time to complete or are very low priority. + * This includes non-volatile memory operations and watchdog management. + * + * @addtogroup TaskBackground + * @{ + */ + +// Public function prototypes + void taskBackground( void ); +/**@}*/ + #endif Index: firmware/App/Tasks/TaskGeneral.c =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskGeneral.c (.../TaskGeneral.c) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Tasks/TaskGeneral.c (.../TaskGeneral.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,27 @@ -/* - * TaskGeneral.c - * - * Created on: Jul 31, 2024 - * Author: fw - */ #include "BLCommon.h" #include "OperationModes.h" #include "TaskGeneral.h" +/** + * @addtogroup TaskGeneral + * @{ + */ + +// ********** private data ********** + +/*********************************************************************//** + * @brief + * The taskGeneral function handles the scheduled General Task interrupt. + * Calls the executive functions for most monitors and controllers, the + * operation modes. + * @details \b Inputs: none + * @details \b Outputs: Executive functions running in general task are called. + * @return none + *************************************************************************/ void taskGeneral( void ) { execOperationModes(); } + +/**@}*/ Index: firmware/App/Tasks/TaskGeneral.h =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskGeneral.h (.../TaskGeneral.h) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Tasks/TaskGeneral.h (.../TaskGeneral.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,16 +1,22 @@ -/* - * TaskGeneral.h - * - * Created on: Jul 31, 2024 - * Author: fw - */ #ifndef __TASKGENERAL_H__ #define __TASKGENERAL_H__ -#define TASK_GENERAL_INTERVAL 50 +/** + * @defgroup TaskGeneral TaskGeneral + * @brief The general task is called by RTI interrupt every 50 ms and performs + * the bulk of sensor, actuator, mode, alarm, and communication operations. + * + * @addtogroup TaskGeneral + * @{ + */ +// Public definitions + +// Public function prototypes + void taskGeneral( void ); +/**@}*/ #endif Index: firmware/App/Tasks/TaskPriority.c =================================================================== diff -u -rf100557efc2f7916054a63bbafb187d8017914d0 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskPriority.c (.../TaskPriority.c) (revision f100557efc2f7916054a63bbafb187d8017914d0) +++ firmware/App/Tasks/TaskPriority.c (.../TaskPriority.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,17 +1,27 @@ -/* - * TaskPriority.c - * - * Created on: Jul 31, 2024 - * Author: fw - */ #include "BLCommon.h" #include "CommBuffers.h" #include "FPGA.h" #include "TaskPriority.h" +/** + * @addtogroup TaskPriority + * @{ + */ + +// ********** private data ********** + +/*********************************************************************//** + * @brief + * The taskPriority function handles the scheduled Priority Task interrupt. + * Calls the executive functions for FPGA. + * @details \b Inputs: none + * @details \b Outputs: Executive functions running in priority task are called. + * @return none + *************************************************************************/ void taskPriority( void ) { execFPGA(); } +/**@}*/ Index: firmware/App/Tasks/TaskPriority.h =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskPriority.h (.../TaskPriority.h) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Tasks/TaskPriority.h (.../TaskPriority.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,23 @@ -/* - * TaskPriority.h - * - * Created on: Jul 31, 2024 - * Author: fw - */ #ifndef __TASKPRIORITY_H__ #define __TASKPRIORITY_H__ -#define TASK_PRIORITY_INTERVAL 10 +/** + * @defgroup TaskPriority TaskPriority + * @brief The priority task is called by RTI interrupt every 10 ms and performs + * high priority and/or urgent sensor/actuator processing as well as the + * interface to the FPGA. + * + * @addtogroup TaskPriority + * @{ + */ +// Public definitions + +// Public function prototypes + void taskPriority( void ); +/**@}*/ + #endif Index: firmware/App/Tasks/TaskTimer.c =================================================================== diff -u -r9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskTimer.c (.../TaskTimer.c) (revision 9af6fc3e5afc442a877bd5e23ecfa6872a3ad5a4) +++ firmware/App/Tasks/TaskTimer.c (.../TaskTimer.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,17 +1,29 @@ -/* - * TaskTimer.c - * - * Created on: Jul 31, 2024 - * Author: fw - */ #include "BLCommon.h" #include "TaskTimer.h" #include "Timers.h" +/** + * @addtogroup TaskTimer + * @{ + */ + +// ********** private data ********** + +/*********************************************************************//** + * @brief + * The taskTimer function handles the scheduled Timer Task interrupt. + * Calls the Timers executive to maintain a 1ms timer counter to + * support timer and timeout functions. + * @details \b Inputs: none + * @details \b Outputs: Executive function for Timers is called. + * @return none + *************************************************************************/ void taskTimer( void ) { incMSTimerCount(); + + // TODo add watchdog } - +/**@}*/ Index: firmware/App/Tasks/TaskTimer.h =================================================================== diff -u -rabb9687e52d9db5df1abe7626ba04a6d431ba823 -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/App/Tasks/TaskTimer.h (.../TaskTimer.h) (revision abb9687e52d9db5df1abe7626ba04a6d431ba823) +++ firmware/App/Tasks/TaskTimer.h (.../TaskTimer.h) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -1,15 +1,22 @@ -/* - * TaskTimer.h - * - * Created on: Jul 31, 2024 - * Author: fw - */ #ifndef __TASKTIMER_H__ #define __TASKTIMER_H__ -#define TASK_TIMER_INTERVAL 1 +/** + * @defgroup TaskTimer TaskTimer + * @brief Timer task is called by RTI interrupt every 1 ms to update the + * millisecond timer counter. + * + * @addtogroup TaskTimer + * @{ + */ +// Public definitions + +// Public function prototypes + void taskTimer( void ); +/**@}*/ + #endif Index: firmware/source/sys_main.c =================================================================== diff -u -r893caf9f58a08a2bd31068806e09603041d64add -rc74c1d99a011dd0fb7f98f183faecda675221fce --- firmware/source/sys_main.c (.../sys_main.c) (revision 893caf9f58a08a2bd31068806e09603041d64add) +++ firmware/source/sys_main.c (.../sys_main.c) (revision c74c1d99a011dd0fb7f98f183faecda675221fce) @@ -43,9 +43,6 @@ /* USER CODE BEGIN (0) */ -static void initProcessor( void ); -static void initSoftware( void ); -static void initTasks( void ); /* USER CODE END */ /* Include Files */ @@ -80,6 +77,9 @@ */ /* USER CODE BEGIN (2) */ +static void initProcessor( void ); +static void initSoftware( void ); +static void initTasks( void ); /* USER CODE END */ int main(void) @@ -97,13 +97,30 @@ /* USER CODE BEGIN (4) */ + +/************************************************************************* + * @brief initProcessor + * The initProcessor function initializes and configures the processor \n + * peripherals. + * @details Inputs: none + * @details Outputs: Processor peripherals initialized and configured. + * @return none + *************************************************************************/ static void initProcessor( void ) { canInit(); sciInit(); dmaEnable(); } +/************************************************************************* + * @brief initSoftware + * The initSoftware function calls all software unit initialization functions + * to initialize and configure the TD application. + * @details Inputs: none + * @details Outputs: All software units initialized. + * @return none + *************************************************************************/ static void initSoftware( void ) { initCommBuffers(); @@ -116,6 +133,13 @@ initTimers(); } +/************************************************************************* + * @brief initTasks + * The initTasks function sets up and starts the scheduled tasks. + * @details Inputs: none + * @details Outputs: Scheduled tasks set up and started. + * @return none + *************************************************************************/ static void initTasks( void ) { // Initialize RTI to setup the 3 tasks