/**
 *******************************************************************************
 * @file    dpm32m0xx_can.h
 *
 * @brief   This file contains all the functions prototypes for the CAN
 *          firmware library.
 *
 * @author  DPM
 *
 * @version V1.0.0
 *
 * @date    2023-11-01
 *
 *******************************************************************************/

#ifndef __DPM32M0XX_CAN_H__
#define __DPM32M0XX_CAN_H__


#ifdef __cplusplus
extern "C"
{
#endif

#if defined(__ARMCC_VERSION) && (__ARMCC_VERSION >= 6010050)
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wpadded"
#endif


#include "dpm32m0xx.h"

#if defined (DPM32M08x) && defined (DPM32M0xx_CAN_ENABLED)


/**
 ******************************************************************************************************
 * @brief CAN time segment 1 time quantum enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_TSEG1_1TQ = 0x00UL,             /*!< 1 time quantum. */
  CAN_TSEG1_2TQ,                      /*!< 2 time quantum. */
  CAN_TSEG1_3TQ,                      /*!< 3 time quantum. */
  CAN_TSEG1_4TQ,                      /*!< 4 time quantum. */
  CAN_TSEG1_5TQ,                      /*!< 5 time quantum. */
  CAN_TSEG1_6TQ,                      /*!< 6 time quantum. */
  CAN_TSEG1_7TQ,                      /*!< 7 time quantum. */
  CAN_TSEG1_8TQ,                      /*!< 8 time quantum. */
  CAN_TSEG1_9TQ,                      /*!< 9 time quantum. */
  CAN_TSEG1_10TQ,                     /*!< 10 time quantum. */
  CAN_TSEG1_11TQ,                     /*!< 11 time quantum. */
  CAN_TSEG1_12TQ,                     /*!< 12 time quantum. */
  CAN_TSEG1_13TQ,                     /*!< 13 time quantum. */
  CAN_TSEG1_14TQ,                     /*!< 14 time quantum. */
  CAN_TSEG1_15TQ,                     /*!< 15 time quantum. */
  CAN_TSEG1_16TQ                      /*!< 16 time quantum. */
} CAN_TSEG1Enum;


/**
 ******************************************************************************************************
 * @brief CAN time segment 2 time quantum enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_TSEG2_1TQ = 0x00UL,             /*!< 1 time quantum. */
  CAN_TSEG2_2TQ,                      /*!< 2 time quantum. */
  CAN_TSEG2_3TQ,                      /*!< 3 time quantum. */
  CAN_TSEG2_4TQ,                      /*!< 4 time quantum. */
  CAN_TSEG2_5TQ,                      /*!< 5 time quantum. */
  CAN_TSEG2_6TQ,                      /*!< 6 time quantum. */
  CAN_TSEG2_7TQ,                      /*!< 7 time quantum. */
  CAN_TSEG2_8TQ                       /*!< 8 time quantum. */
} CAN_TSEG2Enum;


/**
 ******************************************************************************************************
 * @brief CAN synchronization jump width time quantum enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_SJW_1TQ = 0x00UL,               /*!< 1 time quantum. */
  CAN_SJW_2TQ,                        /*!< 2 time quantum. */
  CAN_SJW_3TQ,                        /*!< 3 time quantum. */
  CAN_SJW_4TQ                         /*!< 4 time quantum. */
} CAN_SJWEnum;


/**
 ******************************************************************************************************
 * @brief CAN sampling multiple enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_SAM_SINGLE = 0x00UL,            /*!< triple sampling. */
  CAN_SAM_THREE                       /*!< single sampling. */
} CAN_SAMEnum;


/**
 ******************************************************************************************************
 * @brief CAN remote transmission request type enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_RTR_TYPE_DATA = 0x00UL,         /*!< Data frame. */
  CAN_RTR_TYPE_REMOTE                 /*!< Remote frame. */
} CAN_RTRTypeEnum;

/**
 ******************************************************************************************************
 * @brief CAN basic functions interrupt type enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_INT_TYPE_RX            = CAN_BASE_CTRL_RIE_Msk,             /*!< Reception interrupt. */
  CAN_INT_TYPE_TX            = CAN_BASE_CTRL_TIE_Msk,             /*!< Transmission interrupt. */
  CAN_INT_TYPE_ERR           = CAN_BASE_CTRL_EIE_Msk,             /*!< Error interrupt. */
  CAN_INT_TYPE_OVERRUN       = CAN_BASE_CTRL_OIE_Msk,             /*!< Over run interrupt. */
  CAN_INT_TYPE_OVERRHAP      = CAN_BASE_CTRL_OVRRHIE_Msk          /*!< Over run happen interrupt. */
} CAN_IntTypeEnum;

