/**
  ******************************************************************************
  * @file    stm32f3xx_hal_i2s_ex.c
  * @author  MCD Application Team
  * @brief   I2S Extended HAL module driver.
  *          This file provides firmware functions to manage the following
  *          functionalities of I2S Extended peripheral:
  *           + Extended features Functions
  *
  @verbatim
  ==============================================================================
                    ##### I2S Extended features #####
  ==============================================================================
 [..]
    (#) In I2S full duplex mode, each SPI peripheral is able to manage sending and receiving
        data simultaneously using two data lines. Each SPI peripheral has an extended block
        called I2Sxext ie. I2S2ext for SPI2 and I2S3ext for SPI3).
    (#) The Extended block is not a full SPI IP, it is used only as I2S slave to
        implement full duplex mode. The Extended block uses the same clock sources
        as its master.

    (#) Both I2Sx and I2Sx_ext can be configured as transmitters or receivers.

     -@- Only I2Sx can deliver SCK and WS to I2Sx_ext in full duplex mode, where
         I2Sx can be I2S2 or I2S3.

 ===============================================================================
                  ##### How to use this driver #####
 ===============================================================================
 [..]
   Three mode of operations are available within this driver :

   *** Polling mode IO operation ***
   =================================
   [..]
     (+) Send and receive in the same time an amount of data in blocking mode using HAL_I2S_TransmitReceive()

   *** Interrupt mode IO operation ***
   ===================================
   [..]
     (+) Send and receive in the same time an amount of data in non blocking mode using HAL_I2S_TransmitReceive_IT()
     (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
     (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_TxCpltCallback
     (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
     (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_RxCpltCallback
     (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
         add his own code by customization of function pointer HAL_I2S_ErrorCallback

   *** DMA mode IO operation ***
   ==============================
   [..]
     (+) Send and receive an amount of data in non blocking mode (DMA) using HAL_I2S_TransmitReceive_DMA()
     (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
     (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_TxCpltCallback
     (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
     (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
         add his own code by customization of function pointer HAL_I2S_RxCpltCallback
     (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
         add his own code by customization of function pointer HAL_I2S_ErrorCallback
     (+) Pause the DMA Transfer using HAL_I2S_DMAPause()
     (+) Resume the DMA Transfer using HAL_I2S_DMAResume()
     (+) Stop the DMA Transfer using HAL_I2S_DMAStop()

  @endverbatim
  ******************************************************************************
  * @attention
  *
  * <h2><center>&copy; COPYRIGHT(c) 2016 STMicroelectronics</center></h2>
  *
  * Redistribution and use in source and binary forms, with or without modification,
  * are permitted provided that the following conditions are met:
  *   1. Redistributions of source code must retain the above copyright notice,
  *      this list of conditions and the following disclaimer.
  *   2. Redistributions in binary form must reproduce the above copyright notice,
  *      this list of conditions and the following disclaimer in the documentation
  *      and/or other materials provided with the distribution.
  *   3. Neither the name of STMicroelectronics nor the names of its contributors
  *      may be used to endorse or promote products derived from this software
  *      without specific prior written permission.
  *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
  ******************************************************************************
  */
/*
  Additional Figure: The Extended block uses the same clock sources as its master.

                +-----------------------+
    I2Sx_SCK    |                       |
  ----------+-->|          I2Sx         |------------------->I2Sx_SD(in/out)
         +--|-->|                       |
        |   |   +-----------------------+
        |   |
 I2S_WS |   |
 ------>|   |
        |   |   +-----------------------+
        |   +-->|                       |
        |       |       I2Sx_ext        |------------------->I2Sx_extSD(in/out)
         +----->|                       |
                +-----------------------+
*/

/* Includes ------------------------------------------------------------------*/
#include "stm32f3xx_hal.h"

#ifdef HAL_I2S_MODULE_ENABLED

#if defined(STM32F302xE) || defined(STM32F303xE) || defined(STM32F398xx) || \
    defined(STM32F302xC) || defined(STM32F303xC) || defined(STM32F358xx) || \
    defined(STM32F301x8) || defined(STM32F302x8) || defined(STM32F318xx) || \
    defined(STM32F373xC) || defined(STM32F378xx)

/** @addtogroup STM32F3xx_HAL_Driver
  * @{
  */

/** @defgroup I2SEx I2SEx
  * @brief I2S Extended HAL module driver
  * @{
  */

#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)

/* Private typedef -----------------------------------------------------------*/
/** @defgroup I2SEx_Private_Typedef I2S Extended Private Typedef
  * @{
  */
typedef enum
{
  I2S_USE_I2S      = 0x00U,   /*!< I2Sx should be used           */
  I2S_USE_I2SEXT   = 0x01    /*!< I2Sx_ext should be used       */
}I2S_UseTypeDef;
/**
  * @}
  */

/* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
/* Private function prototypes -----------------------------------------------*/
/** @defgroup I2SEx_Private_Functions I2S Extended Private Functions
  * @{
  */
static void I2S_TxRxDMACplt(DMA_HandleTypeDef *hdma);
static void I2S_TxRxDMAHalfCplt(DMA_HandleTypeDef *hdma);
static void I2S_TxRxDMAError(DMA_HandleTypeDef *hdma);
static void I2S_FullDuplexTx_IT(I2S_HandleTypeDef *hi2s, I2S_UseTypeDef i2sUsed);
static void I2S_FullDuplexRx_IT(I2S_HandleTypeDef *hi2s, I2S_UseTypeDef i2sUsed);
static HAL_StatusTypeDef I2S_FullDuplexWaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag,
                                                                 uint32_t State, uint32_t Timeout, I2S_UseTypeDef i2sUsed);
/**
  * @}
  */

/**
  * @}
  */
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

/* Exported functions ---------------------------------------------------------*/

/** @addtogroup I2S I2S
  * @{
  */

/** @addtogroup I2S_Exported_Functions I2S Exported Functions
  * @{
  */

/** @addtogroup  I2S_Exported_Functions_Group1 Initialization and de-initialization functions
  *  @brief    Initialization and Configuration functions
  *
@verbatim
 ===============================================================================
              ##### Initialization and de-initialization functions #####
 ===============================================================================
    [..]  This subsection provides a set of functions allowing to initialize and
          de-initialiaze the I2Sx peripheral in simplex mode:

      (+) User must Implement HAL_I2S_MspInit() function in which he configures
          all related peripherals resources (CLOCK, GPIO, DMA, IT and NVIC ).

      (+) Call the function HAL_I2S_Init() to configure the selected device with
          the selected configuration:
        (++) Mode
        (++) Standard
        (++) Data Format
        (++) MCLK Output
        (++) Audio frequency
        (++) Polarity

      (+) Call the function HAL_I2S_DeInit() to restore the default configuration
          of the selected I2Sx periperal.
@endverbatim
  * @{
  */

