aboutsummaryrefslogtreecommitdiffstats
path: root/lib/hc32f460/driver/src/hc32f460_sdioc.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/hc32f460/driver/src/hc32f460_sdioc.c')
-rw-r--r--lib/hc32f460/driver/src/hc32f460_sdioc.c2217
1 files changed, 2217 insertions, 0 deletions
diff --git a/lib/hc32f460/driver/src/hc32f460_sdioc.c b/lib/hc32f460/driver/src/hc32f460_sdioc.c
new file mode 100644
index 00000000..5697202a
--- /dev/null
+++ b/lib/hc32f460/driver/src/hc32f460_sdioc.c
@@ -0,0 +1,2217 @@
+/*******************************************************************************
+ * Copyright (C) 2020, Huada Semiconductor Co., Ltd. All rights reserved.
+ *
+ * This software component is licensed by HDSC under BSD 3-Clause license
+ * (the "License"); You may not use this file except in compliance with the
+ * License. You may obtain a copy of the License at:
+ * opensource.org/licenses/BSD-3-Clause
+ */
+/******************************************************************************/
+/** \file hc32f460_sdioc.c
+ **
+ ** A detailed description is available at
+ ** @link SdiocGroup SDIOC description @endlink
+ **
+ ** - 2018-11-11 CDT First version for Device Driver Library of SDIOC.
+ **
+ ******************************************************************************/
+
+/*******************************************************************************
+ * Include files
+ ******************************************************************************/
+#include "hc32f460_sdioc.h"
+#include "hc32f460_utility.h"
+
+/**
+ *******************************************************************************
+ ** \addtogroup SdiocGroup
+ ******************************************************************************/
+//@{
+
+/*******************************************************************************
+ * Local type definitions ('typedef')
+ ******************************************************************************/
+
+/**
+ *******************************************************************************
+ ** \brief SDIOC internal data
+ **
+ ******************************************************************************/
+typedef struct stc_sdioc_intern_data
+{
+ stc_sdioc_normal_irq_cb_t stcNormalIrqCb; ///< Normal irq callback function structure
+
+ stc_sdioc_error_irq_cb_t stcErrorIrqCb; ///< Error irq callback function structure
+} stc_sdioc_intern_data_t;
+
+/**
+ *******************************************************************************
+ ** \brief SDIOC instance data
+ **
+ ******************************************************************************/
+typedef struct stc_sdioc_instance_data
+{
+ const M4_SDIOC_TypeDef *SDIOCx; ///< pointer to registers of an instance
+
+ stc_sdioc_intern_data_t stcInternData; ///< module internal data of instance
+} stc_sdioc_instance_data_t;
+
+/*******************************************************************************
+ * Local pre-processor symbols/macros ('#define')
+ ******************************************************************************/
+
+/*!< Parameter valid check for SDIOC Instances. */
+#define IS_VALID_SDIOC(__SDIOCx__) \
+( (M4_SDIOC1 == (__SDIOCx__)) || \
+ (M4_SDIOC2 == (__SDIOCx__)))
+
+/*!< Parameter valid check for SDIOC mode. */
+#define IS_VALID_SDIOC_MODE(x) \
+( (SdiocModeSD == (x)) || \
+ (SdiocModeMMC == (x)))
+
+/*!< Parameter valid check for SDIOC Response Register. */
+#define IS_VALID_SDIOC_RESP(x) \
+( (SdiocRegResp01 == (x)) || \
+ (SdiocRegResp23 == (x)) || \
+ (SdiocRegResp45 == (x)) || \
+ (SdiocRegResp67 == (x)))
+
+/*!< Parameter valid check for SDIOC bus width. */
+#define IS_VALID_SDIOC_BUS_WIDTH(x) \
+( (SdiocBusWidth1Bit == (x)) || \
+ (SdiocBusWidth4Bit == (x)) || \
+ (SdiocBusWidth8Bit == (x)))
+
+/*!< Parameter valid check for SDIOC speed mode. */
+#define IS_VALID_SDIOC_SPEED_MODE(x) \
+( (SdiocHighSpeedMode == (x)) || \
+ (SdiocNormalSpeedMode == (x)))
+
+/*!< Parameter valid check for SDIOC Clock division. */
+#define IS_VALID_SDIOC_CLK_DIV(x) \
+( (SdiocClkDiv_1 == (x)) || \
+ (SdiocClkDiv_2 == (x)) || \
+ (SdiocClkDiv_4 == (x)) || \
+ (SdiocClkDiv_8 == (x)) || \
+ (SdiocClkDiv_16 == (x)) || \
+ (SdiocClkDiv_32 == (x)) || \
+ (SdiocClkDiv_64 == (x)) || \
+ (SdiocClkDiv_128 == (x)) || \
+ (SdiocClkDiv_256 == (x)))
+
+/*!< Parameter valid check for SDIOC command type. */
+#define IS_VALID_SDIOC_CMD_TYPE(x) \
+( (SdiocCmdAbort == (x)) || \
+ (SdiocCmdResume == (x)) || \
+ (SdiocCmdNormal == (x)) || \
+ (SdiocCmdSuspend == (x)))
+
+/*!< Parameter valid check for SDIOC data transfer direction. */
+#define IS_VALID_SDIOC_TRANSFER_DIR(x) \
+( (SdiocTransferToCard == (x)) || \
+ (SdiocTransferToHost == (x)))
+
+/*!< Parameter valid check for SDIOC software reset type. */
+#define IS_VALID_SDIOC_SWRESETTYPE(x) \
+( (SdiocSwResetAll == (x)) || \
+ (SdiocSwResetCmdLine == (x)) || \
+ (SdiocSwResetDatLine == (x)))
+
+/*!< Parameter valid check for SDIOC data transfer mode. */
+#define IS_VALID_SDIOC_TRANSFER_MODE(x) \
+( (SdiocTransferSingle == (x)) || \
+ (SdiocTransferInfinite == (x)) || \
+ (SdiocTransferMultiple == (x)) || \
+ (SdiocTransferStopMultiple == (x)))
+
+/*!< Parameter valid check for SDIOC data timeout. */
+#define IS_VALID_SDIOC_DATA_TIMEOUT(x) \
+( (SdiocDtoSdclk_2_13 == (x)) || \
+ (SdiocDtoSdclk_2_14 == (x)) || \
+ (SdiocDtoSdclk_2_15 == (x)) || \
+ (SdiocDtoSdclk_2_16 == (x)) || \
+ (SdiocDtoSdclk_2_17 == (x)) || \
+ (SdiocDtoSdclk_2_18 == (x)) || \
+ (SdiocDtoSdclk_2_19 == (x)) || \
+ (SdiocDtoSdclk_2_20 == (x)) || \
+ (SdiocDtoSdclk_2_21 == (x)) || \
+ (SdiocDtoSdclk_2_22 == (x)) || \
+ (SdiocDtoSdclk_2_23 == (x)) || \
+ (SdiocDtoSdclk_2_24 == (x)) || \
+ (SdiocDtoSdclk_2_25 == (x)) || \
+ (SdiocDtoSdclk_2_26 == (x)) || \
+ (SdiocDtoSdclk_2_27 == (x)))
+
+/*!< Parameter valid check for SDIOC Response type name. */
+#define IS_VALID_SDIOC_RESP_TYPE_NAME(x) \
+( (SdiocCmdRspR1 == (x)) || \
+ (SdiocCmdRspR1b == (x)) || \
+ (SdiocCmdRspR2 == (x)) || \
+ (SdiocCmdRspR3 == (x)) || \
+ (SdiocCmdRspR4 == (x)) || \
+ (SdiocCmdRspR5 == (x)) || \
+ (SdiocCmdRspR5b == (x)) || \
+ (SdiocCmdRspR6 == (x)) || \
+ (SdiocCmdRspR7 == (x)) || \
+ (SdiocCmdNoRsp == (x)))
+
+/*!< Parameter valid check for SDIOC data timeout. */
+#define IS_VALID_SDIOC_HOST_STATUS(x) \
+( (SdiocCmdPinLvl == (x)) || \
+ (SdiocData0PinLvl == (x)) || \
+ (SdiocData1PinLvl == (x)) || \
+ (SdiocData2PinLvl == (x)) || \
+ (SdiocData3PinLvl == (x)) || \
+ (SdiocCardInserted == (x)) || \
+ (SdiocDataLineActive == (x)) || \
+ (SdiocCardStateStable == (x)) || \
+ (SdiocBufferReadEnble == (x)) || \
+ (SdiocBufferWriteEnble == (x)) || \
+ (SdiocCardDetectPinLvl == (x)) || \
+ (SdiocCommandInhibitCmd == (x)) || \
+ (SdiocWriteProtectPinLvl == (x)) || \
+ (SdiocCommandInhibitData == (x)) || \
+ (SdiocReadTransferActive == (x)) || \
+ (SdiocWriteTransferActive == (x)))
+
+/*!< Parameter valid check for SDIOC normal interrupt. */
+#define IS_VALID_SDIOC_NOR_INT(x) \
+( (SdiocCardInt == (x)) || \
+ (SdiocErrorInt == (x)) || \
+ (SdiocCardRemoval == (x)) || \
+ (SdiocBlockGapEvent == (x)) || \
+ (SdiocCardInsertedInt == (x)) || \
+ (SdiocCommandComplete == (x)) || \
+ (SdiocBufferReadReady == (x)) || \
+ (SdiocBufferWriteReady == (x)) || \
+ (SdiocTransferComplete == (x)))
+
+/*!< Parameter valid check for SDIOC error interrupt. */
+#define IS_VALID_SDIOC_ERR_INT(x) \
+( (SdiocCmdCrcErr == (x)) || \
+ (SdiocDataCrcErr == (x)) || \
+ (SdiocCmdIndexErr == (x)) || \
+ (SdiocCmdEndBitErr == (x)) || \
+ (SdiocAutoCmd12Err == (x)) || \
+ (SdiocCmdTimeoutErr == (x)) || \
+ (SdiocDataEndBitErr == (x)) || \
+ (SdiocDataTimeoutErr == (x)))
+
+/*!< Parameter valid check for SDIOC auto CMD12 error status. */
+#define IS_VALID_SDIOC_AUTOCMD_ERR(x) \
+( (SdiocCmdNotIssuedErr == (x)) || \
+ (SdiocAutoCmd12CrcErr == (x)) || \
+ (SdiocAutoCmd12Timeout == (x)) || \
+ (SdiocAutoCmd12IndexErr == (x)) || \
+ (SdiocAutoCmd12EndBitErr == (x)) || \
+ (SdiocAutoCmd12NotExecuted == (x)))
+
+/*!< Parameter valid check for SDIOC detect card signal. */
+#define IS_VALID_SDIOC_DETECT_SIG(x) \
+( (SdiocSdcdPinLevel == (x)) || \
+ (SdiocCardDetectTestLevel == (x)))
+
+/*!< Parameter valid check for SDIOC data block count value. */
+#define IS_VALID_SDIOC_BLKCNT(x) ((x) != 0u)
+
+/*!< Parameter valid check for SDIOC data block size value. */
+#define IS_VALID_SDIOC_BLKSIZE(x) (!((x) & 0xF000ul))
+
+/*!< Parameter valid check for SDIOC command value. */
+#define IS_VALID_SDIOC_CMD_VAL(x) (!(0xC0u & (x)))
+
+/*!< Parameter valid check for buffer address. */
+#define IS_VALID_TRANSFER_BUF_ALIGN(x) (!((SDIOC_BUF_ALIGN_SIZE-1ul) & ((uint32_t)(x))))
+
+/*!< Parameter valid check for SDIOC command value. */
+#define IS_VALID_TRANSFER_BUF_LEN(x) (!((SDIOC_BUF_ALIGN_SIZE-1ul) & ((uint32_t)(x))))
+
+/*!< SDIOC unit max count value. */
+#define SDIOC_UNIT_MAX_CNT (ARRAY_SZ(m_astcSdiocInstanceDataLut))
+
+/*!< SDIOC default sdclk frequency. */
+#define SDIOC_SDCLK_400K (400000ul)
+
+/*!< Get the specified register address of the specified SDIOC unit */
+#define SDIOC_ARG01(__SDIOCx__) ((uint32_t)(&((__SDIOCx__)->ARG0)))
+#define SDIOC_BUF01(__SDIOCx__) ((uint32_t)(&((__SDIOCx__)->BUF0)))
+#define SDIOC_RESPx(__SDIOCx__, RESP_REG) ((uint32_t)(&((__SDIOCx__)->RESP0)) + (uint32_t)(RESP_REG))
+
+/* SDIOC buffer align size */
+#define SDIOC_BUF_ALIGN_SIZE (4ul)
+
+/*******************************************************************************
+ * Global variable definitions (declared in header file with 'extern')
+ ******************************************************************************/
+
+/*******************************************************************************
+ * Local function prototypes ('static')
+ ******************************************************************************/
+static en_sdioc_clk_div_t SdiocGetClkDiv(uint32_t u32Exclk,
+ uint32_t u32SdiocClkFreq);
+static stc_sdioc_intern_data_t* SdiocGetInternDataPtr(const M4_SDIOC_TypeDef *SDIOCx);
+
+/*******************************************************************************
+ * Local variable definitions ('static')
+ ******************************************************************************/
+
+/*******************************************************************************
+ * Function implementation - global ('extern') and local ('static')
+ ******************************************************************************/
+
+/**
+ *******************************************************************************
+ ** \brief Get SDIOC clock division.
+ **
+ ** \param [in] u32Exclk Exclk frequency
+ ** \param [in] u32ClkFreq SDIOC clock frequency
+ **
+ ** \retval SdiocClkDiv_1 EXCLK/1
+ ** \retval SdiocClkDiv_2 EXCLK/2
+ ** \retval SdiocClkDiv_4 EXCLK/4
+ ** \retval SdiocClkDiv_8 EXCLK/8
+ ** \retval SdiocClkDiv_16 EXCLK/16
+ ** \retval SdiocClkDiv_32 EXCLK/32
+ ** \retval SdiocClkDiv_64 EXCLK/64
+ ** \retval SdiocClkDiv_128 EXCLK/128
+ ** \retval SdiocClkDiv_256 EXCLK/256
+ **
+ ******************************************************************************/
+static en_sdioc_clk_div_t SdiocGetClkDiv(uint32_t u32Exclk,
+ uint32_t u32ClkFreq)
+{
+ uint32_t u32SdClkDiv = 0ul;
+ en_sdioc_clk_div_t enClockDiv = SdiocClkDiv_256;
+
+ if(0ul != u32ClkFreq)
+ {
+ u32SdClkDiv = u32Exclk / u32ClkFreq;
+ if (u32Exclk % u32ClkFreq)
+ {
+ u32SdClkDiv++;
+ }
+
+ if ((128ul < u32SdClkDiv) && (u32SdClkDiv <= 256ul))
+ {
+ enClockDiv = SdiocClkDiv_256;
+ }
+ else if ((64ul < u32SdClkDiv) && (u32SdClkDiv <= 128ul))
+ {
+ enClockDiv = SdiocClkDiv_128;
+ }
+ else if ((32ul < u32SdClkDiv) && (u32SdClkDiv <= 64ul))
+ {
+ enClockDiv = SdiocClkDiv_64;
+ }
+ else if ((16ul < u32SdClkDiv) && (u32SdClkDiv <= 32ul))
+ {
+ enClockDiv = SdiocClkDiv_32;
+ }
+ else if ((16ul < u32SdClkDiv) && (u32SdClkDiv <= 32ul))
+ {
+ enClockDiv = SdiocClkDiv_32;
+ }
+ else if ((8ul < u32SdClkDiv) && (u32SdClkDiv <= 16ul))
+ {
+ enClockDiv = SdiocClkDiv_16;
+ }
+ else if ((4ul < u32SdClkDiv) && (u32SdClkDiv <= 8ul))
+ {
+ enClockDiv = SdiocClkDiv_8;
+ }
+ else if ((2ul < u32SdClkDiv) && (u32SdClkDiv <= 4ul))
+ {
+ enClockDiv = SdiocClkDiv_4;
+ }
+ else if ((1ul < u32SdClkDiv) && (u32SdClkDiv <= 2ul))
+ {
+ enClockDiv = SdiocClkDiv_2;
+ }
+ else
+ {
+ enClockDiv = SdiocClkDiv_1;
+ }
+ }
+
+ return enClockDiv;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Return the internal data for a certain SDIOC instance.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Pointer to internal data or NULL if instance is not enabled (or not known)
+ **
+ ******************************************************************************/
+static stc_sdioc_intern_data_t* SdiocGetInternDataPtr(const M4_SDIOC_TypeDef *SDIOCx)
+{
+ uint8_t i;
+ stc_sdioc_intern_data_t *pstcInternData = NULL;
+ static stc_sdioc_instance_data_t m_astcSdiocInstanceDataLut[2];
+
+ m_astcSdiocInstanceDataLut[0].SDIOCx = M4_SDIOC1;
+ m_astcSdiocInstanceDataLut[1].SDIOCx = M4_SDIOC2;
+
+ if (NULL != SDIOCx)
+ {
+ for (i = 0u; i < SDIOC_UNIT_MAX_CNT; i++)
+ {
+ if (SDIOCx == m_astcSdiocInstanceDataLut[i].SDIOCx)
+ {
+ pstcInternData = &m_astcSdiocInstanceDataLut[i].stcInternData;
+ break;
+ }
+ }
+ }
+
+ return pstcInternData;
+}
+
+/**
+ *******************************************************************************
+ ** \brief SDIOC instance interrupt service routine
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval None
+ **
+ ******************************************************************************/
+void SDIOC_IrqHandler(M4_SDIOC_TypeDef *SDIOCx)
+{
+ stc_sdioc_intern_data_t *pstcSdiocInternData = SdiocGetInternDataPtr(SDIOCx);
+
+ /* Check for NULL pointer */
+ if (NULL != pstcSdiocInternData)
+ {
+ /**************** Normal interrupt handler ****************/
+ if (1u == SDIOCx->NORINTST_f.CC) /* Command complete */
+ {
+ SDIOCx->NORINTST_f.CC = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnCommandCompleteIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnCommandCompleteIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.TC) /* Transfer complete */
+ {
+ SDIOCx->NORINTST_f.TC = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnTransferCompleteIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnTransferCompleteIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.BGE) /* Block gap event */
+ {
+ SDIOCx->NORINTST_f.BGE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnBlockGapIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnBlockGapIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.BWR) /* Buffer write ready */
+ {
+ SDIOCx->NORINTST_f.BWR = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnBufferWriteReadyIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferWriteReadyIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.BRR) /* Buffer read ready */
+ {
+ SDIOCx->NORINTST_f.BRR = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnBufferReadReadyIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferReadReadyIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.CIST) /* Card insertion */
+ {
+ SDIOCx->NORINTST_f.CIST = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnCardInsertIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardInsertIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.CRM) /* Card removal */
+ {
+ SDIOCx->NORINTST_f.CRM = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnCardRemovalIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardRemovalIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->NORINTST_f.CINT) /* Card interrupt */
+ {
+ if (NULL != pstcSdiocInternData->stcNormalIrqCb.pfnCardIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardIrqCb();
+ }
+ }
+
+ /**************** Error interrupt handler ****************/
+ if (1u == SDIOCx->ERRINTST_f.CTOE) /* Command timeout error */
+ {
+ SDIOCx->ERRINTST_f.CTOE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnCmdTimeoutErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdTimeoutErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.CCE) /* Command CRC error */
+ {
+ SDIOCx->ERRINTST_f.CCE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnCmdCrcErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdCrcErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.CEBE) /* Command end bit error */
+ {
+ SDIOCx->ERRINTST_f.CEBE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnCmdEndBitErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdEndBitErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.CIE) /* Command index error */
+ {
+ SDIOCx->ERRINTST_f.CIE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnCmdIndexErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdIndexErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.DTOE) /* Data timeout error */
+ {
+ SDIOCx->ERRINTST_f.DTOE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnDataTimeoutErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataTimeoutErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.DEBE) /* Data end bit error */
+ {
+ SDIOCx->ERRINTST_f.DEBE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnDataEndBitErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataEndBitErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.DCE) /* Data CRC error */
+ {
+ SDIOCx->ERRINTST_f.DCE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnDataCrcErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataCrcErrIrqCb();
+ }
+ }
+
+ if (1u == SDIOCx->ERRINTST_f.ACE) /* Auto CMD12 error */
+ {
+ SDIOCx->ERRINTST_f.ACE = 1u; /* Clear interrupt flag */
+ if (NULL != pstcSdiocInternData->stcErrorIrqCb.pfnAutoCmdErrIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnAutoCmdErrIrqCb();
+ }
+ }
+ }
+}
+
+/**
+ *******************************************************************************
+ ** \brief Initializes a SDIOC.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] pstcInitCfg Pointer to SDIOC configure structure
+ ** \arg This parameter detail refer @ref stc_sdioc_init_t
+ **
+ ** \retval Ok SDIOC initialized normally
+ ** \retval ErrorTimeout SDIOCx reset timeout
+ ** \retval ErrorInvalidParameter If one of following cases matches:
+ ** - SDIOCx is invalid
+ ** - pstcInitCfg == NULL
+ ** - Other invalid configuration
+ **
+ ******************************************************************************/
+en_result_t SDIOC_Init(M4_SDIOC_TypeDef *SDIOCx,
+ const stc_sdioc_init_t *pstcInitCfg)
+{
+ __IO uint32_t i = 0ul;
+ uint32_t u32Exclk = 0ul;
+ uint32_t u32Cnt = SystemCoreClock / 100ul;
+ en_result_t enRet = ErrorInvalidParameter;
+ stc_sdioc_intern_data_t *pstcSdiocInternData = NULL;
+
+ /* Get pointer to internal data structure. */
+ pstcSdiocInternData = SdiocGetInternDataPtr(SDIOCx);
+ if (NULL != pstcSdiocInternData) /* Check for instance available or not */
+ {
+ /* Reset all */
+ SDIOCx->SFTRST_f.RSTA = 1u;
+ while (0u != SDIOCx->SFTRST_f.RSTA) /* Wait until reset finish */
+ {
+ if (i++ > u32Cnt)
+ {
+ break;
+ }
+ }
+
+ if (i < u32Cnt)
+ {
+ /* Get EXCLK frequency */
+ u32Exclk = SystemCoreClock / (1ul << M4_SYSREG->CMU_SCFGR_f.EXCKS);
+
+ SDIOCx->CLKCON_f.FS = SdiocGetClkDiv(u32Exclk, SdiocClk400K);
+ SDIOCx->CLKCON_f.CE = (uint16_t)1u;
+ SDIOCx->CLKCON_f.ICE = (uint16_t)1u;
+ SDIOCx->PWRCON_f.PWON = (uint8_t)1u; /* Power on */
+
+ /* Enable all status */
+ SDIOCx->ERRINTST = (uint16_t)0x017Fu; /* Clear Error interrupt status */
+ SDIOCx->ERRINTSTEN = (uint16_t)0x017Fu; /* Enable Error interrupt status */
+ SDIOCx->NORINTST = (uint16_t)0x00F7u; /* Clear Normal interrupt status */
+ SDIOCx->NORINTSTEN = (uint16_t)0x01F7u; /* Enable Normal interrupt status */
+
+ /* Enable normal interrupt signal */
+ if (NULL != pstcInitCfg)
+ {
+ if (NULL != pstcInitCfg->pstcNormalIrqEn)
+ {
+ SDIOCx->NORINTSGEN = pstcInitCfg->pstcNormalIrqEn->u16NormalIntsgEn;
+ }
+
+ /* Set normal interrupt callback functions */
+ if (NULL != pstcInitCfg->pstcNormalIrqCb)
+ {
+ pstcSdiocInternData->stcNormalIrqCb.pfnCommandCompleteIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnCommandCompleteIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnTransferCompleteIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnTransferCompleteIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBlockGapIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnBlockGapIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferWriteReadyIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnBufferWriteReadyIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferReadReadyIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnBufferReadReadyIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardInsertIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnCardInsertIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardRemovalIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnCardRemovalIrqCb;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardIrqCb = pstcInitCfg->pstcNormalIrqCb->pfnCardIrqCb;
+ }
+
+ /* Enable error interrupt signal */
+ if (NULL != pstcInitCfg->pstcErrorIrqEn)
+ {
+ SDIOCx->ERRINTSGEN = pstcInitCfg->pstcErrorIrqEn->u16ErrorIntsgEn;
+ }
+
+ /* Set error interrupt callback functions */
+ if (NULL != pstcInitCfg->pstcErrorIrqCb)
+ {
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdTimeoutErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnCmdTimeoutErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdCrcErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnCmdCrcErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdEndBitErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnCmdEndBitErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdIndexErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnCmdIndexErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataTimeoutErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnDataTimeoutErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataEndBitErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnDataEndBitErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataCrcErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnDataCrcErrIrqCb;
+ pstcSdiocInternData->stcErrorIrqCb.pfnAutoCmdErrIrqCb = pstcInitCfg->pstcErrorIrqCb->pfnAutoCmdErrIrqCb;
+ }
+ }
+ enRet = Ok;
+ }
+ else
+ {
+ enRet = ErrorTimeout;
+ }
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief De-Initializes the specified SDIOC unit.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Ok De-Initialize successfully.
+ ** \retval ErrorTimeout SDIOCx reset timeout.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid.
+ **
+ ******************************************************************************/
+en_result_t SDIOC_DeInit(M4_SDIOC_TypeDef *SDIOCx)
+{
+ __IO uint32_t i = 0ul;
+ uint32_t u32Cnt = SystemCoreClock / 100ul;
+ en_result_t enRet = ErrorInvalidParameter;
+ stc_sdioc_intern_data_t *pstcSdiocInternData = NULL;
+
+ /* Get pointer to internal data structure. */
+ pstcSdiocInternData = SdiocGetInternDataPtr(SDIOCx);
+ if (NULL != pstcSdiocInternData) /* Check for instance available or not */
+ {
+ /* Reset all */
+ SDIOCx->SFTRST_f.RSTA = 1u;
+ while (0u != SDIOCx->SFTRST_f.RSTA) /* Wait until reset finish */
+ {
+ if (i++ > u32Cnt)
+ {
+ break;
+ }
+ }
+
+ if (i < u32Cnt)
+ {
+ /* Set normal interrupt callback functions */
+ pstcSdiocInternData->stcNormalIrqCb.pfnCommandCompleteIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnTransferCompleteIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBlockGapIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferWriteReadyIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnBufferReadReadyIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardInsertIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardRemovalIrqCb = NULL;
+ pstcSdiocInternData->stcNormalIrqCb.pfnCardIrqCb = NULL;
+
+ /* Set error interrupt callback functions */
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdTimeoutErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdCrcErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdEndBitErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnCmdIndexErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataTimeoutErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataEndBitErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnDataCrcErrIrqCb = NULL;
+ pstcSdiocInternData->stcErrorIrqCb.pfnAutoCmdErrIrqCb = NULL;
+ enRet = Ok;
+ }
+ else
+ {
+ enRet = ErrorTimeout;
+ }
+ }
+
+ return enRet;
+}
+
+/**
+ * @brief Set SDIOC mode.
+ * @param [in] SDIOCx Pointer to SDIOC instance register base
+ * This parameter can be one of the following values:
+ * @arg M4_SDIOC1: SDIOC unit 1 instance register base
+ * @arg M4_SDIOC2: SDIOC unit 2 instance register base
+ * @param [in] enMode SDIOCx mode
+ * @arg SdiocModeSD: SD mode
+ * @arg SdiocModeMMC: MMC mode
+ */
+void SDIOC_SetMode(const M4_SDIOC_TypeDef *SDIOCx, en_sdioc_mode_t enMode)
+{
+ /* Check parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_MODE(enMode));
+
+ if (M4_SDIOC1 == SDIOCx)
+ {
+ M4_PERIC->SDIOC_SYCTLREG_f.SELMMC1 = (uint32_t)enMode;
+ }
+ else
+ {
+ M4_PERIC->SDIOC_SYCTLREG_f.SELMMC2 = (uint32_t)enMode;
+ }
+}
+
+/**
+ *******************************************************************************
+ ** \brief Send SD command
+ **
+ ** This function sends command on CMD line
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] pstcCmdCfg Pointer to command transfer configuration structure.
+ ** \arg This parameter detail refer @ref stc_sdioc_cmd_cfg_t
+ **
+ ** \retval Ok Command sent normally
+ ** \retval ErrorInvalidParameter If one of following cases matches:
+ ** - SDIOCx is invalid
+ ** - pstcCmdCfg == NULL
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SendCommand(M4_SDIOC_TypeDef *SDIOCx,
+ const stc_sdioc_cmd_cfg_t *pstcCmdCfg)
+{
+ uint32_t u32Addr;
+ stc_sdioc_cmd_field_t stcCmdField;
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for NULL pointer */
+ if ((IS_VALID_SDIOC(SDIOCx)) && (NULL != pstcCmdCfg))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_CMD_VAL(pstcCmdCfg->u8CmdIndex));
+ DDL_ASSERT(IS_VALID_SDIOC_CMD_TYPE(pstcCmdCfg->enCmdType));
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(pstcCmdCfg->enDataPresentEnable));
+ DDL_ASSERT(IS_VALID_SDIOC_RESP_TYPE_NAME(pstcCmdCfg->enRspIndex));
+
+ enRet = Ok;
+ switch (pstcCmdCfg->enRspIndex)
+ {
+ case SdiocCmdNoRsp:
+ stcCmdField.RESTYP = SdiocResponseNoneBit;
+ stcCmdField.CCE = 0u;
+ stcCmdField.ICE = 0u;
+ break;
+ case SdiocCmdRspR2:
+ stcCmdField.RESTYP = SdiocResponse136Bit;
+ stcCmdField.CCE = 1u;
+ stcCmdField.ICE = 0u;
+ break;
+ case SdiocCmdRspR3:
+ case SdiocCmdRspR4:
+ stcCmdField.RESTYP = SdiocResponse48Bit;
+ stcCmdField.CCE = 0u;
+ stcCmdField.ICE = 0u;
+ break;
+ case SdiocCmdRspR1:
+ case SdiocCmdRspR5:
+ case SdiocCmdRspR6:
+ case SdiocCmdRspR7:
+ stcCmdField.RESTYP = SdiocResponse48Bit;
+ stcCmdField.CCE = 1u;
+ stcCmdField.ICE = 1u;
+ break;
+ case SdiocCmdRspR1b:
+ case SdiocCmdRspR5b:
+ stcCmdField.RESTYP = SdiocResponse48BitCheckBusy;
+ stcCmdField.CCE = 1u;
+ stcCmdField.ICE = 1u;
+ break;
+ default:
+ enRet = ErrorInvalidParameter;
+ break;
+ }
+
+ if (enRet == Ok)
+ {
+ stcCmdField.RESERVED2 = (uint16_t)0u;
+ stcCmdField.TYP = (uint16_t)pstcCmdCfg->enCmdType;
+ stcCmdField.IDX = (uint16_t)pstcCmdCfg->u8CmdIndex;
+ stcCmdField.DAT = (uint16_t)(pstcCmdCfg->enDataPresentEnable);
+
+ u32Addr = SDIOC_ARG01(SDIOCx);
+ *(__IO uint32_t *)u32Addr = pstcCmdCfg->u32Argument;
+
+ u32Addr = (uint32_t)&stcCmdField;
+ SDIOCx->CMD = *(uint16_t *)u32Addr;
+ }
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the response received from the card for the last command
+ **
+ ** This function sends command on CMD line
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enRespReg Response Specifies the SDIOC response register.
+ ** \arg SdiocRegResp01 Response0 and Response1 Register
+ ** \arg SdiocRegResp23 Response2 and Response3 Register
+ ** \arg SdiocRegResp45 Response4 and Response5 Register
+ ** \arg SdiocRegResp67 Response6 and Response7 Register
+ **
+ ** \retval The Corresponding response register value
+ **
+ ******************************************************************************/
+uint32_t SDIOC_GetResponse(const M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_response_reg_t enRespReg)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_RESP(enRespReg));
+
+ return *(__IO uint32_t *)SDIOC_RESPx(SDIOCx, enRespReg) ;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Read data from SDIOCx data buffer
+ **
+ ** This function reads 32-bit data from data buffer
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] au8Data Buffer which will store SDIOC_BUFFER data
+ ** \param [in] u32Len Data length
+ **
+ ** \retval Ok Data is read normally
+ ** \retval ErrorInvalidParameter If one of following cases matches:
+ ** - SDIOCx is invalid
+ ** - pu32Data == NULL
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ReadBuffer(M4_SDIOC_TypeDef *SDIOCx,
+ uint8_t au8Data[],
+ uint32_t u32Len)
+{
+ uint32_t i = 0ul;
+ uint32_t u32Temp = 0ul;;
+ __IO uint32_t *SDIO_BUF_REG = NULL;
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx && pu8Data pointer */
+ if ((NULL != au8Data) && \
+ (IS_VALID_SDIOC(SDIOCx)) && \
+ (IS_VALID_TRANSFER_BUF_LEN(u32Len)))
+ {
+ SDIO_BUF_REG = (__IO uint32_t *)SDIOC_BUF01(SDIOCx);
+
+ while (i < u32Len)
+ {
+ u32Temp = *SDIO_BUF_REG;
+ au8Data[i++] = (uint8_t)((u32Temp >> 0ul) & 0x000000FF);
+ au8Data[i++] = (uint8_t)((u32Temp >> 8ul) & 0x000000FF);
+ au8Data[i++] = (uint8_t)((u32Temp >> 16ul) & 0x000000FF);
+ au8Data[i++] = (uint8_t)((u32Temp >> 24ul) & 0x000000FF);
+ }
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Write data to SDIOCx data buffer
+ **
+ ** This function writes 32-bit data to data buffer
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] au8Data Buffer which will be wrote to SDIOC_BUFFER
+ ** \param [in] u32Len Data length
+ **
+ ** \retval Ok Data is written normally
+ ** \retval ErrorInvalidParameter If one of following cases matches:
+ ** - SDIOCx is invalid
+ ** - pu8Data == NULL
+ **
+ ******************************************************************************/
+en_result_t SDIOC_WriteBuffer(M4_SDIOC_TypeDef *SDIOCx,
+ uint8_t au8Data[],
+ uint32_t u32Len)
+{
+ uint32_t i = 0ul;
+ uint32_t u32Temp = 0ul;
+ __IO uint32_t *SDIO_BUF_REG = NULL;
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx && pu8Data pointer */
+ if ((NULL != au8Data) && \
+ (IS_VALID_SDIOC(SDIOCx)) && \
+ (IS_VALID_TRANSFER_BUF_LEN(u32Len)))
+ {
+ SDIO_BUF_REG = (__IO uint32_t *)SDIOC_BUF01(SDIOCx);
+
+ while (i < u32Len)
+ {
+ u32Temp = (((uint32_t)au8Data[i++]) << 0ul) & 0x000000FFul;
+ u32Temp += (((uint32_t)au8Data[i++]) << 8ul) & 0x0000FF00ul;
+ u32Temp += (((uint32_t)au8Data[i++]) << 16ul) & 0x00FF0000ul;
+ u32Temp += (((uint32_t)au8Data[i++]) << 24ul) & 0xFF000000ul;
+
+ *SDIO_BUF_REG = u32Temp;
+ }
+
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Configure SDIOCx data parameters
+ **
+ ** This function writes 32-bit data to data buffer
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] pstcDataCfg Pointer to SDIOC data transfer configuration structure
+ ** \arg This parameter detail refer @ref stc_sdioc_data_cfg_t
+ **
+ ** \retval Ok configure normally
+ ** \retval ErrorInvalidParameter If one of following cases matches:
+ ** - SDIOCx is invalid
+ ** - pstcDataCfg == NULL
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ConfigData(M4_SDIOC_TypeDef *SDIOCx,
+ const stc_sdioc_data_cfg_t *pstcDataCfg)
+{
+ uint16_t u16BlkCnt = (uint16_t)0;
+ uint32_t u32Addr;
+ stc_sdioc_transmode_field_t stcTransModeField = {0};
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx && pstcDataCfg pointer */
+ if ((IS_VALID_SDIOC(SDIOCx)) && (NULL != pstcDataCfg))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_BLKCNT(pstcDataCfg->u16BlkCnt));
+ DDL_ASSERT(IS_VALID_SDIOC_BLKSIZE(pstcDataCfg->u16BlkSize));
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(pstcDataCfg->enAutoCmd12Enable));
+ DDL_ASSERT(IS_VALID_SDIOC_DATA_TIMEOUT(pstcDataCfg->enDataTimeOut));
+ DDL_ASSERT(IS_VALID_SDIOC_TRANSFER_DIR(pstcDataCfg->enTransferDir));
+ DDL_ASSERT(IS_VALID_SDIOC_TRANSFER_MODE(pstcDataCfg->enTransferMode));
+
+ enRet = Ok;
+
+ switch (pstcDataCfg->enTransferMode)
+ {
+ case SdiocTransferSingle:
+ stcTransModeField.MULB = 0u;
+ stcTransModeField.BCE = 0u;
+ break;
+ case SdiocTransferInfinite:
+ stcTransModeField.MULB = 1u;
+ stcTransModeField.BCE = 0u;
+ break;
+ case SdiocTransferMultiple:
+ u16BlkCnt = pstcDataCfg->u16BlkCnt;
+ stcTransModeField.MULB = 1u;
+ stcTransModeField.BCE = 1u;
+ break;
+ case SdiocTransferStopMultiple:
+ stcTransModeField.MULB = 1u;
+ stcTransModeField.BCE = 1u;
+ break;
+ default:
+ enRet = ErrorInvalidParameter;
+ break;
+ }
+
+ if (enRet == Ok)
+ {
+ stcTransModeField.RESERVED0 = (uint16_t)0u;
+ stcTransModeField.DDIR = (uint16_t)(pstcDataCfg->enTransferDir);
+ stcTransModeField.ATCEN = (uint16_t)(pstcDataCfg->enAutoCmd12Enable);
+
+ /* Set the SDIOC Data Transfer Timeout value */
+ SDIOCx->TOUTCON = (uint8_t)(pstcDataCfg->enDataTimeOut);
+ /* Set the SDIOC Block Count value */
+ SDIOCx->BLKCNT = u16BlkCnt;
+ /* Set the SDIOC Block Size value */
+ SDIOCx->BLKSIZE = pstcDataCfg->u16BlkSize;
+ /* Set the SDIOC Data Transfer Mode */
+ u32Addr = (uint32_t)&stcTransModeField;
+ SDIOCx->TRANSMODE = *(uint16_t *)u32Addr;
+ }
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable SDCLK output
+ **
+ ** SD host drives SDCLK line.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enCmd The SDCLK functional state command
+ ** \arg Enable Enable SDCLK function
+ ** \arg Disable Disable SDCLK function
+ **
+ ** \retval Ok SDCLK output of SDIOCx enabled normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SdclkCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+
+ SDIOCx->CLKCON_f.CE = (uint16_t)(enCmd);
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Set the clock division of SD clock
+ **
+ ** This function changes the SD clock division.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enClkDiv SDIOC clock division value
+ ** \arg SdiocClkDiv_1 EXCLK/1
+ ** \arg SdiocClkDiv_2 EXCLK/2
+ ** \arg SdiocClkDiv_4 EXCLK/4
+ ** \arg SdiocClkDiv_8 EXCLK/8
+ ** \arg SdiocClkDiv_16 EXCLK/16
+ ** \arg SdiocClkDiv_32 EXCLK/32
+ ** \arg SdiocClkDiv_64 EXCLK/64
+ ** \arg SdiocClkDiv_128 EXCLK/128
+ ** \arg SdiocClkDiv_256 EXCLK/256
+ **
+ ** \retval Ok SDIOC clock division is changed normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetClkDiv(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_clk_div_t enClkDiv)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_CLK_DIV(enClkDiv));
+
+ /* Set clock division */
+ SDIOCx->CLKCON_f.FS = (uint16_t)enClkDiv;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the clock division of SD clock
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval SdiocClkDiv_1 EXCLK/1
+ ** \retval SdiocClkDiv_2 EXCLK/2
+ ** \retval SdiocClkDiv_4 EXCLK/4
+ ** \retval SdiocClkDiv_8 EXCLK/8
+ ** \retval SdiocClkDiv_16 EXCLK/16
+ ** \retval SdiocClkDiv_32 EXCLK/32
+ ** \retval SdiocClkDiv_64 EXCLK/64
+ ** \retval SdiocClkDiv_128 EXCLK/128
+ **
+ ******************************************************************************/
+en_sdioc_clk_div_t SDIOC_GetClkDiv(M4_SDIOC_TypeDef *SDIOCx)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+
+ return ((en_sdioc_clk_div_t)SDIOCx->CLKCON_f.FS);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the clock division of SD clock
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] u32ClkFreq SDIOC clock frequency
+ **
+ ** \retval Ok Set successfully.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetClk(M4_SDIOC_TypeDef *SDIOCx, uint32_t u32ClkFreq)
+{
+ uint32_t u32Exclk = 0ul;
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Get EXCLK frequency */
+ u32Exclk = SystemCoreClock / (1ul << M4_SYSREG->CMU_SCFGR_f.EXCKS);
+
+ SDIOCx->CLKCON_f.CE = (uint16_t)0u;
+ SDIOCx->CLKCON_f.FS = (uint16_t)SdiocGetClkDiv(u32Exclk, u32ClkFreq);
+ SDIOCx->CLKCON_f.CE = (uint16_t)1u;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Set the bus width of SD Bus
+ **
+ ** This function changes the SD bus width.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enBusWidth Bus width
+ ** \arg SdiocBusWidth1Bit The SDIOC bus width 1 bit
+ ** \arg SdiocBusWidth4Bit The SDIOC bus width 4 bit
+ ** \arg SdiocBusWidth8Bit The SDIOC bus width 8 bit
+ **
+ ** \retval Ok Bus width is set normally
+ ** \retval ErrorInvalidParameter If one of following conditions are met:
+ ** - SDIOCx is invalid
+ ** - enBusWidth is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetBusWidth(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_bus_width_t enBusWidth)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_BUS_WIDTH(enBusWidth));
+
+ enRet = Ok;
+
+ switch (enBusWidth)
+ {
+ case SdiocBusWidth1Bit:
+ SDIOCx->HOSTCON_f.EXDW = 0u;
+ SDIOCx->HOSTCON_f.DW = 0u;
+ break;
+ case SdiocBusWidth4Bit:
+ SDIOCx->HOSTCON_f.EXDW = 0u;
+ SDIOCx->HOSTCON_f.DW = 1u;
+ break;
+ case SdiocBusWidth8Bit:
+ SDIOCx->HOSTCON_f.EXDW = 1u;
+ break;
+ default:
+ enRet = ErrorInvalidParameter;
+ break;
+ }
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the bus width of SD Bus
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval SdiocBusWidth1Bit The SDIOC bus width 1 bit
+ ** \retval SdiocBusWidth4Bit The SDIOC bus width 4 bit
+ ** \retval SdiocBusWidth8Bit The SDIOC bus width 8 bit
+ **
+ ******************************************************************************/
+en_sdioc_bus_width_t SDIOC_GetBusWidth(M4_SDIOC_TypeDef *SDIOCx)
+{
+ en_sdioc_bus_width_t enBusWidth = SdiocBusWidth4Bit;
+
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+
+ if (0u == SDIOCx->HOSTCON_f.EXDW)
+ {
+ if (0u == SDIOCx->HOSTCON_f.DW)
+ {
+ enBusWidth = SdiocBusWidth1Bit;
+ }
+ }
+ else
+ {
+ enBusWidth = SdiocBusWidth8Bit;
+ }
+
+ return enBusWidth;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Set the bus speed mode of SD Bus
+ **
+ ** This function changes the SD bus speed mode.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enSpeedMode Speed mode
+ ** \arg SdiocHighSpeedMode High speed mode
+ ** \arg SdiocNormalSpeedMode Normal speed mode
+ **
+ ** \retval Ok Bus speed is set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetSpeedMode(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_speed_mode_t enSpeedMode)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_SPEED_MODE(enSpeedMode));
+
+ /* Set high speed mode */
+ SDIOCx->HOSTCON_f.HSEN = ((SdiocHighSpeedMode == enSpeedMode) ? 1u : 0u);
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the bus speed mode of SD Bus
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval SdiocHighSpeedMode High speed mode
+ ** \retval SdiocNormalSpeedMode Normal speed mode
+ **
+ ******************************************************************************/
+en_sdioc_speed_mode_t SDIOC_GetSpeedMode(M4_SDIOC_TypeDef *SDIOCx)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+
+ return ((SDIOCx->HOSTCON_f.HSEN) ? SdiocHighSpeedMode : SdiocNormalSpeedMode);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Set data timeout counter value
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enTimeout Data timeout count value
+ ** \arg SdiocDtoSdclk_2_13 Timeout time: SDCLK*2^13
+ ** \arg SdiocDtoSdclk_2_14 Timeout time: SDCLK*2^14
+ ** \arg SdiocDtoSdclk_2_15 Timeout time: SDCLK*2^15
+ ** \arg SdiocDtoSdclk_2_16 Timeout time: SDCLK*2^16
+ ** \arg SdiocDtoSdclk_2_17 Timeout time: SDCLK*2^17
+ ** \arg SdiocDtoSdclk_2_18 Timeout time: SDCLK*2^18
+ ** \arg SdiocDtoSdclk_2_19 Timeout time: SDCLK*2^19
+ ** \arg SdiocDtoSdclk_2_20 Timeout time: SDCLK*2^20
+ ** \arg SdiocDtoSdclk_2_21 Timeout time: SDCLK*2^21
+ ** \arg SdiocDtoSdclk_2_22 Timeout time: SDCLK*2^22
+ ** \arg SdiocDtoSdclk_2_23 Timeout time: SDCLK*2^23
+ ** \arg SdiocDtoSdclk_2_24 Timeout time: SDCLK*2^24
+ ** \arg SdiocDtoSdclk_2_25 Timeout time: SDCLK*2^25
+ ** \arg SdiocDtoSdclk_2_26 Timeout time: SDCLK*2^26
+ ** \arg SdiocDtoSdclk_2_27 Timeout time: SDCLK*2^27
+ **
+ ** \retval Ok Bus speed is set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetDataTimeout(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_data_timeout_t enTimeout)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_DATA_TIMEOUT(enTimeout));
+
+ /* Set data timeout */
+ SDIOCx->TOUTCON_f.DTO = (uint8_t)enTimeout;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get data timeout counter value
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval SdiocDtoSdclk_2_13 Timeout time: SDCLK*2^13
+ ** \retval SdiocDtoSdclk_2_14 Timeout time: SDCLK*2^14
+ ** \retval SdiocDtoSdclk_2_15 Timeout time: SDCLK*2^15
+ ** \retval SdiocDtoSdclk_2_16 Timeout time: SDCLK*2^16
+ ** \retval SdiocDtoSdclk_2_17 Timeout time: SDCLK*2^17
+ ** \retval SdiocDtoSdclk_2_18 Timeout time: SDCLK*2^18
+ ** \retval SdiocDtoSdclk_2_19 Timeout time: SDCLK*2^19
+ ** \retval SdiocDtoSdclk_2_20 Timeout time: SDCLK*2^20
+ ** \retval SdiocDtoSdclk_2_21 Timeout time: SDCLK*2^21
+ ** \retval SdiocDtoSdclk_2_22 Timeout time: SDCLK*2^22
+ ** \retval SdiocDtoSdclk_2_23 Timeout time: SDCLK*2^23
+ ** \retval SdiocDtoSdclk_2_24 Timeout time: SDCLK*2^24
+ ** \retval SdiocDtoSdclk_2_25 Timeout time: SDCLK*2^25
+ ** \retval SdiocDtoSdclk_2_26 Timeout time: SDCLK*2^26
+ ** \retval SdiocDtoSdclk_2_27 Timeout time: SDCLK*2^27
+ **
+ ******************************************************************************/
+en_sdioc_data_timeout_t SDIOC_GetDataTimeout(M4_SDIOC_TypeDef *SDIOCx)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+
+ return (en_sdioc_data_timeout_t)(SDIOCx->TOUTCON_f.DTO);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Set the card detect signal
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enDetectSignal Card detect signal
+ ** \arg SdiocSdcdPinLevel SDCD# is selected (for normal use)
+ ** \arg SdiocCardDetectTestLevel The Card Detect Test Level is selected(for test purpose)
+ **
+ ** \retval Ok Set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SetCardDetectSignal(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_detect_signal_t enDetectSignal)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_DETECT_SIG(enDetectSignal));
+ SDIOCx->HOSTCON_f.CDSS = (uint8_t)enDetectSignal;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get card inserted or not.
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Set Card Inserted
+ ** \retval Reset No Card
+ **
+ ** \note This bit is enabled while the Card Detect Signal Selection is set to 1
+ ** and it indicates card inserted or not.
+ **
+ ******************************************************************************/
+en_flag_status_t SDIOC_GetCardDetectTestLevel(M4_SDIOC_TypeDef *SDIOCx)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+
+ return (en_flag_status_t)(SDIOCx->HOSTCON_f.CDTL);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Power on SD bus power
+ **
+ ** This function starts power supply on SD bus
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Ok Power on normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_BusPowerOn(M4_SDIOC_TypeDef *SDIOCx)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ SDIOCx->PWRCON_f.PWON = 1u;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Power off SD bus power
+ **
+ ** This function stops power supply on SD bus
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Ok Power off normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_BusPowerOff(M4_SDIOC_TypeDef *SDIOCx)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ SDIOCx->PWRCON_f.PWON = 0u;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the function of Stop At Block Gap Request during block gap
+ **
+ ** This function is used to stop data trasnfer of multi-block transfer
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enCmd SDIOC Stop At Block Gap Request functional state
+ ** \arg Enable Enable the function of Stop At Block Gap Request
+ ** \arg Disable Disable the function of Stop At Block Gap Request
+ **
+ ** \retval Ok Set successfully
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_StopAtBlockGapCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+ SDIOCx->BLKGPCON_f.SABGR = (uint8_t)(enCmd);
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Restart data transfer
+ **
+ ** This function is used to restart data transfer when transfer is pending
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ **
+ ** \retval Ok Set successfully
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_RestartTransfer(M4_SDIOC_TypeDef *SDIOCx)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ SDIOCx->BLKGPCON_f.CR = 1u;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the function of Read Wait Control
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enCmd SDIOC Read Wait Control functional state
+ ** \arg Enable Enable the Read Wait Control function
+ ** \arg Disable Disable the Read Wait Control function
+ **
+ ** \retval Ok Set successfully
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ReadWaitCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+ SDIOCx->BLKGPCON_f.RWC = (uint8_t)(enCmd);
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the function of Interrupt At Block Gap
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enCmd SDIOC Interrupt At Block Gap functional state
+ ** \arg Enable Enable the function of Interrupt At Block Gap
+ ** \arg Disable Disable the function of Interrupt At Block Gap
+ **
+ ** \retval Ok Set successfully
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_InterruptAtBlockGapCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+ SDIOCx->BLKGPCON_f.IABG = (uint8_t)(enCmd);
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Generate software reset to SD card
+ **
+ ** This function generates software reset all command to SD card
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enSwResetType Software reset type
+ ** \arg SdiocSwResetAll This reset affects the entire Host Controller except for the card detection circuit.
+ ** \arg SdiocSwResetCmdLine Only part of command circuit is reset.
+ ** \arg SdiocSwResetDataLine Only part of data circuit is reset.
+ **
+ ** \retval Ok Software reset is done normally
+ ** \retval ErrorTimeout SDIOCx reset timeout
+ ** \retval ErrorInvalidParameter If one of following conditions are met:
+ ** - SDIOCx is invalid
+ ** - enSwResetType is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_SoftwareReset(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_sw_reset_t enSwResetType)
+{
+ __IO uint32_t i = 0ul;
+ uint32_t u32Cnt = SystemCoreClock / 100ul;
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_SWRESETTYPE(enSwResetType));
+
+ enRet = Ok;
+ switch (enSwResetType)
+ {
+ case SdiocSwResetAll:
+ SDIOCx->SFTRST_f.RSTA = (uint8_t)1u;
+ while(0u != SDIOCx->SFTRST_f.RSTA) /* Wait until reset finish */
+ {
+ if (i++ > u32Cnt)
+ {
+ break;
+ }
+ }
+ break;
+ case SdiocSwResetCmdLine:
+ SDIOCx->SFTRST_f.RSTC = (uint8_t)1u;
+ while(0u != SDIOCx->SFTRST_f.RSTC) /* Wait until reset finish */
+ {
+ if (i++ > u32Cnt)
+ {
+ break;
+ }
+ }
+ break;
+ case SdiocSwResetDatLine:
+ SDIOCx->SFTRST_f.RSTD = (uint8_t)1u;
+ while(0u != SDIOCx->SFTRST_f.RSTD) /* Wait until reset finish */
+ {
+ if (i++ > u32Cnt)
+ {
+ break;
+ }
+ }
+ break;
+ default:
+ enRet = ErrorInvalidParameter;
+ break;
+ }
+ }
+
+ if (i > u32Cnt)
+ {
+ enRet = ErrorTimeout;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the status of SDIOC host controller
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enHostStatus SDIOC host status
+ ** \arg SdiocCommandInhibitCmd Command Inhibit(CMD). 1: Cannot issue command; 0:Can issue command using only CMD line
+ ** \arg SdiocCommandInhibitData Command Inhibit(DAT). 1: Cannot issue command which uses the DAT line; 0:Can issue command which uses the DAT line
+ ** \arg SdiocDataLineActive 1: DAT Line Active; 0: DAT Line Inactive
+ ** \arg SdiocWriteTransferActive Write Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocReadTransferActive Read Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocBufferWriteEnble 1: Write enable; 0: Write Disable
+ ** \arg SdiocBufferReadEnble 1: Read enable; 0: Read Disable
+ ** \arg SdiocCardInserted 1: Card Inserted; 0: Reset or Debouncing or No Card
+ ** \arg SdiocCardStateStable 1: No Card or Inserted; 0: Reset or Debouncing
+ ** \arg SdiocCardDetectPinLvl 1: Card present; 0: No card present
+ ** \arg SdiocWriteProtectPinLvl 1: Write enabled; 0: Write protected
+ ** \arg SdiocData0PinLvl 1: DAT0 line signal level high; 0: DAT0 line signal level low
+ ** \arg SdiocData1PinLvl 1: DAT1 line signal level high; 0: DAT1 line signal level low
+ ** \arg SdiocData2PinLvl 1: DAT2 line signal level high; 0: DAT2 line signal level low
+ ** \arg SdiocData3PinLvl 1: DAT3 line signal level high; 0: DAT3 line signal level low
+ ** \arg SdiocCmdPinLvl 1: CMD line signal level high; 0: CMD line signal level low
+ **
+ ** \retval Set The specified status is set
+ ** \retval Reset The specified status is zero
+ **
+ ******************************************************************************/
+en_flag_status_t SDIOC_GetStatus(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_host_status_t enHostStatus)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_HOST_STATUS(enHostStatus));
+
+ return ((SDIOCx->PSTAT & ((uint32_t)enHostStatus)) ? Set : Reset);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the specified signal of SDIOC normal interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enNorInt SDIOC normal interrupt
+ ** \arg SdiocCommandComplete Command Complete. 1: Command complete; 0:No command complete
+ ** \arg SdiocTransferComplete Transfer Complete. 1: Data transfer complete; 0:No transfer complete
+ ** \arg SdiocBlockGapEvent Block Gap Event. 1: Transaction stopped at block gap; 0: No Block Gap Event
+ ** \arg SdiocBufferWriteReady Buffer Write Ready. 1: Ready to Write buffer; 0: No ready to Write buffer
+ ** \arg SdiocBufferReadReady Buffer Read Ready. 1: Ready to read buffer; 0: No ready to read buffer
+ ** \arg SdiocCardInsertedInt Write Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocCardRemoval Card Removal. 1: Card removed; 0: Card state stable or Debouncing
+ ** \arg SdiocCardInt Card Interrupt. 1: Generate Card Interrupt; 0: No Card Interrupt
+ ** \arg SdiocErrorInt Error Interrupt. 1: Error; 0: No Error
+ ** \param [in] enCmd SDIOC normal interrupt signal functional state
+ ** \arg Enable Enable the specified signal of SD normal interrupt
+ ** \arg Disable Disable the specified signal of SD normal interrupt
+ **
+ ** \retval Ok Set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_NormalIrqSignalCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_nor_int_sel_t enNorInt,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+ DDL_ASSERT(IS_VALID_SDIOC_NOR_INT(enNorInt));
+
+ if (Enable == enCmd)
+ {
+ SDIOCx->NORINTSGEN |= (uint16_t)enNorInt;
+ }
+ else
+ {
+ SDIOCx->NORINTSGEN &= (uint16_t)(~((uint16_t)enNorInt));
+ }
+
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the status of SDIOC normal interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enNorInt SDIOC normal interrupt
+ ** \arg SdiocCommandComplete Command Complete. 1: Command complete; 0:No command complete
+ ** \arg SdiocTransferComplete Transfer Complete. 1: Data transfer complete; 0:No transfer complete
+ ** \arg SdiocBlockGapEvent Block Gap Event. 1: Transaction stopped at block gap; 0: No Block Gap Event
+ ** \arg SdiocBufferWriteReady Buffer Write Ready. 1: Ready to Write buffer; 0: No ready to Write buffer
+ ** \arg SdiocBufferReadReady Buffer Read Ready. 1: Ready to read buffer; 0: No ready to read buffer
+ ** \arg SdiocCardInsertedInt Write Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocCardRemoval Card Removal. 1: Card removed; 0: Card state stable or Debouncing
+ ** \arg SdiocCardInt Card Interrupt. 1: Generate Card Interrupt; 0: No Card Interrupt
+ ** \arg SdiocErrorInt Error Interrupt. 1: Error; 0: No Error
+ ** \param [in] enCmd SDIOC normal interrupt status functional state
+ ** \arg Enable Enable the specified status of SD normal interrupt
+ ** \arg Disable Disable the specified status of SD normal interrupt
+ **
+ ** \retval Ok Set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_NormalIrqStatusCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_nor_int_sel_t enNorInt,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+ DDL_ASSERT(IS_VALID_SDIOC_NOR_INT(enNorInt));
+
+ if (Enable == enCmd)
+ {
+ SDIOCx->NORINTSTEN |= (uint16_t)enNorInt;
+ }
+ else
+ {
+ SDIOCx->NORINTSTEN &= (uint16_t)(~((uint16_t)enNorInt));
+ }
+
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the flag of SD normal interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enNorInt SDIOC normal interrupt
+ ** \arg SdiocCommandComplete Command Complete. 1: Command complete; 0:No command complete
+ ** \arg SdiocTransferComplete Transfer Complete. 1: Data transfer complete; 0:No transfer complete
+ ** \arg SdiocBlockGapEvent Block Gap Event. 1: Transaction stopped at block gap; 0: No Block Gap Event
+ ** \arg SdiocBufferWriteReady Buffer Write Ready. 1: Ready to Write buffer; 0: No ready to Write buffer
+ ** \arg SdiocBufferReadReady Buffer Read Ready. 1: Ready to read buffer; 0: No ready to read buffer
+ ** \arg SdiocCardInsertedInt Write Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocCardRemoval Card Removal. 1: Card removed; 0: Card state stable or Debouncing
+ ** \arg SdiocCardInt Card Interrupt. 1: Generate Card Interrupt; 0: No Card Interrupt
+ ** \arg SdiocErrorInt Error Interrupt. 1: Error; 0: No Error
+ **
+ ** \retval Set The specified interupt flag is set
+ ** \retval Reset The specified interupt flag is zero
+ **
+ ******************************************************************************/
+en_flag_status_t SDIOC_GetNormalIrqFlag(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_nor_int_flag_t enNorInt)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_NOR_INT(enNorInt));
+
+ return ((SDIOCx->NORINTST & ((uint16_t)enNorInt)) ? Set : Reset);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Clear the flag of SD normal interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enNorInt SDIOC normal interrupt
+ ** \arg SdiocCommandComplete Command Complete. 1: Command complete; 0:No command complete
+ ** \arg SdiocTransferComplete Transfer Complete. 1: Data transfer complete; 0:No transfer complete
+ ** \arg SdiocBlockGapEvent Block Gap Event. 1: Transaction stopped at block gap; 0: No Block Gap Event
+ ** \arg SdiocBufferWriteReady Buffer Write Ready. 1: Ready to Write buffer; 0: No ready to Write buffer
+ ** \arg SdiocBufferReadReady Buffer Read Ready. 1: Ready to read buffer; 0: No ready to read buffer
+ ** \arg SdiocCardInsertedInt Write Transfer Active.1: Transferring data; 0: No valid data
+ ** \arg SdiocCardRemoval Card Removal. 1: Card removed; 0: Card state stable or Debouncing
+ ** \arg SdiocCardInt Card Interrupt. 1: Generate Card Interrupt; 0: No Card Interrupt
+ ** \arg SdiocErrorInt Error Interrupt. 1: Error; 0: No Error
+ **
+ ** \retval Ok Clear successfully.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ClearNormalIrqFlag(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_nor_int_flag_t enNorInt)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_NOR_INT(enNorInt));
+ SDIOCx->NORINTST = (uint16_t)enNorInt;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the signal of SD error interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enErrInt SDIOC error interrupt
+ ** \arg SdiocCmdTimeoutErr Command Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocCmdCrcErr Command CRC Error. 1: Command CRC Error Generated; 0:No Error
+ ** \arg SdiocCmdEndBitErr Command End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocCmdIndexErr Command Index Error. 1: Command Index Error Generatedr; 0:No Error
+ ** \arg SdiocDataTimeoutErr Data Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocDataCrcErr Data CRC Error. 1: Data CRC Error Generated; 0:No Error
+ ** \arg SdiocDataEndBitErr Data End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocAutoCmd12Err Auto CMD12 Error. 1: Error; 0:No Error
+ ** \param [in] enCmd SDIOC error interrupt signal functional state
+ ** \arg Enable Enable the specified signal of SD error interrupt
+ ** \arg Disable Disable the specified signal of SD error interrupt
+ **
+ ** \retval Ok Set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ErrIrqSignalCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_err_int_sel_t enErrInt,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_ERR_INT(enErrInt));
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+
+ if (Enable == enCmd)
+ {
+ SDIOCx->ERRINTSGEN |= (uint16_t)enErrInt;
+ }
+ else
+ {
+ SDIOCx->ERRINTSGEN &= (uint16_t)enErrInt;
+ }
+
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Enable/Disable the status of SD error interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enErrInt SDIOC error interrupt
+ ** \arg SdiocCmdTimeoutErr Command Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocCmdCrcErr Command CRC Error. 1: Command CRC Error Generated; 0:No Error
+ ** \arg SdiocCmdEndBitErr Command End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocCmdIndexErr Command Index Error. 1: Command Index Error Generatedr; 0:No Error
+ ** \arg SdiocDataTimeoutErr Data Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocDataCrcErr Data CRC Error. 1: Data CRC Error Generated; 0:No Error
+ ** \arg SdiocDataEndBitErr Data End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocAutoCmd12Err Auto CMD12 Error. 1: Error; 0:No Error
+ ** \param [in] enCmd SDIOC error interrupt status functional state
+ ** \arg Enable Enable the specified status of SD error interrupt
+ ** \arg Disable Disable the specified status of SD error interrupt
+ **
+ ** \retval Ok Set normally
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ErrIrqStatusCmd(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_err_int_sel_t enErrInt,
+ en_functional_state_t enCmd)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_ERR_INT(enErrInt));
+ DDL_ASSERT(IS_FUNCTIONAL_STATE(enCmd));
+
+ if (Enable == enCmd)
+ {
+ SDIOCx->ERRINTSTEN |= (uint16_t)enErrInt;
+ }
+ else
+ {
+ SDIOCx->ERRINTSTEN &= (uint16_t)enErrInt;
+ }
+
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the flag of SD error interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enErrInt SDIOC error interrupt
+ ** \arg SdiocCmdTimeoutErr Command Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocCmdCrcErr Command CRC Error. 1: Command CRC Error Generated; 0:No Error
+ ** \arg SdiocCmdEndBitErr Command End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocCmdIndexErr Command Index Error. 1: Command Index Error Generatedr; 0:No Error
+ ** \arg SdiocDataTimeoutErr Data Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocDataCrcErr Data CRC Error. 1: Data CRC Error Generated; 0:No Error
+ ** \arg SdiocDataEndBitErr Data End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocAutoCmd12Err Auto CMD12 Error. 1: Error; 0:No Error
+ **
+ ** \retval Set The specified interupt flag is set
+ ** \retval Reset The specified interupt flag is zero
+ **
+ ******************************************************************************/
+en_flag_status_t SDIOC_GetErrIrqFlag(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_err_int_flag_t enErrInt)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_ERR_INT(enErrInt));
+
+ return ((SDIOCx->ERRINTST & ((uint16_t)enErrInt)) ? Set : Reset);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Clear the flag of SD error interrupt
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enErrInt SDIOC error interrupt
+ ** \arg SdiocCmdTimeoutErr Command Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocCmdCrcErr Command CRC Error. 1: Command CRC Error Generated; 0:No Error
+ ** \arg SdiocCmdEndBitErr Command End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocCmdIndexErr Command Index Error. 1: Command Index Error Generatedr; 0:No Error
+ ** \arg SdiocDataTimeoutErr Data Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocDataCrcErr Data CRC Error. 1: Data CRC Error Generated; 0:No Error
+ ** \arg SdiocDataEndBitErr Data End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocAutoCmd12Err Auto CMD12 Error. 1: Error; 0:No Error
+ **
+ ** \retval Ok Clear successfully.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ClearErrIrqFlag(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_err_int_flag_t enErrInt)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_ERR_INT(enErrInt));
+ SDIOCx->ERRINTST = (uint16_t)enErrInt;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Force the specified error interrupt flag
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enErrInt SDIOC error interrupt
+ ** \arg SdiocCmdTimeoutErr Command Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocCmdCrcErr Command CRC Error. 1: Command CRC Error Generated; 0:No Error
+ ** \arg SdiocCmdEndBitErr Command End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocCmdIndexErr Command Index Error. 1: Command Index Error Generatedr; 0:No Error
+ ** \arg SdiocDataTimeoutErr Data Timeout Error. 1: Timer out; 0:No Error
+ ** \arg SdiocDataCrcErr Data CRC Error. 1: Data CRC Error Generated; 0:No Error
+ ** \arg SdiocDataEndBitErr Data End Bit Error. 1: End Bit Error Generated; 0:No Error
+ ** \arg SdiocAutoCmd12Err Auto CMD12 Error. 1: Error; 0:No Error
+ **
+ ** \retval Ok Set successfully.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ForceErrIrqFlag(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_err_int_sel_t enErrInt)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_ERR_INT(enErrInt));
+ SDIOCx->FEE |= (uint16_t)enErrInt;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+/**
+ *******************************************************************************
+ ** \brief Get the status of auto CMD12 error
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enAutoCmdErr SDIOC auto cmd error status selection
+ ** \arg SdiocAutoCmd12NotExecuted Auto CMD12 Not Executed. 1: Not executed; 0:Executed
+ ** \arg SdiocAutoCmd12Timeout Auto CMD12 Timeout Error. 1: Time out; 0:No error
+ ** \arg SdiocAutoCmd12CrcErr Auto CMD12 CRC Error. 1: CRC Error Generated; 0: No error
+ ** \arg SdiocAutoCmd12EndBitErr Auto CMD12 End Bit Error. 1: End Bit Error Generated; 0: No error to Write buffer
+ ** \arg SdiocAutoCmd12IndexErr Auto CMD12 Index Error. 1: Error; 0: No error
+ ** \arg SdiocCmdNotIssuedErr Command Not Issued By Auto CMD12 Error.1: Not Issued; 0: No error
+ **
+ ** \retval Set The specified status flag is set
+ ** \retval Reset The specified status flag is zero
+ **
+ ******************************************************************************/
+en_flag_status_t SDIOC_GetAutoCmdErrStatus(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_atuo_cmd_err_status_t enAutoCmdErr)
+{
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC(SDIOCx));
+ DDL_ASSERT(IS_VALID_SDIOC_AUTOCMD_ERR(enAutoCmdErr));
+
+ return ((SDIOCx->ATCERRST & ((uint16_t)enAutoCmdErr)) ? Set : Reset);
+}
+
+/**
+ *******************************************************************************
+ ** \brief Force the specified auto CMD12 error
+ **
+ ** \param [in] SDIOCx Pointer to SDIOC instance register base
+ ** \arg M4_SDIOC1 SDIOC unit 1 instance register base
+ ** \arg M4_SDIOC2 SDIOC unit 2 instance register base
+ ** \param [in] enAutoCmdErr SDIOC auto cmd error selection
+ ** \arg SdiocAutoCmd12NotExecuted Auto CMD12 Not Executed. 1: Not executed; 0:Executed
+ ** \arg SdiocAutoCmd12Timeout Auto CMD12 Timeout Error. 1: Time out; 0:No error
+ ** \arg SdiocAutoCmd12CrcErr Auto CMD12 CRC Error. 1: CRC Error Generated; 0: No error
+ ** \arg SdiocAutoCmd12EndBitErr Auto CMD12 End Bit Error. 1: End Bit Error Generated; 0: No error to Write buffer
+ ** \arg SdiocAutoCmd12IndexErr Auto CMD12 Index Error. 1: Error; 0: No error
+ ** \arg SdiocCmdNotIssuedErr Command Not Issued By Auto CMD12 Error.1: Not Issued; 0: No error
+ **
+ ** \retval Ok Set successfully.
+ ** \retval ErrorInvalidParameter SDIOCx is invalid
+ **
+ ******************************************************************************/
+en_result_t SDIOC_ForceAutoCmdErr(M4_SDIOC_TypeDef *SDIOCx,
+ en_sdioc_atuo_cmd_err_sel_t enAutoCmdErr)
+{
+ en_result_t enRet = ErrorInvalidParameter;
+
+ /* Check for SDIOCx pointer */
+ if (IS_VALID_SDIOC(SDIOCx))
+ {
+ /* Check the parameters */
+ DDL_ASSERT(IS_VALID_SDIOC_AUTOCMD_ERR(enAutoCmdErr));
+ SDIOCx->FEA |= (uint16_t)enAutoCmdErr;
+ enRet = Ok;
+ }
+
+ return enRet;
+}
+
+//@} // SdiocGroup
+
+/*******************************************************************************
+ * EOF (not truncated)
+ ******************************************************************************/