/**
 ******************************************************************************************************
 * @brief CAN basic functions interrupt flag enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_INT_FLAG_RX             = CAN_BASE_INTERRUPT_RI_Msk,              /*!< Reception interrupt flag. */
  CAN_INT_FLAG_TX             = CAN_BASE_INTERRUPT_TI_Msk,              /*!< Transmission interrupt flag. */
  CAN_INT_FLAG_ERR            = CAN_BASE_INTERRUPT_EI_Msk,              /*!< Error interrupt flag. */
  CAN_INT_FLAG_OVERRUN        = CAN_BASE_INTERRUPT_DOI_Msk,             /*!< Over run interrupt flag. */
  CAN_INT_FLAG_OVERRHAP       = CAN_BASE_INTERRUPT_OVRROI_Msk           /*!< Over run happen interrupt flag. */
} CAN_IntFlagEnum;


/**
 ******************************************************************************************************
 * @brief CAN basic functions interrupt flag enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_FLAG_RBS                = CAN_BASE_STATUS_RBS_Msk,      /*!< Receive buffer status. */
  CAN_FLAG_DOS                = CAN_BASE_STATUS_DOS_Msk,      /*!< Data over run status. */
  CAN_FLAG_TBS                = CAN_BASE_STATUS_TBS_Msk,      /*!< Transmit buffer status. */
  CAN_FLAG_TCS                = CAN_BASE_STATUS_TCS_Msk,      /*!< Transmission complete status. */
  CAN_FLAG_RS                 = CAN_BASE_STATUS_RS_Msk,       /*!< Receive status. */
  CAN_FLAG_TS                 = CAN_BASE_STATUS_TS_Msk,       /*!< Transmit status. */
  CAN_FLAG_ES                 = CAN_BASE_STATUS_ES_Msk,       /*!< Error status. */
  CAN_FLAG_BS                 = CAN_BASE_STATUS_BS_Msk,       /*!< Bus status. */
  CAN_FLAG_OHS                = CAN_BASE_STATUS_OVRROS_Msk    /*!< Over run happen status. */
} CAN_FlagEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI listen only mode enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_LOM_DISABLE = 0x00UL,      /*!< Disable listen only mode. */
  CAN_PELI_LOM_ENABLE                 /*!< Enable listen only mode. */
} CAN_PELI_LOMEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI self test mode enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_STM_DISABLE = 0x00UL,      /*!< Disable self test mode. */
  CAN_PELI_STM_ENABLE                 /*!< Enable self test mode. */
} CAN_PELI_STMEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI acceptance filter mode enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_AFM_DUAL = 0x00UL,         /*!< Select two acceptance filters (16 bits active each). */
  CAN_PELI_AFM_SINGLE                 /*!< Single acceptance filter (32-bit length). */
} CAN_PELI_AFMEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI frame format enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_IDE_STD = 0x00UL,        /*!< Standard frame format. */
  CAN_PELI_IDE_EXT                  /*!< Extended frame format. */
} CAN_PELI_IDEEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI frame type enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_RTR_DATA = 0x00UL,         /*!< Data Frame. */
  CAN_PELI_RTR_REMOTE                 /*!< Remote frame. */
} CAN_PELI_RTREnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI error type enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_ERRTYPE_BIT = 0x00UL,      /*!< Bit error. */
  CAN_PELI_ERRTYPE_FORMAT,            /*!< Format error. */
  CAN_PELI_ERRTYPE_STUFF,             /*!< Stuff error. */
  CAN_PELI_ERRTYPE_OTHER              /*!< Other type of error. */
} CAN_PELI_ErrTypeEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI error direction enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_ERRDIR_TRANSMITTER = 0x00UL,  /*!< Error while sending. */
  CAN_PELI_ERRDIR_RECEIVER               /*!< Error while receiving. */
} CAN_PELI_ErrDirectionEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI error segment enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_ERRSEG_ID28_21 = 0x02UL,      /*!< ID.28 to ID.21. */
  CAN_PELI_ERRSEG_START_FRAME,           /*!< Start of frame. */
  CAN_PELI_ERRSEG_SRTR,                  /*!< Bit SRTR. */
  CAN_PELI_ERRSEG_IDE,                   /*!< Bit IDE. */
  CAN_PELI_ERRSEG_ID20_18,               /*!< ID.20 to ID.18. */
  CAN_PELI_ERRSEG_ID17_13,               /*!< ID.17 to ID.13. */
  CAN_PELI_ERRSEG_CRC,                   /*!< CRC sequence. */
  CAN_PELI_ERRSEG_RESERVED_BIT0,         /*!< Reserved bit 0. */
  CAN_PELI_ERRSEG_DATA,                  /*!< Data field. */
  CAN_PELI_ERRSEG_DATA_LEN,              /*!< Data length code. */
  CAN_PELI_ERRSEG_RTR,                   /*!< Bit RTR. */
  CAN_PELI_ERRSEG_RESERVED_BIT1,         /*!< Reserved bit 1. */
  CAN_PELI_ERRSEG_ID4_0,                 /*!< ID.4 to ID.0. */
  CAN_PELI_ERRSEG_ID12_5,                /*!< ID.12 to ID.5. */
  CAN_PELI_ERRSEG_ACTIVE_ERR,            /*!< Active error flag. */
  CAN_PELI_ERRSEG_INTERMISSION,          /*!< Intermission. */
  CAN_PELI_ERRSEG_TOLERATE,              /*!< Tolerate dominant bits. */
  CAN_PELI_ERRSEG_PASSIVE_ERR = 0x16UL,  /*!< Passive error flag. */
  CAN_PELI_ERRSEG_ERR_DELIMITER,         /*!< Error delimiter. */
  CAN_PELI_ERRSEG_CRC_DELIMITER,         /*!< CRC delimiter. */
  CAN_PELI_ERRSEG_ACK_SLOT,              /*!< Acknowledge slot. */
  CAN_PELI_ERRSEG_END_FRAME,             /*!< End of frame. */
  CAN_PELI_ERRSEG_ACK_DELIMITER,         /*!< Acknowledge delimiter. */
  CAN_PELI_ERRSEG_ACK_OVERLOAD,          /*!< Overload flag. */
  CAN_PELI_ERRSEG_ACK_UNKNOWN            /*!< Unknown. */
} CAN_PELI_ErrSegmentEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI interrupt type enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_INT_TYPE_OVERR_HAP        = CAN_PELI_IE_OVRRHIE_Msk,  /*!< Overrun happen interrupt enable. */
  CAN_PELI_INT_TYPE_BUS_ERR          = CAN_PELI_IE_BEIE_Msk,     /*!< Bus error interrupt enable. */
  CAN_PELI_INT_TYPE_ARB_LOST         = CAN_PELI_IE_ALIE_Msk,     /*!< Arbitration lost interrupt enable. */
  CAN_PELI_INT_TYPE_ERR_PASSIVE      = CAN_PELI_IE_EPIE_Msk,     /*!< Error passive interrupt enable. */
  CAN_PELI_INT_TYPE_OVERR            = CAN_PELI_IE_DOIE_Msk,     /*!< Data overrun interrupt enable. */
  CAN_PELI_INT_TYPE_ERR_WARRING      = CAN_PELI_IE_EIE_Msk,      /*!< Error warning interrupt enable. */
  CAN_PELI_INT_TYPE_TX               = CAN_PELI_IE_TIE_Msk,      /*!< Transmit interrupt enable. */
  CAN_PELI_INT_TYPE_RX               = CAN_PELI_IE_RIE_Msk       /*!< Receive interrupt enable. */
} CAN_PELI_IntTypeEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI interrupt flag enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_INT_FLAG_OVERR_HAP   = CAN_PELI_INTERRUPT_OVRROI_Msk,   /*!< Overrun happen interrupt falg. */
  CAN_PELI_INT_FLAG_BUS_ERR     = CAN_PELI_INTERRUPT_BEI_Msk,      /*!< Bus error interrupt falg. */
  CAN_PELI_INT_FLAG_ARB_LOST    = CAN_PELI_INTERRUPT_ALI_Msk,      /*!< Arbitration lost interrupt falg. */
  CAN_PELI_INT_FLAG_ERR_PASSIVE = CAN_PELI_INTERRUPT_EPI_Msk,      /*!< Error passive interrupt falg. */
  CAN_PELI_INT_FLAG_OVERR       = CAN_PELI_INTERRUPT_DOI_Msk,      /*!< Data Overrun interrupt falg. */
  CAN_PELI_INT_FLAG_ERR_WARRING = CAN_PELI_INTERRUPT_EI_Msk,       /*!< Error warning interrupt falg. */
  CAN_PELI_INT_FLAG_TX          = CAN_PELI_INTERRUPT_TI_Msk,       /*!< Transmit interrupt falg. */
  CAN_PELI_INT_FLAG_RX          = CAN_PELI_INTERRUPT_RI_Msk        /*!< Receive interrupt falg. */
} CAN_PELI_IntFlagEnum;