/**
  * @brief Initializes the I2S according to the specified parameters
  *         in the I2S_InitTypeDef and create the associated handle.
  * @param hi2s: I2S handle
  * @retval HAL status
  */
HAL_StatusTypeDef HAL_I2S_Init(I2S_HandleTypeDef *hi2s)
{
  uint16_t tmpreg = 0U, i2sdiv = 2U, i2sodd = 0U, packetlength = 1U;
  uint32_t tmp = 0U, i2sclk = 0U;
#if defined(SPI_I2S_FULLDUPLEX_SUPPORT)
  RCC_PeriphCLKInitTypeDef rccperiphclkinit;
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

  /* Check the I2S handle allocation */
  if(hi2s == NULL)
  {
    return HAL_ERROR;
  }

  /* Check the parameters */
  assert_param(IS_I2S_ALL_INSTANCE(hi2s->Instance));
  assert_param(IS_I2S_MODE(hi2s->Init.Mode));
  assert_param(IS_I2S_STANDARD(hi2s->Init.Standard));
  assert_param(IS_I2S_DATA_FORMAT(hi2s->Init.DataFormat));
  assert_param(IS_I2S_MCLK_OUTPUT(hi2s->Init.MCLKOutput));
  assert_param(IS_I2S_AUDIO_FREQ(hi2s->Init.AudioFreq));
  assert_param(IS_I2S_CPOL(hi2s->Init.CPOL));
  assert_param(IS_I2S_CLOCKSOURCE(hi2s->Init.ClockSource));
  assert_param(IS_I2S_FULLDUPLEX_MODE(hi2s->Init.FullDuplexMode));

  hi2s->State = HAL_I2S_STATE_BUSY;

  /* Init the low level hardware : GPIO, CLOCK, CORTEX...etc */
  HAL_I2S_MspInit(hi2s);

  /*----------------------- SPIx I2SCFGR & I2SPR Configuration -----------------*/
  /* Clear I2SMOD, I2SE, I2SCFG, PCMSYNC, I2SSTD, CKPOL, DATLEN and CHLEN bits */
  hi2s->Instance->I2SCFGR &= ~(SPI_I2SCFGR_CHLEN | SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CKPOL | \
                               SPI_I2SCFGR_I2SSTD | SPI_I2SCFGR_PCMSYNC | SPI_I2SCFGR_I2SCFG | \
                               SPI_I2SCFGR_I2SE | SPI_I2SCFGR_I2SMOD);
  hi2s->Instance->I2SPR = 0x0002U;

  /* Get the I2SCFGR register value */
  tmpreg = hi2s->Instance->I2SCFGR;

  /* If the default value has to be written, reinitialize i2sdiv and i2sodd*/
  if(hi2s->Init.AudioFreq == I2S_AUDIOFREQ_DEFAULT)
  {
    i2sodd = (uint16_t)0U;
    i2sdiv = (uint16_t)2U;
  }
  /* If the requested audio frequency is not the default, compute the prescaler */
  else
  {
    /* Check the frame length (For the Prescaler computing) *******************/
    if(hi2s->Init.DataFormat == I2S_DATAFORMAT_16B)
    {
      /* Packet length is 16 bits */
      packetlength = 1U;
    }
    else
    {
      /* Packet length is 32 bits */
      packetlength = 2U;
    }

    /* Get I2S source Clock frequency  ****************************************/
#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
    rccperiphclkinit.PeriphClockSelection = RCC_PERIPHCLK_I2S;

    /* If an external I2S clock has to be used, the specific define should be set
    in the project configuration or in the stm32f3xx_conf.h file */
    if(hi2s->Init.ClockSource == I2S_CLOCK_EXTERNAL)
    {
      /* Set external clock as I2S clock source */
      rccperiphclkinit.I2sClockSelection = RCC_I2SCLKSOURCE_EXT;
      HAL_RCCEx_PeriphCLKConfig(&rccperiphclkinit);

      /* Set the I2S clock to the external clock  value */
      i2sclk = EXTERNAL_CLOCK_VALUE;
    }
    else
    {
      /* Set SYSCLK as I2S clock source */
      rccperiphclkinit.I2sClockSelection = RCC_I2SCLKSOURCE_SYSCLK;
      HAL_RCCEx_PeriphCLKConfig(&rccperiphclkinit);

      /* Get the I2S source clock value */
      i2sclk = HAL_RCC_GetSysClockFreq();
    }
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

#if defined (STM32F373xC) || defined (STM32F378xx)
    if(hi2s->Instance == SPI1)
    {
      i2sclk = HAL_RCC_GetPCLK2Freq();
    }
    else if((hi2s->Instance == SPI2) || (hi2s->Instance == SPI3))
    {
      i2sclk = HAL_RCC_GetPCLK1Freq();
    }
#endif /* STM32F373xC || STM32F378xx */

    /* Compute the Real divider depending on the MCLK output state, with a floating point */
    if(hi2s->Init.MCLKOutput == I2S_MCLKOUTPUT_ENABLE)
    {
      /* MCLK output is enabled */
      tmp = (uint16_t)(((((i2sclk / 256U) * 10U) / hi2s->Init.AudioFreq)) + 5U);
    }
    else
    {
      /* MCLK output is disabled */
      tmp = (uint16_t)(((((i2sclk / (32U * packetlength)) *10U ) / hi2s->Init.AudioFreq)) + 5U);
    }

    /* Remove the flatting point */
    tmp = tmp / 10U;

    /* Check the parity of the divider */
    i2sodd = (uint16_t)(tmp & (uint16_t)0x0001U);

    /* Compute the i2sdiv prescaler */
    i2sdiv = (uint16_t)((tmp - i2sodd) / 2U);

    /* Get the Mask for the Odd bit (SPI_I2SPR[8]) register */
    i2sodd = (uint16_t) (i2sodd << 8U);
  }

  /* Test if the divider is 1 or 0 or greater than 0xFFU */
  if((i2sdiv < 2U) || (i2sdiv > 0xFFU))
  {
    /* Set the default values */
    i2sdiv = 2U;
    i2sodd = 0U;
  }

  /* Write to SPIx I2SPR register the computed value */
  hi2s->Instance->I2SPR = (uint16_t)((uint16_t)i2sdiv | (uint16_t)(i2sodd | (uint16_t)hi2s->Init.MCLKOutput));

  /* Configure the I2S with the I2S_InitStruct values */
  tmpreg |= (uint16_t)((uint16_t)SPI_I2SCFGR_I2SMOD | (uint16_t)(hi2s->Init.Mode | \
                       (uint16_t)(hi2s->Init.Standard | (uint16_t)(hi2s->Init.DataFormat | \
                       (uint16_t)hi2s->Init.CPOL))));

  /* Write to SPIx I2SCFGR */
  hi2s->Instance->I2SCFGR = tmpreg;

#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
  if (hi2s->Init.FullDuplexMode == I2S_FULLDUPLEXMODE_ENABLE)
  {
    /* Clear I2SMOD, I2SE, I2SCFG, PCMSYNC, I2SSTD, CKPOL, DATLEN and CHLEN bits */
    I2SxEXT(hi2s->Instance)->I2SCFGR &= ~(SPI_I2SCFGR_CHLEN | SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CKPOL | \
                                          SPI_I2SCFGR_I2SSTD | SPI_I2SCFGR_PCMSYNC | SPI_I2SCFGR_I2SCFG | \
                                          SPI_I2SCFGR_I2SE | SPI_I2SCFGR_I2SMOD);
    I2SxEXT(hi2s->Instance)->I2SPR = 0x0002U;

    /* Get the I2SCFGR register value */
    tmpreg = I2SxEXT(hi2s->Instance)->I2SCFGR;

    /* Get the mode to be configured for the extended I2S */
    if((hi2s->Init.Mode == I2S_MODE_MASTER_TX) || (hi2s->Init.Mode == I2S_MODE_SLAVE_TX))
    {
      tmp = I2S_MODE_SLAVE_RX;
    }
    else
    {
      if((hi2s->Init.Mode == I2S_MODE_MASTER_RX) || (hi2s->Init.Mode == I2S_MODE_SLAVE_RX))
      {
        tmp = I2S_MODE_SLAVE_TX;
      }
    }

    /* Configure the I2S Slave with the I2S Master parameter values */
    tmpreg |= (uint16_t)((uint16_t)SPI_I2SCFGR_I2SMOD | (uint16_t)(tmp | \
                         (uint16_t)(hi2s->Init.Standard | (uint16_t)(hi2s->Init.DataFormat | \
                         (uint16_t)hi2s->Init.CPOL))));

    /* Write to SPIx I2SCFGR */
    I2SxEXT(hi2s->Instance)->I2SCFGR = tmpreg;
  }
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

  hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
  hi2s->State= HAL_I2S_STATE_READY;

  return HAL_OK;
}
/**
  * @}
  */

