/** @brief Definition of types to aid manipulation of watchdog registers.
 *
 * @copyright 2020 Remsdaq Ltd.
 *
 * @file c4_watchdog_types.h
 *
 *  @date: 27 Jul 2020
 *  @author: Dan Smithers <dwhs@remsdaq.com>
 */



#ifndef C4_WATCHDOG_TYPES_H_
#define C4_WATCHDOG_TYPES_H_


/*******************************************************************************
 * Includes
 ******************************************************************************/
#include <stdint.h>

/*******************************************************************************
 * Defines
 ******************************************************************************/

/*******************************************************************************
 * Structures
 ******************************************************************************/

/** @brief Structure to overlay on the watchdog registers.
 *
 * The structure allows access either as whole word registers (.R) or
 * using bitfield structures (.B.xxx).
 */
typedef struct
{
    /** @brief The Watchdog Control Register (WDOG_WCR) controls the WDOG operation.
     *
     * @li WDZST, WDBG and WDW are write-once only bits. Once the software does a write
     * access to these bits, they will be locked and cannot be reprogrammed until the next
     * system reset assertion.
     * @li WDE is a write one once only bit. Once software performs a write "1" operation to
     * this bit it cannot be reset/cleared until the next system reset.
     * @li WDT is also a write one once only bit. Once software performs a write "1" operation
     * to this bit it cannot be reset/cleared until the next POR. This bit does not get reset/
     * cleared due to any system reset.
     */
    union
    {
        struct
        {
            uint16_t WDZST:1; /**< @brief Watchdog Low Power.
            *
            * Determines the operation of the WDOG during low-power modes. This bit is write
            * once-only.
            * @note The WDOG can continue/suspend the timer operation in the low-power modes (STOP and
            * DOZE mode).
            *
            * - 0b - Continue timer operation (Default).
            * - 1b - Suspend the watchdog timer.
            */
            uint16_t WDBG :1; /**< @brief Watchdog DEBUG Enable.
            *
            * Determines the operation of the WDOG during DEBUG mode. This bit is write
            * once only.
            *
            * - 0b - Continue WDOG timer operation (Default).
            * - 1b - Suspend the watchdog timer.
            */
            uint16_t WDE  :1; /**< @brief Watchdog Enable.
            *
            * Enables or disables the WDOG block. This is a write one once only bit. It is not
            * possible to clear this bit by a software write, once the bit is set.
            * @note This bit can be set/reset in debug mode (exception).
            *
            * - 0b - Disable the Watchdog (Default).
            * - 1b - Enable the Watchdog.
            */
            uint16_t WDT  :1; /**< @brief WDOG_B Time-out assertion
            *
            * Determines if the WDOG_B gets asserted upon a Watchdog Time-out
            * Event. This is a write-one once only bit.
            *
            * @note There is no effect on WDOG_RESET_B_DEB (WDOG Reset) upon writing on this bit. WDOG_B
            * gets asserted along with WDOG_RESET_B_DEB if this bit is set.
            *
            * - 0b - No effect on WDOG_B (Default).
            * - 1b - Assert WDOG_B upon a Watchdog Time-out event.
            */
            uint16_t SRS  :1; /**< @brief Software Reset Signal.
            *
            * Controls the software assertion of the WDOG-generated reset signal
            * WDOG_RESET_B_DEB . This bit automatically resets to "1" after it has been asserted to "0".
            *
            * @note This bit does not generate the software reset to the block.
            *
            * - 0b - Assert system reset signal.
            * - 1b - No effect on the system (Default).
            */
            uint16_t WDA  :1; /**< @brief WDOG_B assertion.
            *
            * Controls the software assertion of the WDOG_B signal.
            *
            * - 0b - Assert WDOG_B output.
            * - 1b - No effect on system (Default).
            */
            uint16_t SRE  :1; /**< @brief Software reset extension.
            *
            * An option way to generate software reset
            * adopt a new way to generate a more robust software reset. This bit can be set/clear with IP bus and will
            * be reset with power-on reset .
            *
            * - 0b - using original way to generate software reset (default)
            * - 1b - using new way to generate software reset.
            */
            uint16_t WDW  :1; /**< @brief Watchdog Disable for Wait.
            *
            * This bit determines the operation of WDOG during Low Power WAIT mode.
            * This is a write once only bit.
            *
            * - 0b - Continue WDOG timer operation (Default).
            * - 1b - Suspend WDOG timer operation.
            */
            uint16_t WT   :8; /**< @brief Watchdog Time-out Field.
            *
            * This 8-bit field contains the time-out value that is loaded into the Watchdog
            * counter after the service routine has been performed or after the Watchdog is enabled. After reset,
            * WT[7:0] must have a value written to it before enabling the Watchdog otherwise count value of zero
            * which is 0.5 seconds is loaded into the counter.
            *
            * @note: The time-out value can be written at any point of time but it is loaded to the counter at the time
            * when WDOG is enabled or after the service routine has been performed. For more information
            * see Timeout event.
            *
            * - 00000000b - 0.5 Seconds (Default).
            * - 00000001b - 1.0 Seconds.
            * - 00000010b - 1.5 Seconds.
            * - 00000011b - 2.0 Seconds.
            * -
            * - 11111111b - 128 Seconds.
            * */
        } B; /**< Bitfield representation. */
        uint16_t R; /**< Register representation. */
    } WCR;
    /** @brief Watchdog Service
     *
     * When enabled, the WDOG requires that a service sequence be written to the Watchdog
     * Service Register (WSR) to prevent the timeout condition.
     * @note Executing the service sequence will reload the WDOG timeout
     * counter.
     */
    union
    {
        struct
        {
            uint16_t WSR; /** @brief Watchdog Service Register.
             *
             * This 16-bit field contains the Watchdog service sequence. Both writes must
             * occur in the order listed prior to the time-out, but any number of instructions can be executed between the
             * two writes. The service sequence must be performed as follows:
             *
             * - 0101010101010101b - Write to the Watchdog Service Register (WDOG_WSR).
             * - 1010101010101010b - Write to the Watchdog Service Register (WDOG_WSR).
             */
        } B; /**< Bitfield representation. */
        uint16_t R; /**< Register representation. */
    } WSR;
    /** @brief Watchdog Reset Status
     *
     * The WRSR is a read-only register that records the source of the output reset assertion. It
     * is not cleared by a hard reset. Therefore, only one bit in the WRSR will always be
     * asserted high. The register will always indicate the source of the last reset generated due
     * to WDOG. Read access to this register is with one wait state. Any write performed on
     * this register will generate a Peripheral Bus Error .
     *
     * A reset can be generated by the following sources, as listed in priority from highest to
     * lowest:
     * - Watchdog Time-out
     * - Software Reset
     */
    union
    {
        struct
        {
            uint16_t SFTW:1; /**< @brief Software Reset.
            *
            * Indicates whether the reset is the result of a WDOG software reset by asserting SRS bit
            *
            * - 0b - Reset is not the result of a software reset.
            * - 1b - Reset is the result of a software reset.
            */
            uint16_t TOUT:1; /**< @brief TOUT
            *
            * Timeout. Indicates whether the reset is the result of a WDOG timeout.
            *
            * - 0b - Reset is not the result of a WDOG timeout.
            * - 1b - Reset is the result of a WDOG timeout.
            */
            uint16_t rsvd1:2; /**< @brief reserved             */
            uint16_t POR   :1; /**< @brief Power On Reset.
            *  Indicates whether the reset is the result of a power on reset.
            *  - 0b - Reset is not the result of a power on reset.
            *  - 1b - Reset is the result of a power on reset.
            */
            uint16_t rsvd2:11; /**< @brief reserved            */
        } B; /**< Bitfield representation. */
        uint16_t R; /**< Register representation. */
    } WRSR;
    /** @brief Watchdog Interrupt Control
     *
     * The WDOG_WICR controls the WDOG interrupt generation.
     */
    union c4_WDOG_wicr
    {
        struct
        {
            uint16_t WICT:8; /**< @brief Watchdog Interrupt Count Time-out field
            * This determines how long before the counter time-out must
            * the interrupt occur. The reset value is 0x04 implies interrupt will occur 2 seconds before time-out. The
            * maximum value that can be programmed to WICT field is 127.5 seconds with a resolution of 0.5 seconds.
            *
            * @note This field is write once only. Once the software does a write access to this field, it will get locked
            * and cannot be reprogrammed until the next system reset assertion.
            *
            * - 00000000b - WICT[7:0] = Time duration between interrupt and time-out is 0 seconds.
            * - 00000001b - WICT[7:0] = Time duration between interrupt and time-out is 0.5 seconds.
            * - 00000100b - WICT[7:0] = Time duration between interrupt and time-out is 2 seconds (Default).
            * -
            * - 11111111b - WICT[7:0] = Time duration between interrupt and time-out is 127.5 seconds.
            */
            uint16_t resvd:6; /**< @brief reserved */
            uint16_t WTIS:1; /**< @brief Watchdog TImer Interrupt Status bit.
            *
            * This will reflect the timer interrupt status, whether interrupt has occurred
            * or not. Once the interrupt has been triggered software must clear this bit by writing 1 to it.
            *
            * - 0b - No interrupt has occurred (Default).
            * - 1b - Interrupt has occurred
            */
            uint16_t WIE :1; /**< @brief Watchdog Timer Interrupt enable bit.
            *
            * Reset value is 0.
            * @note This bit is a write once only bit. Once the software does a write access to this bit, it will get
            * locked and cannot be reprogrammed until the next system reset assertion
            *
            * - 0b - Disable Interrupt (Default).
            * - 1b - Enable Interrupt.
            */
        } B; /**< Bitfield representation. */
        uint16_t R; /**< Register representation. */
    } WICR;
    /** @brief Watchdog Miscellaneous Control
     *
     * WDOG_WMCR Controls the Power Down counter operation.
     */
    union
    {
        struct
        {
            uint16_t PDE  :1; /**< @brief Power Down Enable bit.
            *
            * Reset value of this bit is 1, which means the power down counter inside the
            * WDOG is enabled after reset. The software must write 0 to this bit to disable the counter within 16
            * seconds of reset de-assertion. Once disabled this counter cannot be enabled again. See Power-down
            * counter event for operation of this counter.
            *
            * @note This bit is write-one once only bit. Once software sets this bit it cannot be reset until the next
            * system reset.
            *
            * - 0b - Power Down Counter of WDOG is disabled.
            * - 1b - Power Down Counter of WDOG is enabled (Default).
            */
            uint16_t resvd:15; /**< reserved. */
        } B; /**< Bitfield representation. */
        uint16_t R; /**< Register representation. */
    } WMCR;

} c4_WDOG_reg_t;