/**
 ******************************************************************************************************
 * @brief CAN_PELI flag enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_FLAG_OHS           = CAN_PELI_STATUS_OVRROS_Msk,   /*!< Overrun happen status. */
  CAN_PELI_FLAG_BS            = CAN_PELI_STATUS_BS_Msk,       /*!< Bus status. */
  CAN_PELI_FLAG_ES            = CAN_PELI_STATUS_ES_Msk,       /*!< Error status. */
  CAN_PELI_FLAG_TS            = CAN_PELI_STATUS_TS_Msk,       /*!< Transmit status. */
  CAN_PELI_FLAG_RS            = CAN_PELI_STATUS_RS_Msk,       /*!< Receive status. */
  CAN_PELI_FLAG_TCS           = CAN_PELI_STATUS_TCS_Msk,      /*!< Transmission complete status. */
  CAN_PELI_FLAG_TBS           = CAN_PELI_STATUS_TBS_Msk,      /*!< Transmit buffer status. */
  CAN_PELI_FLAG_DOS           = CAN_PELI_STATUS_DOS_Msk,      /*!< Data overrun status. */
  CAN_PELI_FLAG_RBS           = CAN_PELI_STATUS_RBS_Msk       /*!< Receive buffer status. */
} CAN_PELI_FlagEnum;