#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
/** @addtogroup  I2S_Exported_Functions_Group2 IO operation functions
  * @{
  */

/**
  * @brief  This function handles I2S/I2Sext interrupt requests in full-duplex mode.
  * @param  hi2s: I2S handle
  * @retval HAL status
  */
void HAL_I2S_FullDuplex_IRQHandler(I2S_HandleTypeDef *hi2s)
{
  __IO uint32_t i2ssr = hi2s->Instance->SR ;
  __IO uint32_t i2sextsr = I2SxEXT(hi2s->Instance)->SR;

  /* Check if the I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX Mode is selected */
  if(((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_TX) || ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX))
  {
    /* I2S in mode Transmitter -------------------------------------------------*/
    if(((i2ssr & I2S_FLAG_TXE) == I2S_FLAG_TXE) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_TXE) != RESET))
    {
      /* When the I2S mode is configured as I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX,
      the I2S TXE interrupt will be generated to manage the full-duplex transmit phase. */
      I2S_FullDuplexTx_IT(hi2s, I2S_USE_I2S);
    }

    /* I2Sext in mode Receiver -----------------------------------------------*/
    if(((i2sextsr & I2S_FLAG_RXNE) == I2S_FLAG_RXNE) && (__HAL_I2SEXT_GET_IT_SOURCE(hi2s, I2S_IT_RXNE) != RESET))
    {
      /* When the I2S mode is configured as I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX,
      the I2Sext RXNE interrupt will be generated to manage the full-duplex receive phase. */
      I2S_FullDuplexRx_IT(hi2s, I2S_USE_I2SEXT);
    }

    /* I2Sext Overrun error interrupt occured --------------------------------*/
    if(((i2sextsr & I2S_FLAG_OVR) == I2S_FLAG_OVR) && (__HAL_I2SEXT_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
    {
      /* Disable RXNE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Disable TXE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Set the I2S State ready */
      hi2s->State = HAL_I2S_STATE_READY;

      /* Set the error code and execute error callback*/
      hi2s->ErrorCode |= HAL_I2S_ERROR_OVR;
      HAL_I2S_ErrorCallback(hi2s);
    }

    /* I2S Underrun error interrupt occured ----------------------------------*/
    if(((i2ssr & I2S_FLAG_UDR) == I2S_FLAG_UDR) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
    {
      /* Disable TXE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Disable RXNE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Set the I2S State ready */
      hi2s->State = HAL_I2S_STATE_READY;

      /* Set the error code and execute error callback*/
      hi2s->ErrorCode |= HAL_I2S_ERROR_UDR;
      HAL_I2S_ErrorCallback(hi2s);
    }
  }
  /* The I2S_MODE_MASTER_RX or I2S_MODE_SLAVE_RX Mode is selected */
  else
  {
    /* I2Sext in mode Transmitter ----------------------------------------------*/
    if(((i2sextsr & I2S_FLAG_TXE) == I2S_FLAG_TXE) && (__HAL_I2SEXT_GET_IT_SOURCE(hi2s, I2S_IT_TXE) != RESET))
    {
      /* When the I2S mode is configured as I2S_MODE_MASTER_RX or I2S_MODE_SLAVE_RX,
      the I2Sext TXE interrupt will be generated to manage the full-duplex transmit phase. */
      I2S_FullDuplexTx_IT(hi2s, I2S_USE_I2SEXT);
    }

    /* I2S in mode Receiver --------------------------------------------------*/
    if(((i2ssr & I2S_FLAG_RXNE) == I2S_FLAG_RXNE) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_RXNE) != RESET))
    {
      /* When the I2S mode is configured as I2S_MODE_MASTER_RX or I2S_MODE_SLAVE_RX,
      the I2S RXNE interrupt will be generated to manage the full-duplex receive phase. */
      I2S_FullDuplexRx_IT(hi2s, I2S_USE_I2S);
    }

    /* I2S Overrun error interrupt occured -------------------------------------*/
    if(((i2ssr & I2S_FLAG_OVR) == I2S_FLAG_OVR) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
    {
      /* Disable RXNE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Disable TXE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Set the I2S State ready */
      hi2s->State = HAL_I2S_STATE_READY;

      /* Set the error code and execute error callback*/
      hi2s->ErrorCode |= HAL_I2S_ERROR_OVR;
      HAL_I2S_ErrorCallback(hi2s);
    }

    /* I2Sext Underrun error interrupt occured -------------------------------*/
    if(((i2sextsr & I2S_FLAG_UDR) == I2S_FLAG_UDR) && (__HAL_I2SEXT_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
    {
      /* Disable TXE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Disable RXNE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Set the I2S State ready */
      hi2s->State = HAL_I2S_STATE_READY;

      /* Set the error code and execute error callback*/
      hi2s->ErrorCode |= HAL_I2S_ERROR_UDR;
      HAL_I2S_ErrorCallback(hi2s);
    }
  }
}

/**
  * @brief Tx and Rx Transfer completed callbacks
  * @param hi2s: I2S handle
  * @retval None
  */
__weak void HAL_I2S_TxRxCpltCallback(I2S_HandleTypeDef *hi2s)
{
  /* Prevent unused argument(s) compilation warning */
  UNUSED(hi2s);

  /* NOTE : This function Should not be modified, when the callback is needed,
            the HAL_I2S_TxRxCpltCallback could be implemented in the user file
   */
}

/**
  * @brief Tx and Rx Transfer half completed callbacks
  * @param hi2s: I2S handle
  * @retval None
  */
__weak void HAL_I2S_TxRxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
{
  /* Prevent unused argument(s) compilation warning */
  UNUSED(hi2s);

  /* NOTE : This function Should not be modified, when the callback is needed,
            the HAL_I2S_TxRxHalfCpltCallback could be implemented in the user file
   */
}

/**
  * @}
  */

#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

/** @addtogroup I2S_Exported_Functions_Group3 Peripheral State and Errors functions
  *  @brief   Peripheral State functions
  *
  *
@verbatim
 ===============================================================================
                      ##### Peripheral State functions #####
 ===============================================================================
    [..]
    This subsection permit to get in run-time the status of the peripheral
    and the data flow.

@endverbatim
  * @{
  */
/**
  * @brief Pauses the audio stream playing from the Media.
  * @param  hi2s : I2S handle
  * @retval None
  */
HAL_StatusTypeDef HAL_I2S_DMAPause(I2S_HandleTypeDef *hi2s)
{
  /* Process Locked */
  __HAL_LOCK(hi2s);

  if(hi2s->State == HAL_I2S_STATE_BUSY_TX)
  {
    /* Pause the audio file playing by disabling the I2S DMA request */
    hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_TXDMAEN);
  }
  else if(hi2s->State == HAL_I2S_STATE_BUSY_RX)
  {
    /* Pause the audio file playing by disabling the I2S DMA request */
    hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_RXDMAEN);
  }
#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
  else if(hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
  {
    /* Pause the audio file playing by disabling the I2S DMA request */
    hi2s->Instance->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
    I2SxEXT(hi2s->Instance)->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
  }
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

  /* Process Unlocked */
  __HAL_UNLOCK(hi2s);

  return HAL_OK;
}

/**
  * @brief Resumes the audio stream playing from the Media.
  * @param  hi2s : I2S handle
  * @retval None
  */
HAL_StatusTypeDef HAL_I2S_DMAResume(I2S_HandleTypeDef *hi2s)
{
  /* Process Locked */
  __HAL_LOCK(hi2s);

  if(hi2s->State == HAL_I2S_STATE_BUSY_TX)
  {
    /* Enable the I2S DMA request */
    hi2s->Instance->CR2 |= SPI_CR2_TXDMAEN;
  }
  else if(hi2s->State == HAL_I2S_STATE_BUSY_RX)
  {
    /* Enable the I2S DMA request */
    hi2s->Instance->CR2 |= SPI_CR2_RXDMAEN;
  }
#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
  else if(hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
  {
    /* Pause the audio file playing by disabling the I2S DMA request */
    hi2s->Instance->CR2 |= (SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN);
    I2SxEXT(hi2s->Instance)->CR2 |= (SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN);

    /* If the I2Sext peripheral is still not enabled, enable it */
    if ((I2SxEXT(hi2s->Instance)->I2SCFGR & SPI_I2SCFGR_I2SE) == 0U)
    {
      /* Enable I2Sext peripheral */
      __HAL_I2SEXT_ENABLE(hi2s);
    }
  }
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

  /* If the I2S peripheral is still not enabled, enable it */
  if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) == 0U)
  {
    /* Enable I2S peripheral */
    __HAL_I2S_ENABLE(hi2s);
  }

  /* Process Unlocked */
  __HAL_UNLOCK(hi2s);

  return HAL_OK;
}