/** @brief System Reset Controller (SRC)
 *
 * This uses bitfield structures to represent the register elements and is overlaid
 * on the memory-mapped registers. It is equivalent to the @see WDOG_Type defined in FreeRTOS
 * which uses shift and mask macros. */
typedef struct
{
	 /** @brief SRC Control Register (SRC_SCR)
	  *
	  * The Reset control register (SCR), contains bits that control operation of the reset
	  * controller. */
   union
   {
	   struct
	   {
		   uint32_t rsvd_0       : 7; /**< Reserved*/
		   uint32_t maskWdogRst  : 4; /**< @brief Mask wdog_rst_b source.
		                               *
		                               * If these 4 bits are coded from A to 5 then, the wdog_rst_b input to SRC will be
									   * masked and the wdog_rst_b will not create a reset to the chip.
									   *
									   * @note During the time the WDOG event is masked using SRC logic, it is likely that the WDOG Reset
									   * Status Register (WRSR) bit 1 (which indicates a WDOG timeout event) will get asserted.
									   * software / OS developer must prepare for this case. Re-enabling the WDOG is possible, by unmasking
									   * it in SRC, though it must be preceded by servicing the WDOG. However, for the case
									   * that the event has been asserted, the status bit (WRSR bit-1) will remain asserted, regardless of
									   * servicing the WDOG module.
									   *
									   * (Hardware reset is the only way to cause the de-assertion of that bit).
									   *
									   * any other code will be coded to 1010 i.e. wdog_rst_b is not masked
									   * - 0101 wdog_rst_b is masked
									   * - 1010 wdog_rst_b is not masked (default) */
		   uint32_t rsvd_1       : 2; /**< Reserved */
		   uint32_t core0Rst     : 1; /**< @brief Software reset for core0 only.
		                               *
		                               * @note: This is a self clearing bit. Once it is set to 1, the reset process will begin, and once it finishes, this
		                               * bit will be self cleared.
		                               *
		                               * - 0 do not assert core0 reset
		                               * - 1 assert core0 reset*/
		   uint32_t rsvd_2       : 3; /**< This read-only field is reserved and always has the value 0. */
		   uint32_t core0DbgRst  : 1; /**< @brief Software reset for core0 debug only.
		                               *
		                               * @note This is a self clearing bit. Once it is set to 1, the reset process will begin, and once it finishes, this
		                               * bit will be self cleared.
		                               *
		                               * - 0 do not assert core0 debug reset
		                               * - 1 assert core0 debug reset*/
		   uint32_t rsvd_3       : 7; /**< Reserved*/
		   uint32_t dbgRstMskPg  : 1; /**< @brief Do not assert debug resets after power gating event of core
		                               *
		                               * - 0 do not mask core debug resets (debug resets will be asserted after power gating event)
		                               * - 1 mask core debug resets (debug resets won't be asserted after power gating event)*/
		   uint32_t rsvd_4       : 2; /**< Reserved */
		   uint32_t maskWdog3Rst : 4; /**< @brief Mask wdog3_rst_b source.
		                               *
		                               * If these 4 bits are coded from A to 5 then, the wdog3_rst_b input to SRC will
		                               * be masked and the wdog3_rst_b will not create a reset to the chip.
		                               *
		                               * @note Any other code than 0101 will be coded to 1010 i.e. wdog3_rst_b is not masked
		                               *
		                               * - 0101 wdog3_rst_b is masked
		                               * - 1010 wdog3_rst_b is not masked*/
	   } B; /**< Bitfield representation. */
	   uint32_t R; /**< Register representation. */
   } SCR;
   /** @brief SRC Boot Mode Register 1 (SRC_SBMR1)
    *
    * The Boot Mode register (SBMR) contains bits that reflect the status of Boot Mode Pins
    * of the chip. The reset value is configuration dependent (depending on boot/fuses/IO
    * pads).
    * If SRC_GPR10[28] bit is set, this bit instructs the ROM code to use the SRC_GPR9
    * register as if it is SBMR1. This allows software to override the fuse bits and boot from an
    * alternate boot source. */
   union
   {
	   struct
	   {
		   uint32_t bootCfg1: 8; /**< Refer to fusemap. */
		   uint32_t bootCfg2: 8; /**< Refer to fusemap. */
		   uint32_t bootCfg3: 8; /**< Refer to fusemap. */
		   uint32_t bootCfg4: 8; /**< Refer to fusemap. */
   	   } B; /**< Bitfield representation. */
   	   uint32_t R; /**< Register representation. */
   } SBMR1;
   /**< @brief SRC Reset Status Register (SRC_SRSR)
    *
    * The SRSR is a write to one clear register which records the source of the reset events for
    * the chip. The SRC reset status register will capture all the reset sources that have
    * occurred. This register is reset on ipp_reset_b. This is a read-write register.
    *
    * For bit[6-0] - writing zero does not have any effect. Writing one will clear the
    * corresponding bit. The individual bits can be cleared by writing one to that bit. When the
    * system comes out of reset, this register will have bits set corresponding to all the reset
    * sources that occurred during system reset. Software has to take care to clear this register
    * by writing one after every reset that occurs so that the register will contain the
    * information of recently occurred reset. */
   union
   {
	   struct
	   {
		   uint32_t ippResetB         :  1; /**< @brief Indicates whether reset was the result of ipp_reset_b pin (Power-up sequence)
		                                     *
		                                     * - 0 Reset is not a result of ipp_reset_b pin.
		                                     * - 1 Reset is a result of ipp_reset_b pin.
		                                     */
		   uint32_t lockupSysResetReq :  1; /**< @brief Indicates a reset has been caused by CPU lockup or software setting of SYSRESETREQ bit in Application
		                                     * Interrupt and Reset Control Register of the ARM core.
		                                     *
		                                     * SW needs to set some GPR bit before writing
		                                     * SYSRESETREQ bit and use the GPR bit to distinguish if the reset is caused by SYSRESETREQ or CPU
		                                     * lockup.
		                                     *
		                                     * - 0 Reset is not a result of the mentioned case.
		                                     * - 1 Reset is a result of the mentioned case.
		                                     */
		   uint32_t csuResetB         :  1; /**< @brief Indicates whether the reset was the result of the csu_reset_b input.
		                                     *
		                                     * - 0 Reset is not a result of the csu_reset_b event.
		                                     * - 1 Reset is a result of the csu_reset_b event.
		                                     */
		   uint32_t ippUserResetB     :  1; /**< @brief Indicates whether the reset was the result of the ipp_user_reset_b qualified reset.
		                                     *
		                                     * - 0 Reset is not a result of the ipp_user_reset_b qualified as COLD reset event.
		                                     * - 1 Reset is a result of the ipp_user_reset_b qualified as COLD reset event.
		                                     */
		   uint32_t wdogRstB          :  1; /**< @brief IC Watchdog Time-out reset.
		                                     *	Indicates whether the reset was the result of the watchdog time-out event.
		                                     *
		                                     *	- 0 Reset is not a result of the watchdog time-out event.
		                                     *	- 1 Reset is a result of the watchdog time-out event.
		                                     */
		   uint32_t jtagRstB          :  1; /**< @brief HIGH - Z JTAG reset.
		                                     *
		                                     * Indicates whether the reset was the result of HIGH-Z reset from JTA
		                                     *
		                                     * - 0 Reset is not a result of HIGH-Z reset from JTAG.
		                                     * - 1 Reset is a result of HIGH-Z reset from JTAG.
		                                     */
		   uint32_t jtagSwRst         :  1; /**< @brief JTAG software reset.
		                                     *
		                                     * Indicates whether the reset was the result of software reset from JTAG.
		                                     *
		                                     * - 0 Reset is not a result of software reset from JTAG.
		                                     * - 1 Reset is a result of software reset from JTAG.
		                                     */
		   uint32_t wdog3RstB         :  1; /**< @brief IC Watchdog3 Time-out reset.
		                                     *
		                                     * Indicates whether the reset was the result of the watchdog3 time-out event.
		                                     *
		                                     * - 0 Reset is not a result of the watchdog3 time-out event.
		                                     * - 1 Reset is a result of the watchdog3 time-out event.
		                                     */
		   uint32_t tempSenseRstB     :  1; /**< @brief Temper Sensor software reset.
		                                     *
		                                     * Indicates whether the reset was the result of software reset from on-chip
		                                     * Temperature Sensor.
		                                     *
		                                     * - 0 Reset is not a result of software reset from Temperature Sensor.
		                                     * - 1 Reset is a result of software reset from Temperature Sensor.
		                                     */
		   uint32_t rsvd_0            : 23; /**< @brief Reserved */
	   } B; /**< Bitfield representation. */
	   uint32_t R; /**< Register representation. */
   } SRSR;
   /** @brief Reserved */
   uint32_t RESERVED_0[4];
   /**< @brief SRC Boot Mode Register 2 (SRC_SBMR2)
    *
    * The Boot Mode register (SBMR), contains bits that reflect the status of Boot Mode Pins
    * of the chip. The default values for those bits depends on the values of pins/fuses during
    * reset sequence, hence the question mark on their default value.
    */
   union
   {
	   struct
	   {
		   uint32_t secConfig :  2; /**< @brief SECONFIG[1] shows the state of the SECONFIG[1] fuse.
		                             *
		                             * See Fusemap for additional information on this
		                             * fuse. SECONFIG[0] shows the state of the SECONFIG[0] fuse. This fuse is shown as reserved in
		                             * Fusemap (address 0x440[1]) because it does not have a user-relevant function.*/
		   uint32_t rsvd_0    :  1; /**< @brief This read-only field is reserved and always has the value 0. */
		   uint32_t dirBtDis  :  1; /**< @brief DIR_BT_DIS shows the state of the DIR_BT_DIS fuse.
		                             *
		                             * See Chapter 5, Fusemap for additional information on this fuse.*/
		   uint32_t btFuseSel :  1; /**< @brief BT_FUSE_SEL (connected to gpio bt_fuse_sel) shows the state of the BT_FUSE_SEL fuse.
		                             * See Fusemap for additional information on this fuse.*/
		   uint32_t rsvd1     : 19; /**< @brief This read-only field is reserved and always has the value 0. */
		   uint32_t bmod      :  2; /**< @brief BMOD[1:0] shows the latched state of the BOOT_MODE1 and BOOT_MODE0 signals on the rising edge of POR_B.
		                             *
		                             * See the Boot mode pin settings section of System Boot.*/
		   uint32_t rsvd_3    :  6; /**< @brief This read-only field is reserved and always has the value 0. */
	   } B; /**< Bitfield representation. */
	   uint32_t R; /**< Register representation. */
   }  SBMR2;
   /** SRC General Purpose Register  (SRC_GPR#)
    *
    * @note These registers are used by the ROM code and should not be used
    * by application software. */
   union
   {
	   struct
	   {
		   uint32_t rsvd_0; /**< @brief Reserved. */
	   } B; /**< Bitfield representation. */
	   uint32_t R; /**< Register representation. */
   }  GPR[10];
} c4_SRC_reg_t;
/*******************************************************************************
 * Prototypes
 ******************************************************************************/

/*******************************************************************************
 * Variables
 ******************************************************************************/

extern c4_WDOG_reg_t * const sWdogRegisters[];

/*******************************************************************************
 Interface Functions
 ******************************************************************************/

#endif /* C4_WATCHDOG_TYPES_H_ */