/**
 ******************************************************************************************************
 * @brief CAN_PELI arbitration lost bit enumeration.
 *****************************************************************************************************/
typedef enum
{
  CAN_PELI_ARBLOST_BIT_1 = 0x00UL,  /*!< Arbitration lost in bit 1 of identifier. */
  CAN_PELI_ARBLOST_BIT_2,           /*!< Arbitration lost in bit 2 of identifier. */
  CAN_PELI_ARBLOST_BIT_3,           /*!< Arbitration lost in bit 3 of identifier. */
  CAN_PELI_ARBLOST_BIT_4,           /*!< Arbitration lost in bit 4 of identifier. */
  CAN_PELI_ARBLOST_BIT_5,           /*!< Arbitration lost in bit 5 of identifier. */
  CAN_PELI_ARBLOST_BIT_6,           /*!< Arbitration lost in bit 6 of identifier. */
  CAN_PELI_ARBLOST_BIT_7,           /*!< Arbitration lost in bit 7 of identifier. */
  CAN_PELI_ARBLOST_BIT_8,           /*!< Arbitration lost in bit 8 of identifier. */
  CAN_PELI_ARBLOST_BIT_9,           /*!< Arbitration lost in bit 9 of identifier. */
  CAN_PELI_ARBLOST_BIT_10,          /*!< Arbitration lost in bit 10 of identifier. */
  CAN_PELI_ARBLOST_BIT_11,          /*!< Arbitration lost in bit 11 of identifier. */
  CAN_PELI_ARBLOST_BIT_SRTR,        /*!< Arbitration lost in bit SRTR. */
  CAN_PELI_ARBLOST_BIT_IDE,         /*!< Arbitration lost in bit IDE. */
  CAN_PELI_ARBLOST_BIT_12,          /*!< Arbitration lost in bit 12 of identifier. */
  CAN_PELI_ARBLOST_BIT_13,          /*!< Arbitration lost in bit 13 of identifier. */
  CAN_PELI_ARBLOST_BIT_14,          /*!< Arbitration lost in bit 14 of identifier. */
  CAN_PELI_ARBLOST_BIT_15,          /*!< Arbitration lost in bit 15 of identifier. */
  CAN_PELI_ARBLOST_BIT_16,          /*!< Arbitration lost in bit 16 of identifier. */
  CAN_PELI_ARBLOST_BIT_17,          /*!< Arbitration lost in bit 17 of identifier. */
  CAN_PELI_ARBLOST_BIT_18,          /*!< Arbitration lost in bit 18 of identifier. */
  CAN_PELI_ARBLOST_BIT_19,          /*!< Arbitration lost in bit 19 of identifier. */
  CAN_PELI_ARBLOST_BIT_20,          /*!< Arbitration lost in bit 20 of identifier. */
  CAN_PELI_ARBLOST_BIT_21,          /*!< Arbitration lost in bit 21 of identifier. */
  CAN_PELI_ARBLOST_BIT_22,          /*!< Arbitration lost in bit 22 of identifier. */
  CAN_PELI_ARBLOST_BIT_23,          /*!< Arbitration lost in bit 23 of identifier. */
  CAN_PELI_ARBLOST_BIT_24,          /*!< Arbitration lost in bit 24 of identifier. */
  CAN_PELI_ARBLOST_BIT_25,          /*!< Arbitration lost in bit 25 of identifier. */
  CAN_PELI_ARBLOST_BIT_26,          /*!< Arbitration lost in bit 26 of identifier. */
  CAN_PELI_ARBLOST_BIT_27,          /*!< Arbitration lost in bit 27 of identifier. */
  CAN_PELI_ARBLOST_BIT_28,          /*!< Arbitration lost in bit 28 of identifier. */
  CAN_PELI_ARBLOST_BIT_29,          /*!< Arbitration lost in bit 19 of identifier. */
  CAN_PELI_ARBLOST_BIT_RTR          /*!< Arbitration lost in bit RTR. */
} CAN_PELI_ARBLostBitEnum;