/**
  * @brief Resumes the audio stream playing from the Media.
  * @param hi2s: I2S handle
  * @retval None
  */
HAL_StatusTypeDef HAL_I2S_DMAStop(I2S_HandleTypeDef *hi2s)
{
  /* Process Locked */
  __HAL_LOCK(hi2s);

  if(hi2s->State == HAL_I2S_STATE_BUSY_TX)
  {
    /* Disable the I2S DMA requests */
    hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_TXDMAEN);

    /* Disable the I2S DMA Channel */
    HAL_DMA_Abort(hi2s->hdmatx);
  }
  else if(hi2s->State == HAL_I2S_STATE_BUSY_RX)
  {
    /* Disable the I2S DMA requests */
    hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_RXDMAEN);

    /* Disable the I2S DMA Channel */
    HAL_DMA_Abort(hi2s->hdmarx);
  }
#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
  else if(hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
  {
    /* Disable the I2S DMA requests */
    hi2s->Instance->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
    I2SxEXT(hi2s->Instance)->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));

    /* Disable the I2S DMA Channels */
    HAL_DMA_Abort(hi2s->hdmatx);
    HAL_DMA_Abort(hi2s->hdmarx);

    /* Disable I2Sext peripheral */
    __HAL_I2SEXT_DISABLE(hi2s);
  }
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

  /* Disable I2S peripheral */
  __HAL_I2S_DISABLE(hi2s);

  hi2s->State = HAL_I2S_STATE_READY;

  /* Process Unlocked */
  __HAL_UNLOCK(hi2s);

  return HAL_OK;
}

/**
  * @}
  */

/**
  * @}
  */

/**
  * @}
  */

#if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
/** @addtogroup I2SEx
  * @brief I2S Extended HAL module driver
  * @{
  */

/** @defgroup I2SEx_Exported_Functions I2S Extended Exported Functions
  * @{
  */

