1 /**
2   ******************************************************************************
3   * @file    stm32f4xx_hal_i2s.c
4   * @author  MCD Application Team
5   * @brief   I2S HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the Integrated Interchip Sound (I2S) peripheral:
8   *           + Initialization and de-initialization functions
9   *           + IO operation functions
10   *           + Peripheral State and Errors functions
11   ******************************************************************************
12   * @attention
13   *
14   * Copyright (c) 2016 STMicroelectronics.
15   * All rights reserved.
16   *
17   * This software is licensed under terms that can be found in the LICENSE file
18   * in the root directory of this software component.
19   * If no LICENSE file comes with this software, it is provided AS-IS.
20   *
21   ******************************************************************************
22   @verbatim
23  ===============================================================================
24                   ##### How to use this driver #####
25  ===============================================================================
26  [..]
27     The I2S HAL driver can be used as follow:
28 
29     (#) Declare a I2S_HandleTypeDef handle structure.
30     (#) Initialize the I2S low level resources by implement the HAL_I2S_MspInit() API:
31         (##) Enable the SPIx interface clock.
32         (##) I2S pins configuration:
33             (+++) Enable the clock for the I2S GPIOs.
34             (+++) Configure these I2S pins as alternate function pull-up.
35         (##) NVIC configuration if you need to use interrupt process (HAL_I2S_Transmit_IT()
36              and HAL_I2S_Receive_IT() APIs).
37             (+++) Configure the I2Sx interrupt priority.
38             (+++) Enable the NVIC I2S IRQ handle.
39         (##) DMA Configuration if you need to use DMA process (HAL_I2S_Transmit_DMA()
40              and HAL_I2S_Receive_DMA() APIs:
41             (+++) Declare a DMA handle structure for the Tx/Rx Stream/Channel.
42             (+++) Enable the DMAx interface clock.
43             (+++) Configure the declared DMA handle structure with the required Tx/Rx parameters.
44             (+++) Configure the DMA Tx/Rx Stream/Channel.
45             (+++) Associate the initialized DMA handle to the I2S DMA Tx/Rx handle.
46             (+++) Configure the priority and enable the NVIC for the transfer complete interrupt on the
47                   DMA Tx/Rx Stream/Channel.
48 
49    (#) Program the Mode, Standard, Data Format, MCLK Output, Audio frequency and Polarity
50        using HAL_I2S_Init() function.
51 
52    -@- The specific I2S interrupts (Transmission complete interrupt,
53        RXNE interrupt and Error Interrupts) will be managed using the macros
54        __HAL_I2S_ENABLE_IT() and __HAL_I2S_DISABLE_IT() inside the transmit and receive process.
55    -@- Make sure that either:
56         (+@) I2S PLL clock is configured or
57         (+@) External clock source is configured after setting correctly
58              the define constant EXTERNAL_CLOCK_VALUE in the stm32f4xx_hal_conf.h file.
59 
60     (#) Three mode of operations are available within this driver :
61 
62    *** Polling mode IO operation ***
63    =================================
64    [..]
65      (+) Send an amount of data in blocking mode using HAL_I2S_Transmit()
66      (+) Receive an amount of data in blocking mode using HAL_I2S_Receive()
67 
68    *** Interrupt mode IO operation ***
69    ===================================
70    [..]
71      (+) Send an amount of data in non blocking mode using HAL_I2S_Transmit_IT()
72      (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
73          add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
74      (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
75          add his own code by customization of function pointer HAL_I2S_TxCpltCallback
76      (+) Receive an amount of data in non blocking mode using HAL_I2S_Receive_IT()
77      (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
78          add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
79      (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
80          add his own code by customization of function pointer HAL_I2S_RxCpltCallback
81      (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
82          add his own code by customization of function pointer HAL_I2S_ErrorCallback
83 
84    *** DMA mode IO operation ***
85    ==============================
86    [..]
87      (+) Send an amount of data in non blocking mode (DMA) using HAL_I2S_Transmit_DMA()
88      (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
89          add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
90      (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
91          add his own code by customization of function pointer HAL_I2S_TxCpltCallback
92      (+) Receive an amount of data in non blocking mode (DMA) using HAL_I2S_Receive_DMA()
93      (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
94          add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
95      (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
96          add his own code by customization of function pointer HAL_I2S_RxCpltCallback
97      (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
98          add his own code by customization of function pointer HAL_I2S_ErrorCallback
99      (+) Pause the DMA Transfer using HAL_I2S_DMAPause()
100      (+) Resume the DMA Transfer using HAL_I2S_DMAResume()
101      (+) Stop the DMA Transfer using HAL_I2S_DMAStop()
102          In Slave mode, if HAL_I2S_DMAStop is used to stop the communication, an error
103          HAL_I2S_ERROR_BUSY_LINE_RX is raised as the master continue to transmit data.
104          In this case __HAL_I2S_FLUSH_RX_DR macro must be used to flush the remaining data
105          inside DR register and avoid using DeInit/Init process for the next transfer.
106 
107    *** I2S HAL driver macros list ***
108    ===================================
109    [..]
110      Below the list of most used macros in I2S HAL driver.
111 
112       (+) __HAL_I2S_ENABLE: Enable the specified SPI peripheral (in I2S mode)
113       (+) __HAL_I2S_DISABLE: Disable the specified SPI peripheral (in I2S mode)
114       (+) __HAL_I2S_ENABLE_IT : Enable the specified I2S interrupts
115       (+) __HAL_I2S_DISABLE_IT : Disable the specified I2S interrupts
116       (+) __HAL_I2S_GET_FLAG: Check whether the specified I2S flag is set or not
117       (+) __HAL_I2S_FLUSH_RX_DR: Read DR Register to Flush RX Data
118 
119     [..]
120       (@) You can refer to the I2S HAL driver header file for more useful macros
121 
122    *** I2S HAL driver macros list ***
123    ===================================
124    [..]
125        Callback registration:
126 
127       (#) The compilation flag USE_HAL_I2S_REGISTER_CALLBACKS when set to 1U
128           allows the user to configure dynamically the driver callbacks.
129           Use Functions HAL_I2S_RegisterCallback() to register an interrupt callback.
130 
131           Function HAL_I2S_RegisterCallback() allows to register following callbacks:
132             (++) TxCpltCallback        : I2S Tx Completed callback
133             (++) RxCpltCallback        : I2S Rx Completed callback
134             (++) TxRxCpltCallback      : I2S TxRx Completed callback
135             (++) TxHalfCpltCallback    : I2S Tx Half Completed callback
136             (++) RxHalfCpltCallback    : I2S Rx Half Completed callback
137             (++) ErrorCallback         : I2S Error callback
138             (++) MspInitCallback       : I2S Msp Init callback
139             (++) MspDeInitCallback     : I2S Msp DeInit callback
140           This function takes as parameters the HAL peripheral handle, the Callback ID
141           and a pointer to the user callback function.
142 
143 
144       (#) Use function HAL_I2S_UnRegisterCallback to reset a callback to the default
145           weak function.
146           HAL_I2S_UnRegisterCallback takes as parameters the HAL peripheral handle,
147           and the Callback ID.
148           This function allows to reset following callbacks:
149             (++) TxCpltCallback        : I2S Tx Completed callback
150             (++) RxCpltCallback        : I2S Rx Completed callback
151             (++) TxRxCpltCallback      : I2S TxRx Completed callback
152             (++) TxHalfCpltCallback    : I2S Tx Half Completed callback
153             (++) RxHalfCpltCallback    : I2S Rx Half Completed callback
154             (++) ErrorCallback         : I2S Error callback
155             (++) MspInitCallback       : I2S Msp Init callback
156             (++) MspDeInitCallback     : I2S Msp DeInit callback
157 
158        [..]
159        By default, after the HAL_I2S_Init() and when the state is HAL_I2S_STATE_RESET
160        all callbacks are set to the corresponding weak functions:
161        examples HAL_I2S_MasterTxCpltCallback(), HAL_I2S_MasterRxCpltCallback().
162        Exception done for MspInit and MspDeInit functions that are
163        reset to the legacy weak functions in the HAL_I2S_Init()/ HAL_I2S_DeInit() only when
164        these callbacks are null (not registered beforehand).
165        If MspInit or MspDeInit are not null, the HAL_I2S_Init()/ HAL_I2S_DeInit()
166        keep and use the user MspInit/MspDeInit callbacks (registered beforehand) whatever the state.
167 
168        [..]
169        Callbacks can be registered/unregistered in HAL_I2S_STATE_READY state only.
170        Exception done MspInit/MspDeInit functions that can be registered/unregistered
171        in HAL_I2S_STATE_READY or HAL_I2S_STATE_RESET state,
172        thus registered (user) MspInit/DeInit callbacks can be used during the Init/DeInit.
173        Then, the user first registers the MspInit/MspDeInit user callbacks
174        using HAL_I2S_RegisterCallback() before calling HAL_I2S_DeInit()
175        or HAL_I2S_Init() function.
176 
177        [..]
178        When the compilation define USE_HAL_I2S_REGISTER_CALLBACKS is set to 0 or
179        not defined, the callback registering feature is not available
180        and weak (surcharged) callbacks are used.
181 
182   @endverbatim
183 
184   */
185 
186 /* Includes ------------------------------------------------------------------*/
187 #include "stm32f4xx_hal.h"
188 
189 #ifdef HAL_I2S_MODULE_ENABLED
190 
191 /** @addtogroup STM32F4xx_HAL_Driver
192   * @{
193   */
194 
195 /** @defgroup I2S I2S
196   * @brief I2S HAL module driver
197   * @{
198   */
199 
200 /* Private typedef -----------------------------------------------------------*/
201 /* Private define ------------------------------------------------------------*/
202 #define I2S_TIMEOUT_FLAG          100U         /*!< Timeout 100 ms            */
203 /* Private macro -------------------------------------------------------------*/
204 /* Private variables ---------------------------------------------------------*/
205 /* Private function prototypes -----------------------------------------------*/
206 /** @defgroup I2S_Private_Functions I2S Private Functions
207   * @{
208   */
209 static void               I2S_DMATxCplt(DMA_HandleTypeDef *hdma);
210 static void               I2S_DMATxHalfCplt(DMA_HandleTypeDef *hdma);
211 static void               I2S_DMARxCplt(DMA_HandleTypeDef *hdma);
212 static void               I2S_DMARxHalfCplt(DMA_HandleTypeDef *hdma);
213 static void               I2S_DMAError(DMA_HandleTypeDef *hdma);
214 static void               I2S_Transmit_IT(I2S_HandleTypeDef *hi2s);
215 static void               I2S_Receive_IT(I2S_HandleTypeDef *hi2s);
216 static void               I2S_IRQHandler(I2S_HandleTypeDef *hi2s);
217 static HAL_StatusTypeDef  I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag, FlagStatus State,
218                                                         uint32_t Timeout);
219 /**
220   * @}
221   */
222 
223 /* Exported functions ---------------------------------------------------------*/
224 
225 /** @defgroup I2S_Exported_Functions I2S Exported Functions
226   * @{
227   */
228 
229 /** @defgroup  I2S_Exported_Functions_Group1 Initialization and de-initialization functions
230   *  @brief    Initialization and Configuration functions
231   *
232 @verbatim
233  ===============================================================================
234               ##### Initialization and de-initialization functions #####
235  ===============================================================================
236     [..]  This subsection provides a set of functions allowing to initialize and
237           de-initialize the I2Sx peripheral in simplex mode:
238 
239       (+) User must Implement HAL_I2S_MspInit() function in which he configures
240           all related peripherals resources (CLOCK, GPIO, DMA, IT and NVIC ).
241 
242       (+) Call the function HAL_I2S_Init() to configure the selected device with
243           the selected configuration:
244         (++) Mode
245         (++) Standard
246         (++) Data Format
247         (++) MCLK Output
248         (++) Audio frequency
249         (++) Polarity
250         (++) Full duplex mode
251 
252      (+) Call the function HAL_I2S_DeInit() to restore the default configuration
253           of the selected I2Sx peripheral.
254   @endverbatim
255   * @{
256   */
257 
258 /**
259   * @brief  Initializes the I2S according to the specified parameters
260   *         in the I2S_InitTypeDef and create the associated handle.
261   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
262   *         the configuration information for I2S module
263   * @retval HAL status
264   */
HAL_I2S_Init(I2S_HandleTypeDef * hi2s)265 HAL_StatusTypeDef HAL_I2S_Init(I2S_HandleTypeDef *hi2s)
266 {
267   uint32_t i2sdiv;
268   uint32_t i2sodd;
269   uint32_t packetlength;
270   uint32_t tmp;
271   uint32_t i2sclk;
272 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
273   uint16_t tmpreg;
274 #endif
275 
276   /* Check the I2S handle allocation */
277   if (hi2s == NULL)
278   {
279     return HAL_ERROR;
280   }
281 
282   /* Check the I2S parameters */
283   assert_param(IS_I2S_ALL_INSTANCE(hi2s->Instance));
284   assert_param(IS_I2S_MODE(hi2s->Init.Mode));
285   assert_param(IS_I2S_STANDARD(hi2s->Init.Standard));
286   assert_param(IS_I2S_DATA_FORMAT(hi2s->Init.DataFormat));
287   assert_param(IS_I2S_MCLK_OUTPUT(hi2s->Init.MCLKOutput));
288   assert_param(IS_I2S_AUDIO_FREQ(hi2s->Init.AudioFreq));
289   assert_param(IS_I2S_CPOL(hi2s->Init.CPOL));
290   assert_param(IS_I2S_CLOCKSOURCE(hi2s->Init.ClockSource));
291 
292   if (hi2s->State == HAL_I2S_STATE_RESET)
293   {
294     /* Allocate lock resource and initialize it */
295     hi2s->Lock = HAL_UNLOCKED;
296 
297     /* Initialize Default I2S IrqHandler ISR */
298     hi2s->IrqHandlerISR = I2S_IRQHandler;
299 
300 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
301     /* Init the I2S Callback settings */
302     hi2s->TxCpltCallback       = HAL_I2S_TxCpltCallback;          /* Legacy weak TxCpltCallback       */
303     hi2s->RxCpltCallback       = HAL_I2S_RxCpltCallback;          /* Legacy weak RxCpltCallback       */
304 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
305     hi2s->TxRxCpltCallback     = HAL_I2SEx_TxRxCpltCallback;      /* Legacy weak TxRxCpltCallback     */
306 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
307     hi2s->TxHalfCpltCallback   = HAL_I2S_TxHalfCpltCallback;      /* Legacy weak TxHalfCpltCallback   */
308     hi2s->RxHalfCpltCallback   = HAL_I2S_RxHalfCpltCallback;      /* Legacy weak RxHalfCpltCallback   */
309 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
310     hi2s->TxRxHalfCpltCallback = HAL_I2SEx_TxRxHalfCpltCallback;  /* Legacy weak TxRxHalfCpltCallback */
311 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
312     hi2s->ErrorCallback        = HAL_I2S_ErrorCallback;           /* Legacy weak ErrorCallback        */
313 
314     if (hi2s->MspInitCallback == NULL)
315     {
316       hi2s->MspInitCallback = HAL_I2S_MspInit; /* Legacy weak MspInit  */
317     }
318 
319     /* Init the low level hardware : GPIO, CLOCK, NVIC... */
320     hi2s->MspInitCallback(hi2s);
321 #else
322     /* Init the low level hardware : GPIO, CLOCK, CORTEX...etc */
323     HAL_I2S_MspInit(hi2s);
324 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
325   }
326 
327   hi2s->State = HAL_I2S_STATE_BUSY;
328 
329   /*----------------------- SPIx I2SCFGR & I2SPR Configuration ----------------*/
330   /* Clear I2SMOD, I2SE, I2SCFG, PCMSYNC, I2SSTD, CKPOL, DATLEN and CHLEN bits */
331   CLEAR_BIT(hi2s->Instance->I2SCFGR, (SPI_I2SCFGR_CHLEN | SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CKPOL | \
332                                       SPI_I2SCFGR_I2SSTD | SPI_I2SCFGR_PCMSYNC | SPI_I2SCFGR_I2SCFG | \
333                                       SPI_I2SCFGR_I2SE | SPI_I2SCFGR_I2SMOD));
334   hi2s->Instance->I2SPR = 0x0002U;
335 
336   /*----------------------- I2SPR: I2SDIV and ODD Calculation -----------------*/
337   /* If the requested audio frequency is not the default, compute the prescaler */
338   if (hi2s->Init.AudioFreq != I2S_AUDIOFREQ_DEFAULT)
339   {
340     /* Check the frame length (For the Prescaler computing) ********************/
341     if (hi2s->Init.DataFormat == I2S_DATAFORMAT_16B)
342     {
343       /* Packet length is 16 bits */
344       packetlength = 16U;
345     }
346     else
347     {
348       /* Packet length is 32 bits */
349       packetlength = 32U;
350     }
351 
352     /* I2S standard */
353     if (hi2s->Init.Standard <= I2S_STANDARD_LSB)
354     {
355       /* In I2S standard packet length is multiplied by 2 */
356       packetlength = packetlength * 2U;
357     }
358 
359     /* Get the source clock value **********************************************/
360 #if defined(I2S_APB1_APB2_FEATURE)
361     if (IS_I2S_APB1_INSTANCE(hi2s->Instance))
362     {
363       i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_I2S_APB1);
364     }
365     else
366     {
367       i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_I2S_APB2);
368     }
369 #else
370     i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_I2S);
371 #endif /* I2S_APB1_APB2_FEATURE */
372 
373     /* Compute the Real divider depending on the MCLK output state, with a floating point */
374     if (hi2s->Init.MCLKOutput == I2S_MCLKOUTPUT_ENABLE)
375     {
376       /* MCLK output is enabled */
377       if (hi2s->Init.DataFormat != I2S_DATAFORMAT_16B)
378       {
379         tmp = (uint32_t)(((((i2sclk / (packetlength * 4U)) * 10U) / hi2s->Init.AudioFreq)) + 5U);
380       }
381       else
382       {
383         tmp = (uint32_t)(((((i2sclk / (packetlength * 8U)) * 10U) / hi2s->Init.AudioFreq)) + 5U);
384       }
385     }
386     else
387     {
388       /* MCLK output is disabled */
389       tmp = (uint32_t)(((((i2sclk / packetlength) * 10U) / hi2s->Init.AudioFreq)) + 5U);
390     }
391 
392     /* Remove the flatting point */
393     tmp = tmp / 10U;
394 
395     /* Check the parity of the divider */
396     i2sodd = (uint32_t)(tmp & (uint32_t)1U);
397 
398     /* Compute the i2sdiv prescaler */
399     i2sdiv = (uint32_t)((tmp - i2sodd) / 2U);
400 
401     /* Get the Mask for the Odd bit (SPI_I2SPR[8]) register */
402     i2sodd = (uint32_t)(i2sodd << 8U);
403   }
404   else
405   {
406     /* Set the default values */
407     i2sdiv = 2U;
408     i2sodd = 0U;
409   }
410 
411   /* Test if the divider is 1 or 0 or greater than 0xFF */
412   if ((i2sdiv < 2U) || (i2sdiv > 0xFFU))
413   {
414     /* Set the error code and execute error callback*/
415     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_PRESCALER);
416     return  HAL_ERROR;
417   }
418 
419   /*----------------------- SPIx I2SCFGR & I2SPR Configuration ----------------*/
420 
421   /* Write to SPIx I2SPR register the computed value */
422   hi2s->Instance->I2SPR = (uint32_t)((uint32_t)i2sdiv | (uint32_t)(i2sodd | (uint32_t)hi2s->Init.MCLKOutput));
423 
424   /* Clear I2SMOD, I2SE, I2SCFG, PCMSYNC, I2SSTD, CKPOL, DATLEN and CHLEN bits */
425   /* And configure the I2S with the I2S_InitStruct values                      */
426   MODIFY_REG(hi2s->Instance->I2SCFGR, (SPI_I2SCFGR_CHLEN | SPI_I2SCFGR_DATLEN | \
427                                        SPI_I2SCFGR_CKPOL | SPI_I2SCFGR_I2SSTD | \
428                                        SPI_I2SCFGR_PCMSYNC | SPI_I2SCFGR_I2SCFG | \
429                                        SPI_I2SCFGR_I2SE  | SPI_I2SCFGR_I2SMOD), \
430              (SPI_I2SCFGR_I2SMOD | hi2s->Init.Mode | \
431               hi2s->Init.Standard | hi2s->Init.DataFormat | \
432               hi2s->Init.CPOL));
433 
434 #if defined(SPI_I2SCFGR_ASTRTEN)
435   if ((hi2s->Init.Standard == I2S_STANDARD_PCM_SHORT) || ((hi2s->Init.Standard == I2S_STANDARD_PCM_LONG)))
436   {
437     /* Write to SPIx I2SCFGR */
438     SET_BIT(hi2s->Instance->I2SCFGR, SPI_I2SCFGR_ASTRTEN);
439   }
440 #endif /* SPI_I2SCFGR_ASTRTEN */
441 
442 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
443 
444   /* Configure the I2S extended if the full duplex mode is enabled */
445   assert_param(IS_I2S_FULLDUPLEX_MODE(hi2s->Init.FullDuplexMode));
446 
447   if (hi2s->Init.FullDuplexMode == I2S_FULLDUPLEXMODE_ENABLE)
448   {
449     /* Set FullDuplex I2S IrqHandler ISR if FULLDUPLEXMODE is enabled */
450     hi2s->IrqHandlerISR = HAL_I2SEx_FullDuplex_IRQHandler;
451 
452     /* Clear I2SMOD, I2SE, I2SCFG, PCMSYNC, I2SSTD, CKPOL, DATLEN and CHLEN bits */
453     CLEAR_BIT(I2SxEXT(hi2s->Instance)->I2SCFGR, (SPI_I2SCFGR_CHLEN | SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CKPOL | \
454                                                  SPI_I2SCFGR_I2SSTD | SPI_I2SCFGR_PCMSYNC | SPI_I2SCFGR_I2SCFG | \
455                                                  SPI_I2SCFGR_I2SE | SPI_I2SCFGR_I2SMOD));
456     I2SxEXT(hi2s->Instance)->I2SPR = 2U;
457 
458     /* Get the I2SCFGR register value */
459     tmpreg = I2SxEXT(hi2s->Instance)->I2SCFGR;
460 
461     /* Get the mode to be configured for the extended I2S */
462     if ((hi2s->Init.Mode == I2S_MODE_MASTER_TX) || (hi2s->Init.Mode == I2S_MODE_SLAVE_TX))
463     {
464       tmp = I2S_MODE_SLAVE_RX;
465     }
466     else /* I2S_MODE_MASTER_RX ||  I2S_MODE_SLAVE_RX */
467     {
468       tmp = I2S_MODE_SLAVE_TX;
469     }
470 
471     /* Configure the I2S Slave with the I2S Master parameter values */
472     tmpreg |= (uint16_t)((uint16_t)SPI_I2SCFGR_I2SMOD    | \
473                          (uint16_t)tmp                   | \
474                          (uint16_t)hi2s->Init.Standard   | \
475                          (uint16_t)hi2s->Init.DataFormat | \
476                          (uint16_t)hi2s->Init.CPOL);
477 
478     /* Write to SPIx I2SCFGR */
479     WRITE_REG(I2SxEXT(hi2s->Instance)->I2SCFGR, tmpreg);
480   }
481 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
482 
483   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
484   hi2s->State     = HAL_I2S_STATE_READY;
485 
486   return HAL_OK;
487 }
488 
489 /**
490   * @brief DeInitializes the I2S peripheral
491   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
492   *         the configuration information for I2S module
493   * @retval HAL status
494   */
HAL_I2S_DeInit(I2S_HandleTypeDef * hi2s)495 HAL_StatusTypeDef HAL_I2S_DeInit(I2S_HandleTypeDef *hi2s)
496 {
497   /* Check the I2S handle allocation */
498   if (hi2s == NULL)
499   {
500     return HAL_ERROR;
501   }
502 
503   /* Check the parameters */
504   assert_param(IS_I2S_ALL_INSTANCE(hi2s->Instance));
505 
506   hi2s->State = HAL_I2S_STATE_BUSY;
507 
508   /* Disable the I2S Peripheral Clock */
509   __HAL_I2S_DISABLE(hi2s);
510 
511 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
512   if (hi2s->MspDeInitCallback == NULL)
513   {
514     hi2s->MspDeInitCallback = HAL_I2S_MspDeInit; /* Legacy weak MspDeInit  */
515   }
516 
517   /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
518   hi2s->MspDeInitCallback(hi2s);
519 #else
520   /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
521   HAL_I2S_MspDeInit(hi2s);
522 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
523 
524   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
525   hi2s->State     = HAL_I2S_STATE_RESET;
526 
527   /* Release Lock */
528   __HAL_UNLOCK(hi2s);
529 
530   return HAL_OK;
531 }
532 
533 /**
534   * @brief I2S MSP Init
535   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
536   *         the configuration information for I2S module
537   * @retval None
538   */
HAL_I2S_MspInit(I2S_HandleTypeDef * hi2s)539 __weak void HAL_I2S_MspInit(I2S_HandleTypeDef *hi2s)
540 {
541   /* Prevent unused argument(s) compilation warning */
542   UNUSED(hi2s);
543 
544   /* NOTE : This function Should not be modified, when the callback is needed,
545             the HAL_I2S_MspInit could be implemented in the user file
546    */
547 }
548 
549 /**
550   * @brief I2S MSP DeInit
551   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
552   *         the configuration information for I2S module
553   * @retval None
554   */
HAL_I2S_MspDeInit(I2S_HandleTypeDef * hi2s)555 __weak void HAL_I2S_MspDeInit(I2S_HandleTypeDef *hi2s)
556 {
557   /* Prevent unused argument(s) compilation warning */
558   UNUSED(hi2s);
559 
560   /* NOTE : This function Should not be modified, when the callback is needed,
561             the HAL_I2S_MspDeInit could be implemented in the user file
562    */
563 }
564 
565 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
566 /**
567   * @brief  Register a User I2S Callback
568   *         To be used instead of the weak predefined callback
569   * @param  hi2s Pointer to a I2S_HandleTypeDef structure that contains
570   *                the configuration information for the specified I2S.
571   * @param  CallbackID ID of the callback to be registered
572   * @param  pCallback pointer to the Callback function
573   * @retval HAL status
574   */
HAL_I2S_RegisterCallback(I2S_HandleTypeDef * hi2s,HAL_I2S_CallbackIDTypeDef CallbackID,pI2S_CallbackTypeDef pCallback)575 HAL_StatusTypeDef HAL_I2S_RegisterCallback(I2S_HandleTypeDef *hi2s, HAL_I2S_CallbackIDTypeDef CallbackID,
576                                            pI2S_CallbackTypeDef pCallback)
577 {
578   HAL_StatusTypeDef status = HAL_OK;
579 
580   if (pCallback == NULL)
581   {
582     /* Update the error code */
583     hi2s->ErrorCode |= HAL_I2S_ERROR_INVALID_CALLBACK;
584 
585     return HAL_ERROR;
586   }
587   /* Process locked */
588   __HAL_LOCK(hi2s);
589 
590   if (HAL_I2S_STATE_READY == hi2s->State)
591   {
592     switch (CallbackID)
593     {
594       case HAL_I2S_TX_COMPLETE_CB_ID :
595         hi2s->TxCpltCallback = pCallback;
596         break;
597 
598       case HAL_I2S_RX_COMPLETE_CB_ID :
599         hi2s->RxCpltCallback = pCallback;
600         break;
601 
602 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
603       case HAL_I2S_TX_RX_COMPLETE_CB_ID :
604         hi2s->TxRxCpltCallback = pCallback;
605         break;
606 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
607 
608       case HAL_I2S_TX_HALF_COMPLETE_CB_ID :
609         hi2s->TxHalfCpltCallback = pCallback;
610         break;
611 
612       case HAL_I2S_RX_HALF_COMPLETE_CB_ID :
613         hi2s->RxHalfCpltCallback = pCallback;
614         break;
615 
616 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
617       case HAL_I2S_TX_RX_HALF_COMPLETE_CB_ID :
618         hi2s->TxRxHalfCpltCallback = pCallback;
619         break;
620 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
621 
622       case HAL_I2S_ERROR_CB_ID :
623         hi2s->ErrorCallback = pCallback;
624         break;
625 
626       case HAL_I2S_MSPINIT_CB_ID :
627         hi2s->MspInitCallback = pCallback;
628         break;
629 
630       case HAL_I2S_MSPDEINIT_CB_ID :
631         hi2s->MspDeInitCallback = pCallback;
632         break;
633 
634       default :
635         /* Update the error code */
636         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
637 
638         /* Return error status */
639         status =  HAL_ERROR;
640         break;
641     }
642   }
643   else if (HAL_I2S_STATE_RESET == hi2s->State)
644   {
645     switch (CallbackID)
646     {
647       case HAL_I2S_MSPINIT_CB_ID :
648         hi2s->MspInitCallback = pCallback;
649         break;
650 
651       case HAL_I2S_MSPDEINIT_CB_ID :
652         hi2s->MspDeInitCallback = pCallback;
653         break;
654 
655       default :
656         /* Update the error code */
657         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
658 
659         /* Return error status */
660         status =  HAL_ERROR;
661         break;
662     }
663   }
664   else
665   {
666     /* Update the error code */
667     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
668 
669     /* Return error status */
670     status =  HAL_ERROR;
671   }
672 
673   /* Release Lock */
674   __HAL_UNLOCK(hi2s);
675   return status;
676 }
677 
678 /**
679   * @brief  Unregister an I2S Callback
680   *         I2S callback is redirected to the weak predefined callback
681   * @param  hi2s Pointer to a I2S_HandleTypeDef structure that contains
682   *                the configuration information for the specified I2S.
683   * @param  CallbackID ID of the callback to be unregistered
684   * @retval HAL status
685   */
HAL_I2S_UnRegisterCallback(I2S_HandleTypeDef * hi2s,HAL_I2S_CallbackIDTypeDef CallbackID)686 HAL_StatusTypeDef HAL_I2S_UnRegisterCallback(I2S_HandleTypeDef *hi2s, HAL_I2S_CallbackIDTypeDef CallbackID)
687 {
688   HAL_StatusTypeDef status = HAL_OK;
689 
690   /* Process locked */
691   __HAL_LOCK(hi2s);
692 
693   if (HAL_I2S_STATE_READY == hi2s->State)
694   {
695     switch (CallbackID)
696     {
697       case HAL_I2S_TX_COMPLETE_CB_ID :
698         hi2s->TxCpltCallback = HAL_I2S_TxCpltCallback;                /* Legacy weak TxCpltCallback       */
699         break;
700 
701       case HAL_I2S_RX_COMPLETE_CB_ID :
702         hi2s->RxCpltCallback = HAL_I2S_RxCpltCallback;                /* Legacy weak RxCpltCallback       */
703         break;
704 
705 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
706       case HAL_I2S_TX_RX_COMPLETE_CB_ID :
707         hi2s->TxRxCpltCallback = HAL_I2SEx_TxRxCpltCallback;          /* Legacy weak TxRxCpltCallback     */
708         break;
709 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
710 
711       case HAL_I2S_TX_HALF_COMPLETE_CB_ID :
712         hi2s->TxHalfCpltCallback = HAL_I2S_TxHalfCpltCallback;        /* Legacy weak TxHalfCpltCallback   */
713         break;
714 
715       case HAL_I2S_RX_HALF_COMPLETE_CB_ID :
716         hi2s->RxHalfCpltCallback = HAL_I2S_RxHalfCpltCallback;        /* Legacy weak RxHalfCpltCallback   */
717         break;
718 
719 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
720       case HAL_I2S_TX_RX_HALF_COMPLETE_CB_ID :
721         hi2s->TxRxHalfCpltCallback = HAL_I2SEx_TxRxHalfCpltCallback;  /* Legacy weak TxRxHalfCpltCallback */
722         break;
723 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
724 
725       case HAL_I2S_ERROR_CB_ID :
726         hi2s->ErrorCallback = HAL_I2S_ErrorCallback;                  /* Legacy weak ErrorCallback        */
727         break;
728 
729       case HAL_I2S_MSPINIT_CB_ID :
730         hi2s->MspInitCallback = HAL_I2S_MspInit;                      /* Legacy weak MspInit              */
731         break;
732 
733       case HAL_I2S_MSPDEINIT_CB_ID :
734         hi2s->MspDeInitCallback = HAL_I2S_MspDeInit;                  /* Legacy weak MspDeInit            */
735         break;
736 
737       default :
738         /* Update the error code */
739         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
740 
741         /* Return error status */
742         status =  HAL_ERROR;
743         break;
744     }
745   }
746   else if (HAL_I2S_STATE_RESET == hi2s->State)
747   {
748     switch (CallbackID)
749     {
750       case HAL_I2S_MSPINIT_CB_ID :
751         hi2s->MspInitCallback = HAL_I2S_MspInit;                      /* Legacy weak MspInit              */
752         break;
753 
754       case HAL_I2S_MSPDEINIT_CB_ID :
755         hi2s->MspDeInitCallback = HAL_I2S_MspDeInit;                  /* Legacy weak MspDeInit            */
756         break;
757 
758       default :
759         /* Update the error code */
760         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
761 
762         /* Return error status */
763         status =  HAL_ERROR;
764         break;
765     }
766   }
767   else
768   {
769     /* Update the error code */
770     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
771 
772     /* Return error status */
773     status =  HAL_ERROR;
774   }
775 
776   /* Release Lock */
777   __HAL_UNLOCK(hi2s);
778   return status;
779 }
780 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
781 /**
782   * @}
783   */
784 
785 /** @defgroup I2S_Exported_Functions_Group2 IO operation functions
786   *  @brief Data transfers functions
787   *
788 @verbatim
789  ===============================================================================
790                       ##### IO operation functions #####
791  ===============================================================================
792     [..]
793     This subsection provides a set of functions allowing to manage the I2S data
794     transfers.
795 
796     (#) There are two modes of transfer:
797        (++) Blocking mode : The communication is performed in the polling mode.
798             The status of all data processing is returned by the same function
799             after finishing transfer.
800        (++) No-Blocking mode : The communication is performed using Interrupts
801             or DMA. These functions return the status of the transfer startup.
802             The end of the data processing will be indicated through the
803             dedicated I2S IRQ when using Interrupt mode or the DMA IRQ when
804             using DMA mode.
805 
806     (#) Blocking mode functions are :
807         (++) HAL_I2S_Transmit()
808         (++) HAL_I2S_Receive()
809 
810     (#) No-Blocking mode functions with Interrupt are :
811         (++) HAL_I2S_Transmit_IT()
812         (++) HAL_I2S_Receive_IT()
813 
814     (#) No-Blocking mode functions with DMA are :
815         (++) HAL_I2S_Transmit_DMA()
816         (++) HAL_I2S_Receive_DMA()
817 
818     (#) A set of Transfer Complete Callbacks are provided in non Blocking mode:
819         (++) HAL_I2S_TxCpltCallback()
820         (++) HAL_I2S_RxCpltCallback()
821         (++) HAL_I2S_ErrorCallback()
822 
823 @endverbatim
824   * @{
825   */
826 
827 /**
828   * @brief  Transmit an amount of data in blocking mode
829   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
830   *         the configuration information for I2S module
831   * @param  pData a 16-bit pointer to data buffer.
832   * @param  Size number of data sample to be sent:
833   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
834   *         configuration phase, the Size parameter means the number of 16-bit data length
835   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
836   *         the Size parameter means the number of 24-bit or 32-bit data length.
837   * @param  Timeout Timeout duration
838   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
839   *         between Master and Slave(example: audio streaming).
840   * @retval HAL status
841   */
HAL_I2S_Transmit(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size,uint32_t Timeout)842 HAL_StatusTypeDef HAL_I2S_Transmit(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size, uint32_t Timeout)
843 {
844   uint32_t tmpreg_cfgr;
845 
846   if ((pData == NULL) || (Size == 0U))
847   {
848     return  HAL_ERROR;
849   }
850 
851   if (hi2s->State != HAL_I2S_STATE_READY)
852   {
853     return HAL_BUSY;
854   }
855 
856   /* Process Locked */
857   __HAL_LOCK(hi2s);
858 
859   /* Set state and reset error code */
860   hi2s->State = HAL_I2S_STATE_BUSY_TX;
861   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
862   hi2s->pTxBuffPtr = pData;
863 
864   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
865 
866   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
867   {
868     hi2s->TxXferSize = (Size << 1U);
869     hi2s->TxXferCount = (Size << 1U);
870   }
871   else
872   {
873     hi2s->TxXferSize = Size;
874     hi2s->TxXferCount = Size;
875   }
876 
877   tmpreg_cfgr = hi2s->Instance->I2SCFGR;
878 
879   /* Check if the I2S is already enabled */
880   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
881   {
882     /* Enable I2S peripheral */
883     __HAL_I2S_ENABLE(hi2s);
884   }
885 
886   /* Wait until TXE flag is set */
887   if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXE, SET, Timeout) != HAL_OK)
888   {
889     /* Set the error code */
890     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
891     hi2s->State = HAL_I2S_STATE_READY;
892     __HAL_UNLOCK(hi2s);
893     return HAL_ERROR;
894   }
895 
896   while (hi2s->TxXferCount > 0U)
897   {
898     hi2s->Instance->DR = (*hi2s->pTxBuffPtr);
899     hi2s->pTxBuffPtr++;
900     hi2s->TxXferCount--;
901 
902     /* Wait until TXE flag is set */
903     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXE, SET, Timeout) != HAL_OK)
904     {
905       /* Set the error code */
906       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
907       hi2s->State = HAL_I2S_STATE_READY;
908       __HAL_UNLOCK(hi2s);
909       return HAL_ERROR;
910     }
911 
912     /* Check if an underrun occurs */
913     if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_UDR) == SET)
914     {
915       /* Clear underrun flag */
916       __HAL_I2S_CLEAR_UDRFLAG(hi2s);
917 
918       /* Set the error code */
919       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
920     }
921   }
922 
923   /* Check if Slave mode is selected */
924   if (((tmpreg_cfgr & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_TX)
925       || ((tmpreg_cfgr & SPI_I2SCFGR_I2SCFG) == I2S_MODE_SLAVE_RX))
926   {
927     /* Wait until Busy flag is reset */
928     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_BSY, RESET, Timeout) != HAL_OK)
929     {
930       /* Set the error code */
931       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
932       hi2s->State = HAL_I2S_STATE_READY;
933       __HAL_UNLOCK(hi2s);
934       return HAL_ERROR;
935     }
936   }
937 
938   hi2s->State = HAL_I2S_STATE_READY;
939   __HAL_UNLOCK(hi2s);
940   return HAL_OK;
941 }
942 
943 /**
944   * @brief  Receive an amount of data in blocking mode
945   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
946   *         the configuration information for I2S module
947   * @param  pData a 16-bit pointer to data buffer.
948   * @param  Size number of data sample to be sent:
949   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
950   *         configuration phase, the Size parameter means the number of 16-bit data length
951   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
952   *         the Size parameter means the number of 24-bit or 32-bit data length.
953   * @param  Timeout Timeout duration
954   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
955   *         between Master and Slave(example: audio streaming).
956   * @note   In I2S Master Receiver mode, just after enabling the peripheral the clock will be generate
957   *         in continuous way and as the I2S is not disabled at the end of the I2S transaction.
958   * @retval HAL status
959   */
HAL_I2S_Receive(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size,uint32_t Timeout)960 HAL_StatusTypeDef HAL_I2S_Receive(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size, uint32_t Timeout)
961 {
962   uint32_t tmpreg_cfgr;
963 
964   if ((pData == NULL) || (Size == 0U))
965   {
966     return  HAL_ERROR;
967   }
968 
969   if (hi2s->State != HAL_I2S_STATE_READY)
970   {
971     return HAL_BUSY;
972   }
973 
974   /* Process Locked */
975   __HAL_LOCK(hi2s);
976 
977   /* Set state and reset error code */
978   hi2s->State = HAL_I2S_STATE_BUSY_RX;
979   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
980   hi2s->pRxBuffPtr = pData;
981 
982   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
983 
984   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
985   {
986     hi2s->RxXferSize = (Size << 1U);
987     hi2s->RxXferCount = (Size << 1U);
988   }
989   else
990   {
991     hi2s->RxXferSize = Size;
992     hi2s->RxXferCount = Size;
993   }
994 
995   /* Check if the I2S is already enabled */
996   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
997   {
998     /* Enable I2S peripheral */
999     __HAL_I2S_ENABLE(hi2s);
1000   }
1001 
1002   /* Check if Master Receiver mode is selected */
1003   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_RX)
1004   {
1005     /* Clear the Overrun Flag by a read operation on the SPI_DR register followed by a read
1006     access to the SPI_SR register. */
1007     __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1008   }
1009 
1010   /* Receive data */
1011   while (hi2s->RxXferCount > 0U)
1012   {
1013     /* Wait until RXNE flag is set */
1014     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_RXNE, SET, Timeout) != HAL_OK)
1015     {
1016       /* Set the error code */
1017       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1018       hi2s->State = HAL_I2S_STATE_READY;
1019       __HAL_UNLOCK(hi2s);
1020       return HAL_ERROR;
1021     }
1022 
1023     (*hi2s->pRxBuffPtr) = (uint16_t)hi2s->Instance->DR;
1024     hi2s->pRxBuffPtr++;
1025     hi2s->RxXferCount--;
1026 
1027     /* Check if an overrun occurs */
1028     if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_OVR) == SET)
1029     {
1030       /* Clear overrun flag */
1031       __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1032 
1033       /* Set the error code */
1034       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
1035     }
1036   }
1037 
1038   hi2s->State = HAL_I2S_STATE_READY;
1039   __HAL_UNLOCK(hi2s);
1040   return HAL_OK;
1041 }
1042 
1043 /**
1044   * @brief  Transmit an amount of data in non-blocking mode with Interrupt
1045   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1046   *         the configuration information for I2S module
1047   * @param  pData a 16-bit pointer to data buffer.
1048   * @param  Size number of data sample to be sent:
1049   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1050   *         configuration phase, the Size parameter means the number of 16-bit data length
1051   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1052   *         the Size parameter means the number of 24-bit or 32-bit data length.
1053   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1054   *         between Master and Slave(example: audio streaming).
1055   * @retval HAL status
1056   */
HAL_I2S_Transmit_IT(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1057 HAL_StatusTypeDef HAL_I2S_Transmit_IT(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1058 {
1059   uint32_t tmpreg_cfgr;
1060 
1061   if ((pData == NULL) || (Size == 0U))
1062   {
1063     return  HAL_ERROR;
1064   }
1065 
1066   if (hi2s->State != HAL_I2S_STATE_READY)
1067   {
1068     return HAL_BUSY;
1069   }
1070 
1071   /* Process Locked */
1072   __HAL_LOCK(hi2s);
1073 
1074   /* Set state and reset error code */
1075   hi2s->State = HAL_I2S_STATE_BUSY_TX;
1076   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1077   hi2s->pTxBuffPtr = pData;
1078 
1079   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
1080 
1081   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
1082   {
1083     hi2s->TxXferSize = (Size << 1U);
1084     hi2s->TxXferCount = (Size << 1U);
1085   }
1086   else
1087   {
1088     hi2s->TxXferSize = Size;
1089     hi2s->TxXferCount = Size;
1090   }
1091 
1092   __HAL_UNLOCK(hi2s);
1093 
1094   /* Enable TXE and ERR interrupt */
1095   __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));
1096 
1097   /* Check if the I2S is already enabled */
1098   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
1099   {
1100     /* Enable I2S peripheral */
1101     __HAL_I2S_ENABLE(hi2s);
1102   }
1103 
1104   return HAL_OK;
1105 }
1106 
1107 /**
1108   * @brief  Receive an amount of data in non-blocking mode with Interrupt
1109   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1110   *         the configuration information for I2S module
1111   * @param  pData a 16-bit pointer to the Receive data buffer.
1112   * @param  Size number of data sample to be sent:
1113   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1114   *         configuration phase, the Size parameter means the number of 16-bit data length
1115   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1116   *         the Size parameter means the number of 24-bit or 32-bit data length.
1117   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1118   *         between Master and Slave(example: audio streaming).
1119   * @note   It is recommended to use DMA for the I2S receiver to avoid de-synchronization
1120   * between Master and Slave otherwise the I2S interrupt should be optimized.
1121   * @retval HAL status
1122   */
HAL_I2S_Receive_IT(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1123 HAL_StatusTypeDef HAL_I2S_Receive_IT(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1124 {
1125   uint32_t tmpreg_cfgr;
1126 
1127   if ((pData == NULL) || (Size == 0U))
1128   {
1129     return  HAL_ERROR;
1130   }
1131 
1132   if (hi2s->State != HAL_I2S_STATE_READY)
1133   {
1134     return HAL_BUSY;
1135   }
1136 
1137   /* Process Locked */
1138   __HAL_LOCK(hi2s);
1139 
1140   /* Set state and reset error code */
1141   hi2s->State = HAL_I2S_STATE_BUSY_RX;
1142   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1143   hi2s->pRxBuffPtr = pData;
1144 
1145   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
1146 
1147   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
1148   {
1149     hi2s->RxXferSize = (Size << 1U);
1150     hi2s->RxXferCount = (Size << 1U);
1151   }
1152   else
1153   {
1154     hi2s->RxXferSize = Size;
1155     hi2s->RxXferCount = Size;
1156   }
1157 
1158   __HAL_UNLOCK(hi2s);
1159 
1160   /* Enable RXNE and ERR interrupt */
1161   __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));
1162 
1163   /* Check if the I2S is already enabled */
1164   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SE) != SPI_I2SCFGR_I2SE)
1165   {
1166     /* Enable I2S peripheral */
1167     __HAL_I2S_ENABLE(hi2s);
1168   }
1169 
1170   return HAL_OK;
1171 }
1172 
1173 /**
1174   * @brief  Transmit an amount of data in non-blocking mode with DMA
1175   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1176   *         the configuration information for I2S module
1177   * @param  pData a 16-bit pointer to the Transmit data buffer.
1178   * @param  Size number of data sample to be sent:
1179   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1180   *         configuration phase, the Size parameter means the number of 16-bit data length
1181   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1182   *         the Size parameter means the number of 24-bit or 32-bit data length.
1183   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1184   *         between Master and Slave(example: audio streaming).
1185   * @retval HAL status
1186   */
HAL_I2S_Transmit_DMA(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1187 HAL_StatusTypeDef HAL_I2S_Transmit_DMA(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1188 {
1189   uint32_t tmpreg_cfgr;
1190 
1191   if ((pData == NULL) || (Size == 0U))
1192   {
1193     return  HAL_ERROR;
1194   }
1195 
1196   if (hi2s->State != HAL_I2S_STATE_READY)
1197   {
1198     return HAL_BUSY;
1199   }
1200 
1201   /* Process Locked */
1202   __HAL_LOCK(hi2s);
1203 
1204   /* Set state and reset error code */
1205   hi2s->State = HAL_I2S_STATE_BUSY_TX;
1206   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1207   hi2s->pTxBuffPtr = pData;
1208 
1209   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
1210 
1211   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
1212   {
1213     hi2s->TxXferSize = (Size << 1U);
1214     hi2s->TxXferCount = (Size << 1U);
1215   }
1216   else
1217   {
1218     hi2s->TxXferSize = Size;
1219     hi2s->TxXferCount = Size;
1220   }
1221 
1222   /* Set the I2S Tx DMA Half transfer complete callback */
1223   hi2s->hdmatx->XferHalfCpltCallback = I2S_DMATxHalfCplt;
1224 
1225   /* Set the I2S Tx DMA transfer complete callback */
1226   hi2s->hdmatx->XferCpltCallback = I2S_DMATxCplt;
1227 
1228   /* Set the DMA error callback */
1229   hi2s->hdmatx->XferErrorCallback = I2S_DMAError;
1230 
1231   /* Enable the Tx DMA Stream/Channel */
1232   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmatx,
1233                                  (uint32_t)hi2s->pTxBuffPtr,
1234                                  (uint32_t)&hi2s->Instance->DR,
1235                                  hi2s->TxXferSize))
1236   {
1237     /* Update SPI error code */
1238     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1239     hi2s->State = HAL_I2S_STATE_READY;
1240 
1241     __HAL_UNLOCK(hi2s);
1242     return HAL_ERROR;
1243   }
1244 
1245   __HAL_UNLOCK(hi2s);
1246 
1247   /* Check if the I2S Tx request is already enabled */
1248   if (HAL_IS_BIT_CLR(hi2s->Instance->CR2, SPI_CR2_TXDMAEN))
1249   {
1250     /* Enable Tx DMA Request */
1251     SET_BIT(hi2s->Instance->CR2, SPI_CR2_TXDMAEN);
1252   }
1253 
1254   /* Check if the I2S is already enabled */
1255   if (HAL_IS_BIT_CLR(hi2s->Instance->I2SCFGR, SPI_I2SCFGR_I2SE))
1256   {
1257     /* Enable I2S peripheral */
1258     __HAL_I2S_ENABLE(hi2s);
1259   }
1260 
1261   return HAL_OK;
1262 }
1263 
1264 /**
1265   * @brief  Receive an amount of data in non-blocking mode with DMA
1266   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1267   *         the configuration information for I2S module
1268   * @param  pData a 16-bit pointer to the Receive data buffer.
1269   * @param  Size number of data sample to be sent:
1270   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1271   *         configuration phase, the Size parameter means the number of 16-bit data length
1272   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1273   *         the Size parameter means the number of 24-bit or 32-bit data length.
1274   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1275   *         between Master and Slave(example: audio streaming).
1276   * @retval HAL status
1277   */
HAL_I2S_Receive_DMA(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1278 HAL_StatusTypeDef HAL_I2S_Receive_DMA(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1279 {
1280   uint32_t tmpreg_cfgr;
1281 
1282   if ((pData == NULL) || (Size == 0U))
1283   {
1284     return  HAL_ERROR;
1285   }
1286 
1287   if (hi2s->State != HAL_I2S_STATE_READY)
1288   {
1289     return HAL_BUSY;
1290   }
1291 
1292   /* Process Locked */
1293   __HAL_LOCK(hi2s);
1294 
1295   /* Set state and reset error code */
1296   hi2s->State = HAL_I2S_STATE_BUSY_RX;
1297   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1298   hi2s->pRxBuffPtr = pData;
1299 
1300   tmpreg_cfgr = hi2s->Instance->I2SCFGR & (SPI_I2SCFGR_DATLEN | SPI_I2SCFGR_CHLEN);
1301 
1302   if ((tmpreg_cfgr == I2S_DATAFORMAT_24B) || (tmpreg_cfgr == I2S_DATAFORMAT_32B))
1303   {
1304     hi2s->RxXferSize = (Size << 1U);
1305     hi2s->RxXferCount = (Size << 1U);
1306   }
1307   else
1308   {
1309     hi2s->RxXferSize = Size;
1310     hi2s->RxXferCount = Size;
1311   }
1312 
1313   /* Set the I2S Rx DMA Half transfer complete callback */
1314   hi2s->hdmarx->XferHalfCpltCallback = I2S_DMARxHalfCplt;
1315 
1316   /* Set the I2S Rx DMA transfer complete callback */
1317   hi2s->hdmarx->XferCpltCallback = I2S_DMARxCplt;
1318 
1319   /* Set the DMA error callback */
1320   hi2s->hdmarx->XferErrorCallback = I2S_DMAError;
1321 
1322   /* Check if Master Receiver mode is selected */
1323   if ((hi2s->Instance->I2SCFGR & SPI_I2SCFGR_I2SCFG) == I2S_MODE_MASTER_RX)
1324   {
1325     /* Clear the Overrun Flag by a read operation to the SPI_DR register followed by a read
1326     access to the SPI_SR register. */
1327     __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1328   }
1329 
1330   /* Enable the Rx DMA Stream/Channel */
1331   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmarx, (uint32_t)&hi2s->Instance->DR, (uint32_t)hi2s->pRxBuffPtr,
1332                                  hi2s->RxXferSize))
1333   {
1334     /* Update SPI error code */
1335     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1336     hi2s->State = HAL_I2S_STATE_READY;
1337 
1338     __HAL_UNLOCK(hi2s);
1339     return HAL_ERROR;
1340   }
1341 
1342   __HAL_UNLOCK(hi2s);
1343 
1344   /* Check if the I2S Rx request is already enabled */
1345   if (HAL_IS_BIT_CLR(hi2s->Instance->CR2, SPI_CR2_RXDMAEN))
1346   {
1347     /* Enable Rx DMA Request */
1348     SET_BIT(hi2s->Instance->CR2, SPI_CR2_RXDMAEN);
1349   }
1350 
1351   /* Check if the I2S is already enabled */
1352   if (HAL_IS_BIT_CLR(hi2s->Instance->I2SCFGR, SPI_I2SCFGR_I2SE))
1353   {
1354     /* Enable I2S peripheral */
1355     __HAL_I2S_ENABLE(hi2s);
1356   }
1357 
1358   return HAL_OK;
1359 }
1360 
1361 /**
1362   * @brief  Pauses the audio DMA Stream/Channel playing from the Media.
1363   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1364   *         the configuration information for I2S module
1365   * @retval HAL status
1366   */
HAL_I2S_DMAPause(I2S_HandleTypeDef * hi2s)1367 HAL_StatusTypeDef HAL_I2S_DMAPause(I2S_HandleTypeDef *hi2s)
1368 {
1369   /* Process Locked */
1370   __HAL_LOCK(hi2s);
1371 
1372   if (hi2s->State == HAL_I2S_STATE_BUSY_TX)
1373   {
1374     /* Disable the I2S DMA Tx request */
1375     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_TXDMAEN);
1376   }
1377   else if (hi2s->State == HAL_I2S_STATE_BUSY_RX)
1378   {
1379     /* Disable the I2S DMA Rx request */
1380     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_RXDMAEN);
1381   }
1382 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
1383   else if (hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
1384   {
1385     /* Pause the audio file playing by disabling the I2S DMA request */
1386     CLEAR_BIT(hi2s->Instance->CR2, (SPI_CR2_TXDMAEN | SPI_CR2_RXDMAEN));
1387     CLEAR_BIT(I2SxEXT(hi2s->Instance)->CR2, (SPI_CR2_TXDMAEN | SPI_CR2_RXDMAEN));
1388   }
1389 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
1390   else
1391   {
1392     /* nothing to do */
1393   }
1394 
1395   /* Process Unlocked */
1396   __HAL_UNLOCK(hi2s);
1397 
1398   return HAL_OK;
1399 }
1400 
1401 /**
1402   * @brief  Resumes the audio DMA Stream/Channel playing from the Media.
1403   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1404   *         the configuration information for I2S module
1405   * @retval HAL status
1406   */
HAL_I2S_DMAResume(I2S_HandleTypeDef * hi2s)1407 HAL_StatusTypeDef HAL_I2S_DMAResume(I2S_HandleTypeDef *hi2s)
1408 {
1409   /* Process Locked */
1410   __HAL_LOCK(hi2s);
1411 
1412   if (hi2s->State == HAL_I2S_STATE_BUSY_TX)
1413   {
1414     /* Enable the I2S DMA Tx request */
1415     SET_BIT(hi2s->Instance->CR2, SPI_CR2_TXDMAEN);
1416   }
1417   else if (hi2s->State == HAL_I2S_STATE_BUSY_RX)
1418   {
1419     /* Enable the I2S DMA Rx request */
1420     SET_BIT(hi2s->Instance->CR2, SPI_CR2_RXDMAEN);
1421   }
1422 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
1423   else if (hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
1424   {
1425     /* Pause the audio file playing by disabling the I2S DMA request */
1426     SET_BIT(hi2s->Instance->CR2, (SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
1427     SET_BIT(I2SxEXT(hi2s->Instance)->CR2, (SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
1428 
1429     /* If the I2Sext peripheral is still not enabled, enable it */
1430     if ((I2SxEXT(hi2s->Instance)->I2SCFGR & SPI_I2SCFGR_I2SE) == 0U)
1431     {
1432       /* Enable I2Sext peripheral */
1433       __HAL_I2SEXT_ENABLE(hi2s);
1434     }
1435   }
1436 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
1437   else
1438   {
1439     /* nothing to do */
1440   }
1441 
1442   /* If the I2S peripheral is still not enabled, enable it */
1443   if (HAL_IS_BIT_CLR(hi2s->Instance->I2SCFGR, SPI_I2SCFGR_I2SE))
1444   {
1445     /* Enable I2S peripheral */
1446     __HAL_I2S_ENABLE(hi2s);
1447   }
1448 
1449   /* Process Unlocked */
1450   __HAL_UNLOCK(hi2s);
1451 
1452   return HAL_OK;
1453 }
1454 
1455 /**
1456   * @brief  Stops the audio DMA Stream/Channel playing from the Media.
1457   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1458   *         the configuration information for I2S module
1459   * @retval HAL status
1460   */
HAL_I2S_DMAStop(I2S_HandleTypeDef * hi2s)1461 HAL_StatusTypeDef HAL_I2S_DMAStop(I2S_HandleTypeDef *hi2s)
1462 {
1463 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
1464   uint32_t tickstart;
1465 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
1466   HAL_StatusTypeDef errorcode = HAL_OK;
1467   /* The Lock is not implemented on this API to allow the user application
1468      to call the HAL SPI API under callbacks HAL_I2S_TxCpltCallback() or HAL_I2S_RxCpltCallback()
1469      when calling HAL_DMA_Abort() API the DMA TX or RX Transfer complete interrupt is generated
1470      and the correspond call back is executed HAL_I2S_TxCpltCallback() or HAL_I2S_RxCpltCallback()
1471      */
1472 
1473   if ((hi2s->Init.Mode == I2S_MODE_MASTER_TX) || (hi2s->Init.Mode == I2S_MODE_SLAVE_TX))
1474   {
1475     /* Abort the I2S DMA tx Stream/Channel */
1476     if (hi2s->hdmatx != NULL)
1477     {
1478       /* Disable the I2S DMA tx Stream/Channel */
1479       if (HAL_OK != HAL_DMA_Abort(hi2s->hdmatx))
1480       {
1481         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1482         errorcode = HAL_ERROR;
1483       }
1484     }
1485 
1486     /* Wait until TXE flag is set */
1487     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXE, SET, I2S_TIMEOUT_FLAG) != HAL_OK)
1488     {
1489       /* Set the error code */
1490       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1491       hi2s->State = HAL_I2S_STATE_READY;
1492       errorcode   = HAL_ERROR;
1493     }
1494 
1495     /* Wait until BSY flag is Reset */
1496     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_BSY, RESET, I2S_TIMEOUT_FLAG) != HAL_OK)
1497     {
1498       /* Set the error code */
1499       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1500       hi2s->State = HAL_I2S_STATE_READY;
1501       errorcode   = HAL_ERROR;
1502     }
1503 
1504     /* Disable I2S peripheral */
1505     __HAL_I2S_DISABLE(hi2s);
1506 
1507     /* Clear UDR flag */
1508     __HAL_I2S_CLEAR_UDRFLAG(hi2s);
1509 
1510     /* Disable the I2S Tx DMA requests */
1511     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_TXDMAEN);
1512 
1513 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
1514 
1515     if (hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
1516     {
1517       /* Abort the I2S DMA rx Stream/Channel */
1518       if (hi2s->hdmarx != NULL)
1519       {
1520         /* Disable the I2S DMA rx Stream/Channel */
1521         if (HAL_OK != HAL_DMA_Abort(hi2s->hdmarx))
1522         {
1523           SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1524           errorcode = HAL_ERROR;
1525         }
1526       }
1527 
1528       /* Disable I2Sext peripheral */
1529       __HAL_I2SEXT_DISABLE(hi2s);
1530 
1531       /* Clear OVR flag */
1532       __HAL_I2SEXT_CLEAR_OVRFLAG(hi2s);
1533 
1534       /* Disable the I2SxEXT DMA request */
1535       CLEAR_BIT(I2SxEXT(hi2s->Instance)->CR2, SPI_CR2_RXDMAEN);
1536 
1537       if (hi2s->Init.Mode == I2S_MODE_SLAVE_TX)
1538       {
1539         /* Set the error code */
1540         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_BUSY_LINE_RX);
1541 
1542         /* Set the I2S State ready */
1543         hi2s->State = HAL_I2S_STATE_READY;
1544         errorcode = HAL_ERROR;
1545       }
1546       else
1547       {
1548         /* Read DR to Flush RX Data */
1549         READ_REG(I2SxEXT(hi2s->Instance)->DR);
1550       }
1551     }
1552 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
1553   }
1554 
1555   else if ((hi2s->Init.Mode == I2S_MODE_MASTER_RX) || (hi2s->Init.Mode == I2S_MODE_SLAVE_RX))
1556   {
1557     /* Abort the I2S DMA rx Stream/Channel */
1558     if (hi2s->hdmarx != NULL)
1559     {
1560       /* Disable the I2S DMA rx Stream/Channel */
1561       if (HAL_OK != HAL_DMA_Abort(hi2s->hdmarx))
1562       {
1563         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1564         errorcode = HAL_ERROR;
1565       }
1566     }
1567 #if defined (SPI_I2S_FULLDUPLEX_SUPPORT)
1568 
1569     if (hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
1570     {
1571       /* Abort the I2S DMA tx Stream/Channel */
1572       if (hi2s->hdmatx != NULL)
1573       {
1574         /* Disable the I2S DMA tx Stream/Channel */
1575         if (HAL_OK != HAL_DMA_Abort(hi2s->hdmatx))
1576         {
1577           SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1578           errorcode = HAL_ERROR;
1579         }
1580       }
1581 
1582       tickstart = HAL_GetTick();
1583 
1584       /* Wait until TXE flag is set */
1585       while (__HAL_I2SEXT_GET_FLAG(hi2s, I2S_FLAG_TXE) != SET)
1586       {
1587         if (((HAL_GetTick() - tickstart) > I2S_TIMEOUT_FLAG))
1588         {
1589           /* Set the error code */
1590           SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1591 
1592           /* Set the I2S State ready */
1593           hi2s->State = HAL_I2S_STATE_READY;
1594           errorcode   = HAL_ERROR;
1595         }
1596       }
1597 
1598       /* Wait until BSY flag is Reset */
1599       while (__HAL_I2SEXT_GET_FLAG(hi2s, I2S_FLAG_BSY) != RESET)
1600       {
1601         if (((HAL_GetTick() - tickstart) > I2S_TIMEOUT_FLAG))
1602         {
1603           /* Set the error code */
1604           SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1605 
1606           /* Set the I2S State ready */
1607           hi2s->State = HAL_I2S_STATE_READY;
1608           errorcode   = HAL_ERROR;
1609         }
1610       }
1611 
1612       /* Disable I2Sext peripheral */
1613       __HAL_I2SEXT_DISABLE(hi2s);
1614 
1615       /* Clear UDR flag */
1616       __HAL_I2SEXT_CLEAR_UDRFLAG(hi2s);
1617 
1618       /* Disable the I2SxEXT DMA request */
1619       CLEAR_BIT(I2SxEXT(hi2s->Instance)->CR2, SPI_CR2_TXDMAEN);
1620     }
1621 #endif /* SPI_I2S_FULLDUPLEX_SUPPORT */
1622 
1623     /* Disable I2S peripheral */
1624     __HAL_I2S_DISABLE(hi2s);
1625 
1626     /* Clear OVR flag */
1627     __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1628 
1629     /* Disable the I2S Rx DMA request */
1630     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_RXDMAEN);
1631 
1632     if (hi2s->Init.Mode == I2S_MODE_SLAVE_RX)
1633     {
1634       /* Set the error code */
1635       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_BUSY_LINE_RX);
1636 
1637       /* Set the I2S State ready */
1638       hi2s->State = HAL_I2S_STATE_READY;
1639       errorcode = HAL_ERROR;
1640     }
1641     else
1642     {
1643       /* Read DR to Flush RX Data */
1644       READ_REG((hi2s->Instance)->DR);
1645     }
1646   }
1647 
1648   hi2s->State = HAL_I2S_STATE_READY;
1649 
1650   return errorcode;
1651 }
1652 
1653 /**
1654   * @brief  This function handles I2S interrupt request.
1655   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1656   *         the configuration information for I2S module
1657   * @retval None
1658   */
HAL_I2S_IRQHandler(I2S_HandleTypeDef * hi2s)1659 void HAL_I2S_IRQHandler(I2S_HandleTypeDef *hi2s)
1660 {
1661   /* Call the IrqHandler ISR set during HAL_I2S_INIT */
1662   hi2s->IrqHandlerISR(hi2s);
1663 }
1664 
1665 /**
1666   * @brief  Tx Transfer Half completed callbacks
1667   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1668   *         the configuration information for I2S module
1669   * @retval None
1670   */
HAL_I2S_TxHalfCpltCallback(I2S_HandleTypeDef * hi2s)1671 __weak void HAL_I2S_TxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
1672 {
1673   /* Prevent unused argument(s) compilation warning */
1674   UNUSED(hi2s);
1675 
1676   /* NOTE : This function Should not be modified, when the callback is needed,
1677             the HAL_I2S_TxHalfCpltCallback could be implemented in the user file
1678    */
1679 }
1680 
1681 /**
1682   * @brief  Tx Transfer completed callbacks
1683   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1684   *         the configuration information for I2S module
1685   * @retval None
1686   */
HAL_I2S_TxCpltCallback(I2S_HandleTypeDef * hi2s)1687 __weak void HAL_I2S_TxCpltCallback(I2S_HandleTypeDef *hi2s)
1688 {
1689   /* Prevent unused argument(s) compilation warning */
1690   UNUSED(hi2s);
1691 
1692   /* NOTE : This function Should not be modified, when the callback is needed,
1693             the HAL_I2S_TxCpltCallback could be implemented in the user file
1694    */
1695 }
1696 
1697 /**
1698   * @brief  Rx Transfer half completed callbacks
1699   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1700   *         the configuration information for I2S module
1701   * @retval None
1702   */
HAL_I2S_RxHalfCpltCallback(I2S_HandleTypeDef * hi2s)1703 __weak void HAL_I2S_RxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
1704 {
1705   /* Prevent unused argument(s) compilation warning */
1706   UNUSED(hi2s);
1707 
1708   /* NOTE : This function Should not be modified, when the callback is needed,
1709             the HAL_I2S_RxHalfCpltCallback could be implemented in the user file
1710    */
1711 }
1712 
1713 /**
1714   * @brief  Rx Transfer completed callbacks
1715   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1716   *         the configuration information for I2S module
1717   * @retval None
1718   */
HAL_I2S_RxCpltCallback(I2S_HandleTypeDef * hi2s)1719 __weak void HAL_I2S_RxCpltCallback(I2S_HandleTypeDef *hi2s)
1720 {
1721   /* Prevent unused argument(s) compilation warning */
1722   UNUSED(hi2s);
1723 
1724   /* NOTE : This function Should not be modified, when the callback is needed,
1725             the HAL_I2S_RxCpltCallback could be implemented in the user file
1726    */
1727 }
1728 
1729 /**
1730   * @brief  I2S error callbacks
1731   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1732   *         the configuration information for I2S module
1733   * @retval None
1734   */
HAL_I2S_ErrorCallback(I2S_HandleTypeDef * hi2s)1735 __weak void HAL_I2S_ErrorCallback(I2S_HandleTypeDef *hi2s)
1736 {
1737   /* Prevent unused argument(s) compilation warning */
1738   UNUSED(hi2s);
1739 
1740   /* NOTE : This function Should not be modified, when the callback is needed,
1741             the HAL_I2S_ErrorCallback could be implemented in the user file
1742    */
1743 }
1744 
1745 /**
1746   * @}
1747   */
1748 
1749 /** @defgroup I2S_Exported_Functions_Group3 Peripheral State and Errors functions
1750   *  @brief   Peripheral State functions
1751   *
1752 @verbatim
1753  ===============================================================================
1754                       ##### Peripheral State and Errors functions #####
1755  ===============================================================================
1756     [..]
1757     This subsection permits to get in run-time the status of the peripheral
1758     and the data flow.
1759 
1760 @endverbatim
1761   * @{
1762   */
1763 
1764 /**
1765   * @brief  Return the I2S state
1766   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1767   *         the configuration information for I2S module
1768   * @retval HAL state
1769   */
HAL_I2S_GetState(I2S_HandleTypeDef * hi2s)1770 HAL_I2S_StateTypeDef HAL_I2S_GetState(I2S_HandleTypeDef *hi2s)
1771 {
1772   return hi2s->State;
1773 }
1774 
1775 /**
1776   * @brief  Return the I2S error code
1777   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1778   *         the configuration information for I2S module
1779   * @retval I2S Error Code
1780   */
HAL_I2S_GetError(I2S_HandleTypeDef * hi2s)1781 uint32_t HAL_I2S_GetError(I2S_HandleTypeDef *hi2s)
1782 {
1783   return hi2s->ErrorCode;
1784 }
1785 /**
1786   * @}
1787   */
1788 
1789 /**
1790   * @}
1791   */
1792 
1793 /** @addtogroup I2S_Private_Functions I2S Private Functions
1794   * @{
1795   */
1796 /**
1797   * @brief  DMA I2S transmit process complete callback
1798   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
1799   *                the configuration information for the specified DMA module.
1800   * @retval None
1801   */
I2S_DMATxCplt(DMA_HandleTypeDef * hdma)1802 static void I2S_DMATxCplt(DMA_HandleTypeDef *hdma)
1803 {
1804   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent; /* Derogation MISRAC2012-Rule-11.5 */
1805 
1806   /* if DMA is configured in DMA_NORMAL Mode */
1807   if (hdma->Init.Mode == DMA_NORMAL)
1808   {
1809     /* Disable Tx DMA Request */
1810     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_TXDMAEN);
1811 
1812     hi2s->TxXferCount = 0U;
1813     hi2s->State = HAL_I2S_STATE_READY;
1814   }
1815   /* Call user Tx complete callback */
1816 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1817   hi2s->TxCpltCallback(hi2s);
1818 #else
1819   HAL_I2S_TxCpltCallback(hi2s);
1820 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1821 }
1822 
1823 /**
1824   * @brief  DMA I2S transmit process half complete callback
1825   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
1826   *                the configuration information for the specified DMA module.
1827   * @retval None
1828   */
I2S_DMATxHalfCplt(DMA_HandleTypeDef * hdma)1829 static void I2S_DMATxHalfCplt(DMA_HandleTypeDef *hdma)
1830 {
1831   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent; /* Derogation MISRAC2012-Rule-11.5 */
1832 
1833   /* Call user Tx half complete callback */
1834 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1835   hi2s->TxHalfCpltCallback(hi2s);
1836 #else
1837   HAL_I2S_TxHalfCpltCallback(hi2s);
1838 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1839 }
1840 
1841 /**
1842   * @brief  DMA I2S receive process complete callback
1843   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
1844   *                the configuration information for the specified DMA module.
1845   * @retval None
1846   */
I2S_DMARxCplt(DMA_HandleTypeDef * hdma)1847 static void I2S_DMARxCplt(DMA_HandleTypeDef *hdma)
1848 {
1849   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent; /* Derogation MISRAC2012-Rule-11.5 */
1850 
1851   /* if DMA is configured in DMA_NORMAL Mode */
1852   if (hdma->Init.Mode == DMA_NORMAL)
1853   {
1854     /* Disable Rx DMA Request */
1855     CLEAR_BIT(hi2s->Instance->CR2, SPI_CR2_RXDMAEN);
1856     hi2s->RxXferCount = 0U;
1857     hi2s->State = HAL_I2S_STATE_READY;
1858   }
1859   /* Call user Rx complete callback */
1860 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1861   hi2s->RxCpltCallback(hi2s);
1862 #else
1863   HAL_I2S_RxCpltCallback(hi2s);
1864 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1865 }
1866 
1867 /**
1868   * @brief  DMA I2S receive process half complete callback
1869   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
1870   *                the configuration information for the specified DMA module.
1871   * @retval None
1872   */
I2S_DMARxHalfCplt(DMA_HandleTypeDef * hdma)1873 static void I2S_DMARxHalfCplt(DMA_HandleTypeDef *hdma)
1874 {
1875   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent; /* Derogation MISRAC2012-Rule-11.5 */
1876 
1877   /* Call user Rx half complete callback */
1878 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1879   hi2s->RxHalfCpltCallback(hi2s);
1880 #else
1881   HAL_I2S_RxHalfCpltCallback(hi2s);
1882 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1883 }
1884 
1885 /**
1886   * @brief  DMA I2S communication error callback
1887   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
1888   *                the configuration information for the specified DMA module.
1889   * @retval None
1890   */
I2S_DMAError(DMA_HandleTypeDef * hdma)1891 static void I2S_DMAError(DMA_HandleTypeDef *hdma)
1892 {
1893   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent; /* Derogation MISRAC2012-Rule-11.5 */
1894 
1895   /* Disable Rx and Tx DMA Request */
1896   CLEAR_BIT(hi2s->Instance->CR2, (SPI_CR2_RXDMAEN | SPI_CR2_TXDMAEN));
1897   hi2s->TxXferCount = 0U;
1898   hi2s->RxXferCount = 0U;
1899 
1900   hi2s->State = HAL_I2S_STATE_READY;
1901 
1902   /* Set the error code and execute error callback*/
1903   SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1904   /* Call user error callback */
1905 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1906   hi2s->ErrorCallback(hi2s);
1907 #else
1908   HAL_I2S_ErrorCallback(hi2s);
1909 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1910 }
1911 
1912 /**
1913   * @brief  Transmit an amount of data in non-blocking mode with Interrupt
1914   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1915   *         the configuration information for I2S module
1916   * @retval None
1917   */
I2S_Transmit_IT(I2S_HandleTypeDef * hi2s)1918 static void I2S_Transmit_IT(I2S_HandleTypeDef *hi2s)
1919 {
1920   /* Transmit data */
1921   hi2s->Instance->DR = (*hi2s->pTxBuffPtr);
1922   hi2s->pTxBuffPtr++;
1923   hi2s->TxXferCount--;
1924 
1925   if (hi2s->TxXferCount == 0U)
1926   {
1927     /* Disable TXE and ERR interrupt */
1928     __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));
1929 
1930     hi2s->State = HAL_I2S_STATE_READY;
1931     /* Call user Tx complete callback */
1932 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1933     hi2s->TxCpltCallback(hi2s);
1934 #else
1935     HAL_I2S_TxCpltCallback(hi2s);
1936 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1937   }
1938 }
1939 
1940 /**
1941   * @brief  Receive an amount of data in non-blocking mode with Interrupt
1942   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1943   *         the configuration information for I2S module
1944   * @retval None
1945   */
I2S_Receive_IT(I2S_HandleTypeDef * hi2s)1946 static void I2S_Receive_IT(I2S_HandleTypeDef *hi2s)
1947 {
1948   /* Receive data */
1949   (*hi2s->pRxBuffPtr) = (uint16_t)hi2s->Instance->DR;
1950   hi2s->pRxBuffPtr++;
1951   hi2s->RxXferCount--;
1952 
1953   if (hi2s->RxXferCount == 0U)
1954   {
1955     /* Disable RXNE and ERR interrupt */
1956     __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));
1957 
1958     hi2s->State = HAL_I2S_STATE_READY;
1959     /* Call user Rx complete callback */
1960 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
1961     hi2s->RxCpltCallback(hi2s);
1962 #else
1963     HAL_I2S_RxCpltCallback(hi2s);
1964 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1965   }
1966 }
1967 
1968 /**
1969   * @brief  This function handles I2S interrupt request.
1970   * @param  hi2s: pointer to a I2S_HandleTypeDef structure that contains
1971   *         the configuration information for I2S module
1972   * @retval None
1973   */
I2S_IRQHandler(I2S_HandleTypeDef * hi2s)1974 static void I2S_IRQHandler(I2S_HandleTypeDef *hi2s)
1975 {
1976   __IO uint32_t i2ssr = hi2s->Instance->SR;
1977 
1978   if (hi2s->State == HAL_I2S_STATE_BUSY_RX)
1979   {
1980     /* I2S in mode Receiver ------------------------------------------------*/
1981     if (((i2ssr & I2S_FLAG_RXNE) == I2S_FLAG_RXNE) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_RXNE) != RESET))
1982     {
1983       I2S_Receive_IT(hi2s);
1984     }
1985 
1986     /* I2S Overrun error interrupt occurred -------------------------------------*/
1987     if (((i2ssr & I2S_FLAG_OVR) == I2S_FLAG_OVR) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
1988     {
1989       /* Disable RXNE and ERR interrupt */
1990       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXNE | I2S_IT_ERR));
1991 
1992       /* Clear Overrun flag */
1993       __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1994 
1995       /* Set the I2S State ready */
1996       hi2s->State = HAL_I2S_STATE_READY;
1997 
1998 
1999       /* Set the error code and execute error callback*/
2000       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
2001       /* Call user error callback */
2002 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
2003       hi2s->ErrorCallback(hi2s);
2004 #else
2005       HAL_I2S_ErrorCallback(hi2s);
2006 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2007     }
2008   }
2009 
2010   if (hi2s->State == HAL_I2S_STATE_BUSY_TX)
2011   {
2012     /* I2S in mode Transmitter -----------------------------------------------*/
2013     if (((i2ssr & I2S_FLAG_TXE) == I2S_FLAG_TXE) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_TXE) != RESET))
2014     {
2015       I2S_Transmit_IT(hi2s);
2016     }
2017 
2018     /* I2S Underrun error interrupt occurred --------------------------------*/
2019     if (((i2ssr & I2S_FLAG_UDR) == I2S_FLAG_UDR) && (__HAL_I2S_GET_IT_SOURCE(hi2s, I2S_IT_ERR) != RESET))
2020     {
2021       /* Disable TXE and ERR interrupt */
2022       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXE | I2S_IT_ERR));
2023 
2024       /* Clear Underrun flag */
2025       __HAL_I2S_CLEAR_UDRFLAG(hi2s);
2026 
2027       /* Set the I2S State ready */
2028       hi2s->State = HAL_I2S_STATE_READY;
2029 
2030       /* Set the error code and execute error callback*/
2031       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
2032       /* Call user error callback */
2033 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
2034       hi2s->ErrorCallback(hi2s);
2035 #else
2036       HAL_I2S_ErrorCallback(hi2s);
2037 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2038     }
2039   }
2040 }
2041 
2042 /**
2043   * @brief  This function handles I2S Communication Timeout.
2044   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2045   *         the configuration information for I2S module
2046   * @param  Flag Flag checked
2047   * @param  State Value of the flag expected
2048   * @param  Timeout Duration of the timeout
2049   * @retval HAL status
2050   */
I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef * hi2s,uint32_t Flag,FlagStatus State,uint32_t Timeout)2051 static HAL_StatusTypeDef I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag, FlagStatus State,
2052                                                        uint32_t Timeout)
2053 {
2054   uint32_t tickstart;
2055 
2056   /* Get tick */
2057   tickstart = HAL_GetTick();
2058 
2059   /* Wait until flag is set to status*/
2060   while (((__HAL_I2S_GET_FLAG(hi2s, Flag)) ? SET : RESET) != State)
2061   {
2062     if (Timeout != HAL_MAX_DELAY)
2063     {
2064       if (((HAL_GetTick() - tickstart) >= Timeout) || (Timeout == 0U))
2065       {
2066         /* Set the I2S State ready */
2067         hi2s->State = HAL_I2S_STATE_READY;
2068 
2069         /* Process Unlocked */
2070         __HAL_UNLOCK(hi2s);
2071 
2072         return HAL_TIMEOUT;
2073       }
2074     }
2075   }
2076   return HAL_OK;
2077 }
2078 
2079 /**
2080   * @}
2081   */
2082 
2083 /**
2084   * @}
2085   */
2086 
2087 /**
2088   * @}
2089   */
2090 
2091 #endif /* HAL_I2S_MODULE_ENABLED */
2092 
2093