/**
 ******************************************************************************************************
 * @brief CAN_Basic initialization structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint8_t CAN_Prescaler;                /*!< Specifies the baud rate prescaler value.
                                              This parameter can be a number between 0x00 and 0xFF.
                                              @note T(scl) = 2 × (BRP+1) x T(clk). */

  uint8_t CAN_SyncJumpWidth;            /*!< Specifies the time quantum of the synchronization jump width.
                                              This parameter can be a value of @ref CAN_SJWEnum */

  uint8_t CAN_Sampling;                 /*!< Specifies the sampling multiple.
                                              This parameter can be a value of @ref CAN_SAMEnum */

  uint8_t CAN_TimeSegment1;             /*!< Specifies the time quantum for time segment 1.
                                              This parameter can be a value of @ref CAN_TSEG1Enum */

  uint8_t CAN_TimeSegment2;             /*!< Specifies the time quantum for time segment 2.
                                              This parameter can be a value of @ref CAN_TSEG2Enum */
} CAN_InitTypeStruct;

/**
 ******************************************************************************************************
 * @brief CAN_Basic filter initialization structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint8_t CAN_FilterId;         /*!< Specifies the filter identification number .
                                      This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_FilterMaskId;     /*!< Specifies the filter mask number or identification number,
                                      This parameter can be a value between 0x00 and 0xFF */

} CAN_FilterInitTypeStruct;

/**
 ******************************************************************************************************
 * @brief CAN_Basic message structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint16_t ID;                    /*!< Specifies the standard identifier.
                                       This parameter can be a value between 0 to 0x7FF. */

  uint8_t RTR;                    /*!< Specifies the type of frame for the received message.
                                       This parameter can be @ref CAN_RTRTypeEnum */

  uint8_t DLC;                    /*!< Specifies the length of the frame that will be received.
                                       This parameter can be a value between 0 to 8 */

  uint8_t Data[8];                /*!< Contains the data to be received. It ranges from 0 to 0xFF. */
} CanBasicMsg;


/**
 ******************************************************************************************************
 * @brief CAN_PELI initialization structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint32_t CAN_PELI_Prescaler;              /*!< Specifies the baud rate prescaler value.
                                                  This parameter can be a number between 0x00 and 0xFF.
                                                  @note T(scl) = 2 × (BRP+1) x T(clk). */

  uint32_t CAN_PELI_SyncJumpWidth;          /*!< Specifies the time quantum of the synchronization jump width.
                                                  This parameter can be a value of @ref CAN_SJWEnum */

  uint32_t CAN_PELI_Sampling;               /*!< Specifies the sampling multiple.
                                                  This parameter can be a value of @ref CAN_SAMEnum */

  uint32_t CAN_PELI_TimeSegment1;           /*!< Specifies the time quantum for time segment 1.
                                                  This parameter can be a value of @ref CAN_TSEG1Enum */

  uint32_t CAN_PELI_TimeSegment2;           /*!< Specifies the time quantum for time segment 2.
                                                  This parameter can be a value of @ref CAN_TSEG2Enum */

  uint32_t CAN_PELI_ListenOnlyMode;         /*!< Specifies if listen only mode is selected.
                                                  This parameter can be a value of @ref CAN_PELI_LOMEnum */

  uint32_t CAN_PELI_SelfTestMode;           /*!< Specifies if self test mode is selected.
                                                  This parameter can be a value of @ref CAN_PELI_STMEnum */

  uint32_t CAN_PELI_ErrorWarningLimit;      /*!< Specifies error limit alarm thresholds.
                                                  This parameter can be a number between 0x00 and 0xFF. */
} CAN_PELI_InitTypeStruct;