/** @defgroup I2SEx_Exported_Functions_Group1 I2S Extended Features Functions
  *  @brief   Extended features functions
  *
@verbatim
 ===============================================================================
                       ##### Extended features Functions #####
 ===============================================================================
    [..]
    This subsection provides a set of functions allowing to manage the I2S data
    transfers.

    (#) There is two mode of transfer:
       (++) Blocking mode: The communication is performed in the polling mode.
            The status of all data processing is returned by the same function
            after finishing transfer.
       (++) No-Blocking mode: The communication is performed using Interrupts
            or DMA. These functions return the status of the transfer startup.
            The end of the data processing will be indicated through the
            dedicated I2S IRQ when using Interrupt mode or the DMA IRQ when
            using DMA mode.

    (#) Blocking mode functions are :
        (++) HAL_I2S_TransmitReceive()

    (#) No-Blocking mode functions with Interrupt are:
        (++) HAL_I2S_TransmitReceive_IT()
        (++) HAL_I2SFullDuplex_IRQHandler()

    (#) No-Blocking mode functions with DMA are:
        (++) HAL_I2S_TransmitReceive_DMA()

    (#) A set of Transfer Complete Callbacks are provided in No_Blocking mode:
        (++) HAL_I2S_TxRxCpltCallback()
        (++) HAL_I2S_TxRxHalfCpltCallback()
        (++) HAL_I2S_TxRxErrorCallback()

@endverbatim
  * @{
  */

/**
  * @brief Full-Duplex Transmit/Receive data in blocking mode.
  * @param hi2s: I2S handle
  * @param pTxData a 16-bit pointer to the Transmit data buffer.
  * @param pRxData a 16-bit pointer to the Receive data buffer.
  * @param Size number of data sample to be sent:
  * @note When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
  *       configuration phase, the Size parameter means the number of 16-bit data length
  *       in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
  *       the Size parameter means the number of 16-bit data length.
  * @param Timeout Timeout duration
  * @note The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
  *       between Master and Slave(example: audio streaming).
  * @retval HAL status
  */
HAL_StatusTypeDef HAL_I2SEx_TransmitReceive(I2S_HandleTypeDef *hi2s, uint16_t *pTxData, uint16_t *pRxData, uint16_t Size, uint32_t Timeout)
{
  if((pTxData == NULL ) || (pRxData == NULL ) || (Size == 0U))
  {
    return  HAL_ERROR;
  }

  /* Check the I2S State */
  if(hi2s->State == HAL_I2S_STATE_READY)
  {
    /* Check the Data format: When a 16-bit data frame or a 16-bit data frame extended
       is selected during the I2S configuration phase, the Size parameter means the number
       of 16-bit data length in the transaction and when a 24-bit data frame or a 32-bit data
       frame is selected the Size parameter means the number of 16-bit data length. */
    if(((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_24B)||\
      ((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_32B))
    {
      hi2s->TxXferSize = (Size << 1U);
      hi2s->TxXferCount = (Size << 1U);
      hi2s->RxXferSize = (Size << 1U);
      hi2s->RxXferCount = (Size << 1U);
    }
    else
    {
      hi2s->TxXferSize = Size;
      hi2s->TxXferCount = Size;
      hi2s->RxXferSize = Size;
      hi2s->RxXferCount = Size;
    }

    /* Process Locked */
    __HAL_LOCK(hi2s);

    hi2s->ErrorCode = HAL_I2S_ERROR_NONE;

    /* Set the I2S State busy TX/RX */
    hi2s->State = HAL_I2S_STATE_BUSY_TX_RX;

    /* Check if the I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX Mode is selected */
    if(((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_TX) || ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX))
    {
      /* Prepare the First Data before enabling the I2S */
      if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX)
      {
        hi2s->Instance->DR = (*pTxData++);
        hi2s->TxXferCount--;
      }

      /* Check if the I2S is already enabled: The I2S is kept enabled at the end of transaction
      to avoid the clock de-synchronization between Master and Slave. */
      if((hi2s->Instance->I2SCFGR &SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        /* Enable I2Sext(receiver) before enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);

        /* Enable I2Sx peripheral */
        __HAL_I2S_ENABLE(hi2s);
      }

      while(hi2s->RxXferCount > 0U)
      {
        /* Wait until TXE flag is set */
        if (I2S_FullDuplexWaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXE, SET, Timeout, I2S_USE_I2S) != HAL_OK)
        {
          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_TIMEOUT;
          HAL_I2S_ErrorCallback(hi2s);
          return HAL_TIMEOUT;
        }

        if (hi2s->TxXferCount > 0U)
        {
          /* Check if an underrun occurs */
          if(__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_UDR) == SET)
          {
            /* Set the I2S State ready */
            hi2s->State = HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            /* Set the error code and execute error callback*/
            hi2s->ErrorCode |= HAL_I2S_ERROR_UDR;
            HAL_I2S_ErrorCallback(hi2s);

            return HAL_ERROR;
          }

          hi2s->Instance->DR = (*pTxData++);
          hi2s->TxXferCount--;
        }

        /* Wait until RXNE flag is set */
        if (I2S_FullDuplexWaitFlagStateUntilTimeout(hi2s, I2S_FLAG_RXNE, SET, Timeout, I2S_USE_I2SEXT) != HAL_OK)
        {
          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_TIMEOUT;
          HAL_I2S_ErrorCallback(hi2s);
          return HAL_TIMEOUT;
        }

        /* Check if an overrun occurs */
        if(__HAL_I2SEXT_GET_FLAG(hi2s, I2S_FLAG_OVR) == SET)
        {
          /* Set the I2S State ready */
          hi2s->State = HAL_I2S_STATE_READY;

          /* Process Unlocked */
          __HAL_UNLOCK(hi2s);

          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_OVR;
          HAL_I2S_ErrorCallback(hi2s);

          return HAL_ERROR;
        }

        (*pRxData++) = I2SxEXT(hi2s->Instance)->DR;
        hi2s->RxXferCount--;	
      }
    }
    /* The I2S_MODE_MASTER_RX or I2S_MODE_SLAVE_RX Mode is selected */
    else
    {
      /* Prepare the First Data before enabling the I2S */
      I2SxEXT(hi2s->Instance)->DR = (*pTxData++);
      hi2s->TxXferCount--;

      /* Check if the I2S is already enabled */
      if((hi2s->Instance->I2SCFGR &SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        /* Enable I2S peripheral before the I2Sext*/
        __HAL_I2S_ENABLE(hi2s);

        /* Enable I2Sext(transmitter) after enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);
      }

      /* Check if Master Receiver mode is selected */
      if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_RX)
      {
        /* Clear the Overrun Flag by a read operation on the SPI_DR register followed by a read
        access to the SPI_SR register. */
        __HAL_I2S_CLEAR_OVRFLAG(hi2s);
      }

      while(hi2s->RxXferCount > 0U)
      {
        /* Wait until TXE flag is set */
        if (I2S_FullDuplexWaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXE, SET, Timeout, I2S_USE_I2SEXT) != HAL_OK)
        {
          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_TIMEOUT;
          HAL_I2S_ErrorCallback(hi2s);
          return HAL_TIMEOUT;
        }

        if (hi2s->TxXferCount > 0U)
        {
          /* Check if an underrun occurs */
          if(__HAL_I2SEXT_GET_FLAG(hi2s, I2S_FLAG_UDR) == SET)
          {
            /* Set the I2S State ready */
            hi2s->State = HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            /* Set the error code and execute error callback*/
            hi2s->ErrorCode |= HAL_I2S_ERROR_UDR;
            HAL_I2S_ErrorCallback(hi2s);

            return HAL_ERROR;
          }

          I2SxEXT(hi2s->Instance)->DR = (*pTxData++);
          hi2s->TxXferCount--;
        }

        /* Wait until RXNE flag is set */
        if (I2S_FullDuplexWaitFlagStateUntilTimeout(hi2s, I2S_FLAG_RXNE, SET, Timeout, I2S_USE_I2S) != HAL_OK)
        {
          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_TIMEOUT;
          HAL_I2S_ErrorCallback(hi2s);
          return HAL_TIMEOUT;
        }

        /* Check if an overrun occurs */
        if(__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_OVR) == SET)
        {
          /* Set the I2S State ready */
          hi2s->State = HAL_I2S_STATE_READY;

          /* Process Unlocked */
          __HAL_UNLOCK(hi2s);

          /* Set the error code and execute error callback*/
          hi2s->ErrorCode |= HAL_I2S_ERROR_OVR;
          HAL_I2S_ErrorCallback(hi2s);

          return HAL_ERROR;
        }

        (*pRxData++) = hi2s->Instance->DR;
        hi2s->RxXferCount--;	
      }
    }

    /* Set the I2S State ready */
    hi2s->State = HAL_I2S_STATE_READY;

    /* Process Unlocked */
    __HAL_UNLOCK(hi2s);

    return HAL_OK;
  }
  else
  {
    return HAL_BUSY;
  }
}

