123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491 |
- /*
- ******************************************************************************
- * @file HAL_I2S.c
- * @version V1.0.0
- * @date 2020
- * @brief I2S HAL module driver.
- * This file provides firmware functions to manage the following
- * functionalities of the Integrated Interchip Sound (I2S) peripheral:
- * + Initialization functions
- * + IO operation functions
- * + Peripheral State
- ******************************************************************************
- */
- #include "ACM32Fxx_HAL.h"
- /*********************************************************************************
- * Function : HAL_I2S_IRQHandler
- * Description : This function handles I2S interrupt request.
- * Input :
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- void HAL_I2S_IRQHandler(I2S_HandleTypeDef *hi2s)
- {
- /* Tx Buffer empty */
- if (hi2s->Instance->STATUS & I2S_STATUS_TXBE)
- {
- if (hi2s->u32_Tx_Count < hi2s->u32_Tx_Size)
- {
- hi2s->Instance->DAT = hi2s->u32_Tx_Buffer[hi2s->u32_Tx_Count++];
- }
- else
- {
- hi2s->Instance->IE &= ~I2S_DIE_TBEIE;
-
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- }
- }
-
- /* Rx Buffer not empty */
- if (hi2s->Instance->STATUS & I2S_STATUS_RXBNE)
- {
- if (hi2s->u32_Rx_Count < hi2s->u32_Rx_Size)
- {
- hi2s->u32_Tx_Buffer[hi2s->u32_Rx_Count++] = hi2s->Instance->DAT;
- }
- else
- {
- /* Disable I2S */
- hi2s->Instance->CTL &= ~I2S_CTL_I2SEN;
-
- hi2s->Instance->IE &= ~I2S_DIE_RBNEIE;
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- }
- }
- }
- /*********************************************************************************
- * Function : HAL_I2S_MspInit
- * Description :
- * Input :
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- __weak void HAL_I2S_MspInit(I2S_HandleTypeDef *hi2s)
- {
- /*
- NOTE : This function should be modified by the user.
- */
-
- /* For Example */
- GPIO_InitTypeDef GPIO_Handle;
-
- if (hi2s->Instance == I2S1)
- {
- /* Enable Clock */
- System_Module_Enable(EN_I2S1);
- System_Module_Enable(EN_GPIOAB);
- /* I2S1 WS PortA Pin4 */
- /* I2S1 CLK PortA Pin5 */
- /* I2S1 MCK PortA Pin6 */
- /* I2S1 SD PortA Pin7 */
- GPIO_Handle.Pin = GPIO_PIN_4 | GPIO_PIN_5 | GPIO_PIN_6 | GPIO_PIN_7;
- GPIO_Handle.Mode = GPIO_MODE_AF_PP;
- GPIO_Handle.Pull = GPIO_PULLUP;
- GPIO_Handle.Alternate = GPIO_FUNCTION_8;
- HAL_GPIO_Init(GPIOA, &GPIO_Handle);
- /* Clear Pending Interrupt */
- NVIC_ClearPendingIRQ(I2S_IRQn);
-
- /* Enable External Interrupt */
- NVIC_EnableIRQ(I2S_IRQn);
- }
- }
- /*********************************************************************************
- * Function : HAL_I2S_MspDeInit
- * Description :
- * Input :
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- __weak void HAL_I2S_MspDeInit(I2S_HandleTypeDef *hi2s)
- {
- /*
- NOTE : This function should be modified by the user.
- */
-
- /* For Example */
- if (hi2s->Instance == I2S1)
- {
- /* I2S1 WS PortA Pin4 */
- /* I2S1 CLK PortA Pin5 */
- /* I2S1 MCK PortA Pin6 */
- /* I2S1 SD PortA Pin7 */
- HAL_GPIO_DeInit(GPIOA, GPIO_PIN_4 | GPIO_PIN_5 | GPIO_PIN_6 | GPIO_PIN_7);
- /* Clear Pending Interrupt */
- NVIC_ClearPendingIRQ(I2S_IRQn);
-
- /* Disable External Interrupt */
- NVIC_DisableIRQ(I2S_IRQn);
- }
- }
- /*********************************************************************************
- * Function : HAL_I2S_Init
- * Description : Initializes the I2S according to the specified parameters
- * in the I2S_InitTypeDef and create the associated handle.
- * Input : hi2s: pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Init(I2S_HandleTypeDef *hi2s)
- {
- #if (USE_FULL_ASSERT == 1)
- /* Check I2S Parameter */
- if (!IS_I2S_MODE(hi2s->Init.u32_Mode)) return HAL_ERROR;
- if (!IS_I2S_STANDARD(hi2s->Init.u32_Standard)) return HAL_ERROR;
- if (!IS_I2S_DATAFORMAT(hi2s->Init.u32_DataFormat)) return HAL_ERROR;
- if (!IS_I2S_MCLK_OUTPUT(hi2s->Init.u32_MCLKOutput)) return HAL_ERROR;
- if (!IS_I2S_MCLK_CPOL(hi2s->Init.u32_CPOL)) return HAL_ERROR;
- if (!IS_I2S_OF(hi2s->Init.u32_FreqOF)) return HAL_ERROR;
- if (!IS_I2S_DIV(hi2s->Init.u32_FreqDIV)) return HAL_ERROR;
- #endif
- /* Init the low level hardware : GPIO, CLOCK, CORTEX...etc */
- HAL_I2S_MspInit(hi2s);
-
- /* Clear Config */
- hi2s->Instance->CTL = 0x00000000;
- hi2s->Instance->PSC = 0x00000000;
- /* Mode、Standard、CPOL、Dataformat */
- hi2s->Instance->CTL = hi2s->Init.u32_Mode | hi2s->Init.u32_Standard | hi2s->Init.u32_CPOL | hi2s->Init.u32_DataFormat;
- /* Frequency */
- hi2s->Instance->PSC = hi2s->Init.u32_MCLKOutput | hi2s->Init.u32_FreqOF | hi2s->Init.u32_FreqDIV;
- /* I2S Enable */
- if (hi2s->Init.u32_Mode != I2S_MODE_MASTER_RX)
- {
- hi2s->Instance->CTL |= I2S_CTL_I2SEN;
- }
-
- /* I2S Status ready */
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_DeInit
- * Description : DeInitializes the I2S peripheral
- * Input : hi2s: pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_DeInit(I2S_HandleTypeDef *hi2s)
- {
- /* Check the I2S handle allocation */
- if (hi2s == NULL)
- {
- return HAL_ERROR;
- }
- /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
- HAL_I2S_MspDeInit(hi2s);
-
- System_Module_Reset(RST_I2S1);
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Transmit
- * Description : Transmit an amount of data in blocking mode
- * Input : hi2s: pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be sent
- * Input : fu32_Timeout: Timeout duration
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Transmit(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size, uint32_t fu32_Timeout)
- {
- uint32_t i;
- uint32_t lu32_Timeout;
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
-
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
-
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_TX;
-
- /* transmit */
- for (i = 0; i < fu32_Size; i++)
- {
- hi2s->Instance->DAT = fp32_Data[i];
- /* have no timeout */
- if (fu32_Timeout == 0)
- {
- while(!(hi2s->Instance->STATUS & I2S_STATUS_TXBE));
- }
- else
- {
- lu32_Timeout = fu32_Timeout * 0xFF;
- while(!(hi2s->Instance->STATUS & I2S_STATUS_TXBE))
- {
- if (lu32_Timeout-- == 0)
- {
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
-
- return HAL_TIMEOUT;
- }
- }
- }
- }
- /* Wait for the last Byte */
- while (hi2s->Instance->STATUS & I2S_STATUS_TRANS);
-
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Receive
- * Description : Receive an amount of data in blocking mode
- * Input : hi2s pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: a 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be Receive
- * Input : fu32_Timeout: Timeout duration
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Receive(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size, uint32_t fu32_Timeout)
- {
- uint32_t i;
- uint32_t lu32_Timeout;
-
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_RX;
- /* I2S Enable */
- hi2s->Instance->CTL |= I2S_CTL_I2SEN;
-
- /* Receive */
- for (i = 0; i < fu32_Size; i++)
- {
- /* have no timeout */
- if (fu32_Timeout == 0)
- {
- while(!(hi2s->Instance->STATUS & I2S_STATUS_RXBNE));
- fp32_Data[i] = hi2s->Instance->DAT;
- }
- else
- {
- lu32_Timeout = fu32_Timeout * 0xFF;
- while(!(hi2s->Instance->STATUS & I2S_STATUS_RXBNE))
- {
- if (lu32_Timeout-- == 0)
- {
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- return HAL_TIMEOUT;
- }
- }
- fp32_Data[i] = hi2s->Instance->DAT;
- }
- }
- /* Disable I2S */
- hi2s->Instance->CTL &= ~I2S_CTL_I2SEN;
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Transmit_IT
- * Description : Transmit an amount of data in non-blocking mode with Interrupt
- * Input : hi2s pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: a 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be send
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Transmit_IT(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size)
- {
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_TX;
-
- hi2s->u32_Tx_Buffer = fp32_Data;
- hi2s->u32_Tx_Size = fu32_Size;
- hi2s->u32_Tx_Count = 0;
-
- hi2s->Instance->IE |= I2S_DIE_TBEIE;
-
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Receive_IT
- * Description : Receive an amount of data in non-blocking mode with Interrupt
- * Input : hi2s pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: a 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be Receive
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Receive_IT(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size)
- {
- uint32_t lu32_Tempvalue;
-
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
-
- /* Clear Rx Buffer */
- while (hi2s->Instance->STATUS & I2S_STATUS_RXBNE)
- {
- lu32_Tempvalue = hi2s->Instance->DAT;
- }
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_RX;
- hi2s->u32_Rx_Buffer = fp32_Data;
- hi2s->u32_Rx_Size = fu32_Size;
- hi2s->u32_Rx_Count = 0;
- hi2s->Instance->IE |= I2S_DIE_RBNEIE;
- /* I2S Enable */
- hi2s->Instance->CTL |= I2S_CTL_I2SEN;
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Transmit_DMA
- * Description : Transmit an amount of data in non-blocking mode with DMA
- * Input : hi2s: pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be sent
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Transmit_DMA(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size)
- {
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
- /* DMA transfer complete */
- if (!(hi2s->I2S_Status & I2S_STATUS_TRANS))
- {
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- }
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_TX;
- hi2s->Instance->IE |= I2S_DIE_DMATEN;
- HAL_DMA_Start_IT(hi2s->HDMA_Tx, (uint32_t)fp32_Data, (uint32_t)&hi2s->Instance->DAT, fu32_Size);
-
- return HAL_OK;
- }
- /*********************************************************************************
- * Function : HAL_I2S_Receive_DMA
- * Description : Receive an amount of data in non-blocking mode with DMA
- * Input : hi2s pointer to a I2S_HandleTypeDef structure that contains
- * the configuration information for I2S module
- * Input : fp32_Data: a 32-bit pointer to data buffer.
- * Input : Size: number of data sample to be Receive
- * Outpu :
- * Author : Chris_Kyle Data : 2020定
- **********************************************************************************/
- HAL_StatusTypeDef HAL_I2S_Receive_DMA(I2S_HandleTypeDef *hi2s, uint32_t *fp32_Data, uint32_t fu32_Size)
- {
- /* Parameter Check */
- if ((fp32_Data == NULL) || (fu32_Size == 0U))
- {
- return HAL_ERROR;
- }
- /* DMA transfer complete */
- if (!(hi2s->I2S_Status & I2S_STATUS_TRANS))
- {
- hi2s->I2S_Status = HAL_I2S_STATE_READY;
- }
- /* I2S Ready? */
- if (hi2s->I2S_Status != HAL_I2S_STATE_READY)
- {
- return HAL_BUSY;
- }
- hi2s->I2S_Status = HAL_I2S_STATE_BUSY_RX;
- hi2s->Instance->IE |= I2S_DIE_DMATEN;
- HAL_DMA_Start_IT(hi2s->HDMA_Rx, (uint32_t)&hi2s->Instance->DAT, (uint32_t)fp32_Data, fu32_Size);
- return HAL_OK;
- }
|