/**
 ******************************************************************************************************
 * @brief CAN_PELI filter init structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint8_t CAN_PELI_AcceptanceFilterMode;    /*!< Specifies acceptance filter mode.
                                                  This parameter can be a value of @ref CAN_PELI_AFMEnum */

  uint8_t CAN_PELI_FilterId0;               /*!< Specifies the filter id 0.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterId1;               /*!< Specifies the filter id 1.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterId2;               /*!< Specifies the filter id 2.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterId3;               /*!< Specifies the filter id 3.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterMaskId0;           /*!< Specifies the filter mask 0.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterMaskId1;           /*!< Specifies the filter mask 1.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterMaskId2;           /*!< Specifies the filter mask 2.
                                                  This parameter can be a value between 0x00 and 0xFF */

  uint8_t CAN_PELI_FilterMaskId3;           /*!< Specifies the filter mask 3.
                                                  This parameter can be a value between 0x00 and 0xFF */
} CAN_PELI_FilterInitTypeStruct;


/**
 ******************************************************************************************************
 * @brief CAN_Peli_Tx/CAN_Peli_Rx message structure definition.
 *****************************************************************************************************/
typedef struct
{
  uint32_t ID;       /*!< Specifies a standard frame format or extended frame format identifier.
                           Standard frame format can be a value between 0 and 0x7FF
                           The extended frame format can be a value between 0 and 0x1FFFFFFF */

  uint8_t IDE;       /*!< Specifies the type of identifier for the message that will be transmitted.
                           This parameter can be a value of @ref CAN_PELI_IDEEnum */

  uint8_t RTR;       /*!< Specifies the type of frame for the message that will be transmitted.
                           This parameter can be a value of @ref CAN_PELI_RTREnum */

  uint8_t DLC;       /*!< Specifies the length of the frame that will be transmitted.
                           This parameter can be a value between 0 to 8 */

  uint8_t Data[8];   /*!< Contains the data to be transmitted.
                           This parameter can be a value between 0 to 0xFF. */
} CanPeliMsg;



/* CAN Param Check. */
#define IS_CAN_SJW(x) (((x) == CAN_SJW_1TQ) || ((x) == CAN_SJW_2TQ) || \
                       ((x) == CAN_SJW_3TQ) || ((x) == CAN_SJW_4TQ))


#define IS_CAN_SAMPLING(x) (((x) == CAN_SAM_SINGLE) || ((x) == CAN_SAM_THREE))


#define IS_CAN_TSEG1(x) (((x) == CAN_TSEG1_1TQ) || ((x) == CAN_TSEG1_2TQ) || \
                         ((x) == CAN_TSEG1_3TQ) || ((x) == CAN_TSEG1_4TQ) || \
                         ((x) == CAN_TSEG1_5TQ) || ((x) == CAN_TSEG1_6TQ) || \
                         ((x) == CAN_TSEG1_7TQ) || ((x) == CAN_TSEG1_8TQ) || \
                         ((x) == CAN_TSEG1_9TQ) || ((x) == CAN_TSEG1_10TQ) || \
                         ((x) == CAN_TSEG1_11TQ) || ((x) == CAN_TSEG1_12TQ) || \
                         ((x) == CAN_TSEG1_13TQ) || ((x) == CAN_TSEG1_14TQ) || \
                         ((x) == CAN_TSEG1_15TQ) || ((x) == CAN_TSEG1_16TQ))


#define IS_CAN_TSEG2(x) (((x) == CAN_TSEG2_1TQ) || ((x) == CAN_TSEG2_2TQ) || \
                         ((x) == CAN_TSEG2_3TQ) || ((x) == CAN_TSEG2_4TQ) || \
                         ((x) == CAN_TSEG2_5TQ) || ((x) == CAN_TSEG2_6TQ) || \
                         ((x) == CAN_TSEG2_7TQ) || ((x) == CAN_TSEG2_8TQ))


#define IS_CAN_INT_TYPE(x) (((x & CAN_INT_TYPE_RX) == CAN_INT_TYPE_RX) || \
                            ((x & CAN_INT_TYPE_TX) == CAN_INT_TYPE_TX) || \
                            ((x & CAN_INT_TYPE_ERR) == CAN_INT_TYPE_ERR) || \
                            ((x & CAN_INT_TYPE_OVERRUN) == CAN_INT_TYPE_OVERRUN) || \
                            ((x & CAN_INT_TYPE_OVERRHAP) == CAN_INT_TYPE_OVERRHAP))


#define IS_CAN_INT_FLAG(x) (((x) == CAN_INT_FLAG_RX) || ((x) == CAN_INT_FLAG_TX) || \
                            ((x) == CAN_INT_FLAG_ERR) || ((x) == CAN_INT_FLAG_OVERRUN) || \
                            ((x) == CAN_INT_FLAG_OVERRHAP))


#define IS_CAN_RTR_TYPE(x) (((x) == CAN_RTR_TYPE_DATA) || ((x) == CAN_RTR_TYPE_REMOTE))


#define IS_CAN_DLC(x) ((x) <= 8)