/**
  * @brief Full-Duplex Transmit/Receive data in non-blocking mode using Interrupt
  * @param hi2s: I2S handle
  * @param pTxData a 16-bit pointer to the Transmit data buffer.
  * @param pRxData a 16-bit pointer to the Receive data buffer.
  * @param Size number of data sample to be sent:
  * @note When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
  *       configuration phase, the Size parameter means the number of 16-bit data length
  *       in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
  *       the Size parameter means the number of 16-bit data length.
  * @note The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
  *       between Master and Slave(example: audio streaming).
  * @retval HAL status
  */
HAL_StatusTypeDef HAL_I2SEx_TransmitReceive_IT(I2S_HandleTypeDef *hi2s, uint16_t *pTxData, uint16_t *pRxData, uint16_t Size)
{
  if(hi2s->State == HAL_I2S_STATE_READY)
  {
    if((pTxData == NULL ) || (pRxData == NULL ) || (Size == 0U))
    {
      return  HAL_ERROR;
    }

    hi2s->pTxBuffPtr = pTxData;
    hi2s->pRxBuffPtr = pRxData;

    /* Check the Data format: When a 16-bit data frame or a 16-bit data frame extended
       is selected during the I2S configuration phase, the Size parameter means the number
       of 16-bit data length in the transaction and when a 24-bit data frame or a 32-bit data
       frame is selected the Size parameter means the number of 16-bit data length. */
    if(((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_24B)||\
      ((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_32B))
    {
      hi2s->TxXferSize = (Size << 1U);
      hi2s->TxXferCount = (Size << 1U);
      hi2s->RxXferSize = (Size << 1U);
      hi2s->RxXferCount = (Size << 1U);
    }
    else
    {
      hi2s->TxXferSize = Size;
      hi2s->TxXferCount = Size;
      hi2s->RxXferSize = Size;
      hi2s->RxXferCount = Size;
    }

    /* Process Locked */
    __HAL_LOCK(hi2s);

    hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
    hi2s->State = HAL_I2S_STATE_BUSY_TX_RX;

    /* Check if the I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX Mode is selected */
    if(((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_TX) || ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX))
    {
      /* Enable I2Sext RXNE and ERR interrupts */
      __HAL_I2SEXT_ENABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Enable I2Sx TXE and ERR interrupts */
      __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Check if the I2S is already enabled */
      if((hi2s->Instance->I2SCFGR &SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX)
        {
          /* Prepare the First Data before enabling the I2S */
          if(hi2s->TxXferCount != 0U)
          {
            /* Transmit First data */
            hi2s->Instance->DR = (*hi2s->pTxBuffPtr++);
            hi2s->TxXferCount--;	

            if(hi2s->TxXferCount == 0U)
            {
              /* Disable TXE and ERR interrupt */
              __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

              if(hi2s->RxXferCount == 0U)
              {
                /* Disable I2Sext RXNE and ERR interrupt */
                __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_RXNE| I2S_IT_ERR));

                hi2s->State = HAL_I2S_STATE_READY;
                HAL_I2S_TxRxCpltCallback(hi2s);
              }
            }
          }
        }
        /* Enable I2Sext(receiver) before enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);

        /* Enable I2Sx peripheral */
        __HAL_I2S_ENABLE(hi2s);
      }
    }
    /* The I2S_MODE_MASTER_RX or I2S_MODE_SLAVE_RX Mode is selected */
    else
    {
      /* Enable I2Sext TXE and ERR interrupts */
      __HAL_I2SEXT_ENABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      /* Enable I2Sext RXNE and ERR interrupts */
      __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      /* Check if the I2S is already enabled */
      if((hi2s->Instance->I2SCFGR &SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        /* Prepare the First Data before enabling the I2S */
        if(hi2s->TxXferCount != 0U)
        {
          /* Transmit First data */
          I2SxEXT(hi2s->Instance)->DR = (*hi2s->pTxBuffPtr++);
          hi2s->TxXferCount--;	

          if(hi2s->TxXferCount == 0U)
          {
            /* Disable I2Sext TXE and ERR interrupt */
            __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

            if(hi2s->RxXferCount == 0U)
            {
              /* Disable RXNE and ERR interrupt */
              __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE| I2S_IT_ERR));

              hi2s->State = HAL_I2S_STATE_READY;
              HAL_I2S_TxRxCpltCallback(hi2s);
            }
          }
        }
        /* Enable I2Sext(transmitter) after enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);

        /* Enable I2S peripheral */
        __HAL_I2S_ENABLE(hi2s);
      }
    }
    /* Process Unlocked */
    __HAL_UNLOCK(hi2s);

    return HAL_OK;
  }
  else
  {
    return HAL_BUSY;
  }
}

/**
  * @brief Full-Duplex Transmit/Receive data in non-blocking mode using DMA
  * @param hi2s: I2S handle
  * @param pTxData a 16-bit pointer to the Transmit data buffer.
  * @param pRxData a 16-bit pointer to the Receive data buffer.
  * @param Size number of data sample to be sent:
  * @note When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
  *       configuration phase, the Size parameter means the number of 16-bit data length
  *       in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
  *       the Size parameter means the number of 16-bit data length.
  * @note The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
  *       between Master and Slave(example: audio streaming).
  * @retval HAL status
  */