#define IS_CAN_FLAG(x) (((x) == CAN_FLAG_RBS) || ((x) == CAN_FLAG_DOS) || \
                        ((x) == CAN_FLAG_TBS) || ((x) == CAN_FLAG_TCS) || \
                        ((x) == CAN_FLAG_RS) || ((x) == CAN_FLAG_TS) || \
                        ((x) == CAN_FLAG_ES) || ((x) == CAN_FLAG_BS) || \
                        ((x) == CAN_FLAG_OHS))


/* CAN_PELI Param Check. */
#define IS_CAN_PELI_BRP_VAL(x)         (((x) <= 0xFF))
#define IS_CAN_PELI_SJW(x)             (IS_CAN_SJW(x))
#define IS_CAN_PELI_SAM(x)             (IS_CAN_SAMPLING(x))
#define IS_CAN_PELI_TSEG1(x)           (IS_CAN_TSEG1(x))
#define IS_CAN_PELI_TSEG2(x)           (IS_CAN_TSEG2(x))
#define IS_CAN_PELI_LOM(x)             (((x) == CAN_PELI_LOM_DISABLE) || ((x) == CAN_PELI_LOM_ENABLE))
#define IS_CAN_PELI_STM(x)             (((x) == CAN_PELI_STM_DISABLE) || ((x) == CAN_PELI_STM_ENABLE))
#define IS_CAN_PELI_EWL_VAL(x)         (((x) <= 0xFF))
#define IS_CAN_PELI_AFM(x)             (((x) == CAN_PELI_AFM_DUAL) || ((x) == CAN_PELI_AFM_SINGLE))
#define IS_CAN_PELI_FILTER_ID_VAL(x)   (((x) <= 0xFF))
#define IS_CAN_PELI_FILTER_MASK_VAL(x) (((x) <= 0xFF))
#define IS_CAN_PELI_STD_ID_VAL(x)      (((x) <= 0x7FF))
#define IS_CAN_PELI_EXD_ID_VAL(x)      (((x) <= 0x1FFFFFFF))
#define IS_CAN_PELI_IDE(x)             (((x) == CAN_PELI_IDE_STD) || ((x) == CAN_PELI_IDE_EXT))
#define IS_CAN_PELI_RTR(x)             (((x) == CAN_PELI_RTR_DATA) || ((x) == CAN_PELI_RTR_REMOTE))
#define IS_CAN_PELI_DLC_VAL(x)         (((x) <= 0x08))


#define IS_CAN_PELI_INT_TYPE(x) (((x) == CAN_PELI_INT_TYPE_OVERR_HAP) || ((x) == CAN_PELI_INT_TYPE_BUS_ERR) || \
                                 ((x) == CAN_PELI_INT_TYPE_ARB_LOST) || ((x) == CAN_PELI_INT_TYPE_ERR_PASSIVE) || \
                                 ((x) == CAN_PELI_INT_TYPE_OVERR) || ((x) == CAN_PELI_INT_TYPE_ERR_WARRING) || \
                                 ((x) == CAN_PELI_INT_TYPE_TX) || ((x) == CAN_PELI_INT_TYPE_RX))


#define IS_CAN_PELI_INT_FLAG(x) (((x) == CAN_PELI_INT_FLAG_OVERR_HAP) || ((x) == CAN_PELI_INT_FLAG_BUS_ERR) || \
                                 ((x) == CAN_PELI_INT_FLAG_ARB_LOST) || ((x) == CAN_PELI_INT_FLAG_ERR_PASSIVE) || \
                                 ((x) == CAN_PELI_INT_FLAG_OVERR) || ((x) == CAN_PELI_INT_FLAG_ERR_WARRING) || \
                                 ((x) == CAN_PELI_INT_FLAG_TX) || ((x) == CAN_PELI_INT_FLAG_RX))


#define IS_CAN_PELI_FLAG(x) (((x) == CAN_PELI_FLAG_OHS) || ((x) == CAN_PELI_FLAG_BS) || \
                             ((x) == CAN_PELI_FLAG_ES) || ((x) == CAN_PELI_FLAG_TS) || \
                             ((x) == CAN_PELI_FLAG_RS) || ((x) == CAN_PELI_FLAG_TCS) || \
                             ((x) == CAN_PELI_FLAG_TBS) || ((x) == CAN_PELI_FLAG_DOS) || \
                             ((x) == CAN_PELI_FLAG_RBS))




/* Basic Work functions. */
void                          CAN_ResetModeCmd(FunctionalState NewState);
void                          CAN_ClearDataOverflow(void);
void                          CAN_ClearIntPendingBit(void);