HAL_StatusTypeDef HAL_I2SEx_TransmitReceive_DMA(I2S_HandleTypeDef *hi2s, uint16_t *pTxData, uint16_t *pRxData, uint16_t Size)
{
  uint32_t *tmp;

  if((pTxData == NULL ) || (pRxData == NULL ) || (Size == 0U))
  {
    return  HAL_ERROR;
  }

  if(hi2s->State == HAL_I2S_STATE_READY)
  {
    hi2s->pTxBuffPtr = pTxData;
    hi2s->pRxBuffPtr = pRxData;

    /* Check the Data format: When a 16-bit data frame or a 16-bit data frame extended
       is selected during the I2S configuration phase, the Size parameter means the number
       of 16-bit data length in the transaction and when a 24-bit data frame or a 32-bit data
       frame is selected the Size parameter means the number of 16-bit data length. */
    if(((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_24B)||\
      ((hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN)) == I2S_DATAFORMAT_32B))
    {
      hi2s->TxXferSize = (Size << 1U);
      hi2s->TxXferCount = (Size << 1U);
      hi2s->RxXferSize = (Size << 1U);
      hi2s->RxXferCount = (Size << 1U);
    }
    else
    {
      hi2s->TxXferSize = Size;
      hi2s->TxXferCount = Size;
      hi2s->RxXferSize = Size;
      hi2s->RxXferCount = Size;
    }

    /* Process Locked */
    __HAL_LOCK(hi2s);

    hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
    hi2s->State = HAL_I2S_STATE_BUSY_TX_RX;

    /* Set the I2S Rx DMA transfer complete callback */
    hi2s->hdmarx->XferCpltCallback = I2S_TxRxDMACplt;

    /* Set the I2S Rx DMA Half transfer complete callback */
    hi2s->hdmarx->XferHalfCpltCallback = I2S_TxRxDMAHalfCplt;

    /* Set the I2S Rx DMA error callback */
    hi2s->hdmarx->XferErrorCallback = I2S_TxRxDMAError;

    /* Set the I2S Tx DMA transfer callbacks as NULL because the
    communication closing is performed in DMA reception callbacks */
    hi2s->hdmatx->XferCpltCallback = NULL;
    hi2s->hdmatx->XferHalfCpltCallback = NULL;

    /* Set the I2S Tx DMA error callback */
    hi2s->hdmatx->XferErrorCallback = I2S_TxRxDMAError;

    /* Check if the I2S_MODE_MASTER_TX or I2S_MODE_SLAVE_TX Mode is selected */
    if(((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_TX) || ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX))
    {
      /* Enable the Rx DMA Channel */
      tmp = (uint32_t*)&pRxData;
      HAL_DMA_Start_IT(hi2s->hdmarx, (uint32_t)&I2SxEXT(hi2s->Instance)->DR, *(uint32_t*)tmp, hi2s->RxXferSize);

      /* Enable Rx DMA Request */
      I2SxEXT(hi2s->Instance)->CR2 |= SPI_CR2_RXDMAEN;

      /* Enable the Tx DMA Channel */
      tmp = (uint32_t*)&pTxData;
      HAL_DMA_Start_IT(hi2s->hdmatx, *(uint32_t*)tmp, (uint32_t)&hi2s->Instance->DR, hi2s->TxXferSize);

      /* Enable Tx DMA Request */
      hi2s->Instance->CR2 |= SPI_CR2_TXDMAEN;

      /* Check if the I2S is already enabled */
      if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        /* Enable I2Sext(receiver) before enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);

        /* Enable I2S peripheral after the I2Sext*/
        __HAL_I2S_ENABLE(hi2s);
      }
    }
    else
    {
      /* Check if Master Receiver mode is selected */
      if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_RX)
      {
        /* Clear the Overrun Flag by a read operation on the SPI_DR register followed by a read
        access to the SPI_SR register. */
        __HAL_I2S_CLEAR_OVRFLAG(hi2s);
      }

      /* Enable the Tx DMA Channel */
      tmp = (uint32_t*)&pTxData;
      HAL_DMA_Start_IT(hi2s->hdmatx, *(uint32_t*)tmp, (uint32_t)&I2SxEXT(hi2s->Instance)->DR, hi2s->TxXferSize);

      /* Enable Tx DMA Request */
      I2SxEXT(hi2s->Instance)->CR2 |= SPI_CR2_TXDMAEN;

      /* Enable the Rx DMA Channel */
      tmp = (uint32_t*)&pRxData;
      HAL_DMA_Start_IT(hi2s->hdmarx, (uint32_t)&hi2s->Instance->DR, *(uint32_t*)tmp, hi2s->RxXferSize);

      /* Enable Rx DMA Request */
      hi2s->Instance->CR2 |= SPI_CR2_RXDMAEN;

      /* Check if the I2S is already enabled */
      if((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
      {
        /* Enable I2Sext(transmitter) before enabling I2Sx peripheral */
        __HAL_I2SEXT_ENABLE(hi2s);

        /* Enable I2S peripheral after the I2Sext*/
        __HAL_I2S_ENABLE(hi2s);
      }
    }

    /* Process Unlocked */
    __HAL_UNLOCK(hi2s);

    return HAL_OK;
  }
  else
  {
    return HAL_BUSY;
  }
}

/**
  * @}
  */

/**
  * @}
  */

/** @addtogroup I2SEx_Private_Functions I2S Extended Private Functions
  * @{
  */

/**
  * @brief DMA I2S transmit receive process complete callback
  * @param hdma DMA handle
  * @retval None
  */
static void I2S_TxRxDMACplt(DMA_HandleTypeDef *hdma)
{
  I2S_HandleTypeDef* hi2s = ( I2S_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;

  /* DMA Normal Mode */
  if((hdma->Instance->CCR & DMA_CCR_CIRC) == 0U)
  {
    /* Disable Rx/Tx DMA Request */
    if(((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_TX) || ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX))
    {
      hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_TXDMAEN);
      I2SxEXT(hi2s->Instance)->CR2 &= (uint32_t)(~SPI_CR2_RXDMAEN);
    }
    else
    {
      hi2s->Instance->CR2 &= (uint32_t)(~SPI_CR2_RXDMAEN);
      I2SxEXT(hi2s->Instance)->CR2 &= (uint32_t)(~SPI_CR2_TXDMAEN);
    }

    hi2s->RxXferCount = 0U;
    hi2s->TxXferCount = 0U;

    hi2s->State = HAL_I2S_STATE_READY;
  }

  HAL_I2S_TxRxCpltCallback(hi2s);
}

static void I2S_TxRxDMAHalfCplt(DMA_HandleTypeDef *hdma)
{
  I2S_HandleTypeDef* hi2s = ( I2S_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;

  HAL_I2S_TxRxHalfCpltCallback(hi2s);
}

/**
  * @brief DMA I2S communication error callback
  * @param hdma : DMA handle
  * @retval None
  */
static void I2S_TxRxDMAError(DMA_HandleTypeDef *hdma)
{
  I2S_HandleTypeDef* hi2s = ( I2S_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;

  /* Disable Rx and Tx DMA Request */
  hi2s->Instance->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
  I2SxEXT(hi2s->Instance)->CR2 &= (uint32_t)(~(SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));

  hi2s->TxXferCount = 0U;
  hi2s->RxXferCount = 0U;

  hi2s->State= HAL_I2S_STATE_READY;

  /* Set the error code and execute error callback*/
  hi2s->ErrorCode |= HAL_I2S_ERROR_DMA;
  HAL_I2S_ErrorCallback(hi2s);
}

/**
  * @brief Full-Duplex IT handler transmit function
  * @param hi2s: I2S handle
  * @param i2sUsed: indicate if I2Sx or I2Sx_ext is concerned
  * @retval None
  */
static void I2S_FullDuplexTx_IT(I2S_HandleTypeDef *hi2s, I2S_UseTypeDef i2sUsed)
{
  if(i2sUsed == I2S_USE_I2S)
  {
    /* Transmit data */
    hi2s->Instance->DR = (*hi2s->pTxBuffPtr++);
    hi2s->TxXferCount--;	

    if(hi2s->TxXferCount == 0U)
    {
      /* Disable TXE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      if(hi2s->RxXferCount == 0U)
      {
        hi2s->State = HAL_I2S_STATE_READY;
        HAL_I2S_TxRxCpltCallback(hi2s);
      }
    }
  }
  else
  {
    /* Transmit data */
    I2SxEXT(hi2s->Instance)->DR = (*hi2s->pTxBuffPtr++);
    hi2s->TxXferCount--;	

    if(hi2s->TxXferCount == 0U)
    {
      /* Disable I2Sext TXE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));

      if(hi2s->RxXferCount == 0U)
      {
        hi2s->State = HAL_I2S_STATE_READY;
        HAL_I2S_TxRxCpltCallback(hi2s);
      }
    }
  }
}

/**
  * @brief Full-Duplex IT handler receive function
  * @param hi2s: I2S handle
  * @param i2sUsed: indicate if I2Sx or I2Sx_ext is concerned
  * @retval None
  */
static void I2S_FullDuplexRx_IT(I2S_HandleTypeDef *hi2s, I2S_UseTypeDef i2sUsed)
{
  if(i2sUsed == I2S_USE_I2S)
  {
    /* Receive data */
    (*hi2s->pRxBuffPtr++) = hi2s->Instance->DR;
    hi2s->RxXferCount--;

    if(hi2s->RxXferCount == 0U)
    {
      /* Disable RXNE and ERR interrupt */
      __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      if(hi2s->TxXferCount == 0U)
      {
        hi2s->State = HAL_I2S_STATE_READY;
        HAL_I2S_TxRxCpltCallback(hi2s);
      }
    }
  }
  else
  {
    /* Receive data */
    (*hi2s->pRxBuffPtr++) = I2SxEXT(hi2s->Instance)->DR;
    hi2s->RxXferCount--;	

    if(hi2s->RxXferCount == 0U)
    {
      /* Disable I2Sext RXNE and ERR interrupt */
      __HAL_I2SEXT_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));

      if(hi2s->TxXferCount == 0U)
      {
        hi2s->State = HAL_I2S_STATE_READY;
        HAL_I2S_TxRxCpltCallback(hi2s);
      }
    }
  }
}

/**
  * @brief This function handles I2S Communication Timeout.
  * @param hi2s: I2S handle
  * @param Flag Flag checked
  * @param State Value of the flag expected
  * @param Timeout Duration of the timeout
  * @param i2sUsed: I2S instance reference
  * @retval HAL status
  */
static HAL_StatusTypeDef I2S_FullDuplexWaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag,
                                                                 uint32_t State, uint32_t Timeout, I2S_UseTypeDef i2sUsed)
{
  uint32_t tickstart = HAL_GetTick();

  if(i2sUsed == I2S_USE_I2S)
  {
    if(State == RESET)
    {
      /* Wait until flag is reset */
      while((__HAL_I2S_GET_FLAG(hi2s, Flag)) != RESET)
      {
        if(Timeout != HAL_MAX_DELAY)
        {
          if((Timeout == 0U) || ((HAL_GetTick()-tickstart) > Timeout))
          {
            /* Set the I2S State ready */
            hi2s->State= HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            return HAL_TIMEOUT;
          }
        }
      }
    }
    else /* State == SET */
    {
      /* Wait until flag is set */
      while((__HAL_I2S_GET_FLAG(hi2s, Flag)) != SET)
      {
        if(Timeout != HAL_MAX_DELAY)
        {
          if((Timeout == 0U) || ((HAL_GetTick()-tickstart) > Timeout))
          {
            /* Set the I2S State ready */
            hi2s->State= HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            return HAL_TIMEOUT;
          }
        }
      }
    }
  }
  else /* i2sUsed == I2S_USE_I2SEXT */
  {
    if(State == RESET)
    {
      /* Wait until flag is reset */
      while((__HAL_I2SEXT_GET_FLAG(hi2s, Flag)) != RESET)
      {
        if(Timeout != HAL_MAX_DELAY)
        {
          if((Timeout == 0U) || ((HAL_GetTick()-tickstart) > Timeout))
          {
            /* Set the I2S State ready */
            hi2s->State= HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            return HAL_TIMEOUT;
          }
        }
      }
    }
    else /* State == SET */
    {
      /* Wait until flag is set */
      while((__HAL_I2SEXT_GET_FLAG(hi2s, Flag)) != SET)
      {
        if(Timeout != HAL_MAX_DELAY)
        {
          if((Timeout == 0U) || ((HAL_GetTick()-tickstart) > Timeout))
          {
            /* Set the I2S State ready */
            hi2s->State= HAL_I2S_STATE_READY;

            /* Process Unlocked */
            __HAL_UNLOCK(hi2s);

            return HAL_TIMEOUT;
          }
        }
      }
    }
  }

  return HAL_OK;
}
#endif /* SPI_I2S_FULLDUPLEX_SUPPORT */

/**
  * @}
  */

/**
  * @}
  */

#endif /* STM32F302xE || STM32F303xE || STM32F398xx || */
       /* STM32F302xC || STM32F303xC || STM32F358xx || */
       /* STM32F301x8 || STM32F302x8 || STM32F318xx || */
       /* STM32F373xC || STM32F378xx                   */

#endif /* HAL_I2S_MODULE_ENABLED */

/**
  * @}
  */

/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