/* CAN_BASIC initialization and Configuration functions. */
void                          CAN_DeInit(void);
void                          CAN_Init(CAN_InitTypeStruct* CAN_InitType);
void                          CAN_StructInit(CAN_InitTypeStruct* CAN_InitType);
void                          CAN_Cmd(FunctionalState Newstate);

/* CAN_BASIC configuration filter functions. */
void                          CAN_FilterInit(CAN_FilterInitTypeStruct* CAN_FilterInitStruct);
void                          CAN_FilterStructInit(CAN_FilterInitTypeStruct* CAN_FilterInitStruct);

/* CAN_BASIC Data transfers functions. */
void                          CAN_ReceiveFIFORelease(void);
void                          CAN_CancelTransmit(void);
void                          CAN_Transmit(CanBasicMsg* TxMessage);
void                          CAN_TransmitRepeat(CanBasicMsg* TxMessage);
void                          CAN_Receive(CanBasicMsg* RxMessage);

/* CAN_BASIC interrupts and flags management functions. */
void                          CAN_IntCmd(uint32_t CAN_IntType, FunctionalState Newstate);
FunctionalState               CAN_GetIntCmdStatus(CAN_IntTypeEnum CAN_IntType);
FlagState                     CAN_GetIntFlagStatus(CAN_IntFlagEnum CAN_IntFlag);
FlagState                     CAN_GetFlagStatus(CAN_FlagEnum CAN_Flag);


/* Peli Work functions */
void                          CAN_PELI_ResetModeCmd(FunctionalState Newstate);
void                          CAN_PELI_ClearDataOverflow(void);
void                          CAN_PELI_ClearITPendingBit(void);

/* CAN_PELI initialization and Configuration functions. */
void                          CAN_PELI_DeInit(void);
void                          CAN_PELI_Init(CAN_PELI_InitTypeStruct* CAN_Peli_InitType);
void                          CAN_PELI_StructInit(CAN_PELI_InitTypeStruct* CAN_Peli_InitType);
void                          CAN_PELI_Cmd(FunctionalState Newstate);

/* CAN_PELI configuration filter functions. */
void                          CAN_PELI_FilterInit(CAN_PELI_FilterInitTypeStruct* CAN_Peli_FilterInitType);
void                          CAN_PELI_FilterStructInit(CAN_PELI_FilterInitTypeStruct *CAN_Peli_FilterInitType);

/* CAN_PELI Data transfers functions. */
void                          CAN_PELI_Transmit(CanPeliMsg* TxMessage);
void                          CAN_PELI_TransmitRepeat(CanPeliMsg* TxMessage);
void                          CAN_PELI_Receive(CanPeliMsg* RxMessage);
void                          CAN_PELI_CancelTransmit(void);
void                          CAN_PELI_ReceiveFIFORelease(void);

/* CAN_PELI error handling functions. */
CAN_PELI_ARBLostBitEnum       CAN_PELI_GetArbitrationLostBit(void);
uint32_t                      CAN_PELI_GetErrorCodeCaptureReg(void);
CAN_PELI_ErrTypeEnum          CAN_PELI_ParseErrorType(uint32_t ErrorCode);
CAN_PELI_ErrDirectionEnum     CAN_PELI_ParseErrorDirection(uint32_t ErrorCode);
CAN_PELI_ErrSegmentEnum       CAN_PELI_ParseErrorSegment(uint32_t ErrorCode);
uint8_t                       CAN_PELI_GetReceiveMessageCounter(void);
uint8_t                       CAN_PELI_GetReceiveErrorCounter(void);
uint8_t                       CAN_PELI_GetTransmitErrorCounter(void);
void                          CAN_PELI_SetReceiveErrorCounter(uint8_t ErrorCnt);
void                          CAN_PELI_SetTransmitErrorCounter(uint8_t ErrorCnt);

/* CAN_PELI interrupts and flags management functions. */
void                          CAN_PELI_IntCmd(uint32_t CAN_PELI_IntType, FunctionalState Newstate);
FunctionalState               CAN_PELI_GetIntCmdStatus(uint32_t CAN_PELI_IntType);
FlagState                     CAN_PELI_GetIntFlagStatus(uint32_t CAN_PELI_IntFlag);
FlagState                     CAN_PELI_GetFlagStatus(uint32_t CAN_PELI_Flag);


#endif /* (DPM32M08x) && defined (DPM32M0xx_CAN_ENABLED) */

#if defined(__ARMCC_VERSION) && (__ARMCC_VERSION >= 6010050)
#pragma clang diagnostic pop
#endif


#ifdef __cplusplus
}
#endif

#endif /* __DPM32M0XX_CAN_H__ */
