1 /**
2   ******************************************************************************
3   * @file    stm32h7xx_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) 2017 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 
56         (+@) External clock source is configured after setting correctly
57              the define constant EXTERNAL_CLOCK_VALUE in the stm32h7xx_hal_conf.h file.
58 
59     (#) Three mode of operations are available within this driver :
60 
61    *** Polling mode IO operation ***
62    =================================
63    [..]
64      (+) Send an amount of data in blocking mode using HAL_I2S_Transmit()
65      (+) Receive an amount of data in blocking mode using HAL_I2S_Receive()
66 
67    *** Interrupt mode IO operation ***
68    ===================================
69    [..]
70      (+) Send an amount of data in non blocking mode using HAL_I2S_Transmit_IT()
71      (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
72          add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
73      (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
74          add his own code by customization of function pointer HAL_I2S_TxCpltCallback
75      (+) Receive an amount of data in non blocking mode using HAL_I2S_Receive_IT()
76      (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
77          add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
78      (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
79          add his own code by customization of function pointer HAL_I2S_RxCpltCallback
80      (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
81          add his own code by customization of function pointer HAL_I2S_ErrorCallback
82 
83    *** DMA mode IO operation ***
84    ==============================
85    [..]
86      (+) Send an amount of data in non blocking mode (DMA) using HAL_I2S_Transmit_DMA()
87      (+) At transmission end of half transfer HAL_I2S_TxHalfCpltCallback is executed and user can
88          add his own code by customization of function pointer HAL_I2S_TxHalfCpltCallback
89      (+) At transmission end of transfer HAL_I2S_TxCpltCallback is executed and user can
90          add his own code by customization of function pointer HAL_I2S_TxCpltCallback
91      (+) Receive an amount of data in non blocking mode (DMA) using HAL_I2S_Receive_DMA()
92      (+) At reception end of half transfer HAL_I2S_RxHalfCpltCallback is executed and user can
93          add his own code by customization of function pointer HAL_I2S_RxHalfCpltCallback
94      (+) At reception end of transfer HAL_I2S_RxCpltCallback is executed and user can
95          add his own code by customization of function pointer HAL_I2S_RxCpltCallback
96      (+) In case of transfer Error, HAL_I2S_ErrorCallback() function is executed and user can
97          add his own code by customization of function pointer HAL_I2S_ErrorCallback
98      (+) Pause the DMA Transfer using HAL_I2S_DMAPause()
99      (+) Resume the DMA Transfer using HAL_I2S_DMAResume()
100      (+) Stop the DMA Transfer using HAL_I2S_DMAStop()
101 
102    *** I2S HAL driver macros list ***
103    ===================================
104    [..]
105      Below the list of most used macros in I2S HAL driver.
106 
107       (+) __HAL_I2S_ENABLE: Enable the specified SPI peripheral (in I2S mode)
108       (+) __HAL_I2S_DISABLE: Disable the specified SPI peripheral (in I2S mode)
109       (+) __HAL_I2S_ENABLE_IT : Enable the specified I2S interrupts
110       (+) __HAL_I2S_DISABLE_IT : Disable the specified I2S interrupts
111       (+) __HAL_I2S_GET_FLAG: Check whether the specified I2S flag is set or not
112 
113     [..]
114       (@) You can refer to the I2S HAL driver header file for more useful macros
115 
116    *** I2S HAL driver macros list ***
117    ===================================
118    [..]
119        Callback registration:
120 
121       (#) The compilation flag USE_HAL_I2S_REGISTER_CALLBACKS when set to 1UL
122           allows the user to configure dynamically the driver callbacks.
123           Use Functions HAL_I2S_RegisterCallback() to register an interrupt callback.
124 
125           Function HAL_I2S_RegisterCallback() allows to register following callbacks:
126             (+) TxCpltCallback        : I2S Tx Completed callback
127             (+) RxCpltCallback        : I2S Rx Completed callback
128             (+) TxRxCpltCallback      : I2S TxRx Completed callback
129             (+) TxHalfCpltCallback    : I2S Tx Half Completed callback
130             (+) RxHalfCpltCallback    : I2S Rx Half Completed callback
131             (+) TxRxHalfCpltCallback  : I2S TxRx Half Completed callback
132             (+) ErrorCallback         : I2S Error callback
133             (+) MspInitCallback       : I2S Msp Init callback
134             (+) MspDeInitCallback     : I2S Msp DeInit callback
135           This function takes as parameters the HAL peripheral handle, the Callback ID
136           and a pointer to the user callback function.
137 
138 
139       (#) Use function HAL_I2S_UnRegisterCallback to reset a callback to the default
140           weak function.
141           HAL_I2S_UnRegisterCallback takes as parameters the HAL peripheral handle,
142           and the Callback ID.
143           This function allows to reset following callbacks:
144             (+) TxCpltCallback        : I2S Tx Completed callback
145             (+) RxCpltCallback        : I2S Rx Completed callback
146             (+) TxRxCpltCallback      : I2S TxRx Completed callback
147             (+) TxHalfCpltCallback    : I2S Tx Half Completed callback
148             (+) RxHalfCpltCallback    : I2S Rx Half Completed callback
149             (+) TxRxHalfCpltCallback  : I2S TxRx Half Completed callback
150             (+) ErrorCallback         : I2S Error callback
151             (+) MspInitCallback       : I2S Msp Init callback
152             (+) MspDeInitCallback     : I2S Msp DeInit callback
153 
154        By default, after the HAL_I2S_Init() and when the state is HAL_I2S_STATE_RESET
155        all callbacks are set to the corresponding weak functions:
156        examples HAL_I2S_MasterTxCpltCallback(), HAL_I2S_MasterRxCpltCallback().
157        Exception done for MspInit and MspDeInit functions that are
158        reset to the legacy weak functions in the HAL_I2S_Init()/ HAL_I2S_DeInit() only when
159        these callbacks are null (not registered beforehand).
160        If MspInit or MspDeInit are not null, the HAL_I2S_Init()/ HAL_I2S_DeInit()
161        keep and use the user MspInit/MspDeInit callbacks (registered beforehand) whatever the state.
162 
163        Callbacks can be registered/unregistered in HAL_I2S_STATE_READY state only.
164        Exception done MspInit/MspDeInit functions that can be registered/unregistered
165        in HAL_I2S_STATE_READY or HAL_I2S_STATE_RESET state,
166        thus registered (user) MspInit/DeInit callbacks can be used during the Init/DeInit.
167        Then, the user first registers the MspInit/MspDeInit user callbacks
168        using HAL_I2S_RegisterCallback() before calling HAL_I2S_DeInit()
169        or HAL_I2S_Init() function.
170 
171        When The compilation define USE_HAL_I2S_REGISTER_CALLBACKS is set to 0 or
172        not defined, the callback registering feature is not available
173        and weak (surcharged) callbacks are used.
174 
175 
176   @endverbatim
177   */
178 
179 /* Includes ------------------------------------------------------------------*/
180 #include "stm32h7xx_hal.h"
181 
182 #ifdef HAL_I2S_MODULE_ENABLED
183 
184 /** @addtogroup STM32H7xx_HAL_Driver
185   * @{
186   */
187 
188 /** @defgroup I2S I2S
189   * @brief I2S HAL module driver
190   * @{
191   */
192 
193 /* Private typedef -----------------------------------------------------------*/
194 /* Private define ------------------------------------------------------------*/
195 /** @defgroup I2S_Private_Define I2S Private Define
196   * @{
197   */
198 #define I2S_TIMEOUT 0xFFFFUL
199 /**
200   * @}
201   */
202 
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               I2SEx_DMATxRxCplt(DMA_HandleTypeDef *hdma);
214 static void               I2SEx_DMATxRxHalfCplt(DMA_HandleTypeDef *hdma);
215 static void               I2S_DMAError(DMA_HandleTypeDef *hdma);
216 static void               I2S_Transmit_16Bit_IT(I2S_HandleTypeDef *hi2s);
217 static void               I2S_Transmit_32Bit_IT(I2S_HandleTypeDef *hi2s);
218 static void               I2S_Receive_16Bit_IT(I2S_HandleTypeDef *hi2s);
219 static void               I2S_Receive_32Bit_IT(I2S_HandleTypeDef *hi2s);
220 static HAL_StatusTypeDef  I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag, FlagStatus State,
221                                                         uint32_t Tickstart, uint32_t Timeout);
222 /**
223   * @}
224   */
225 
226 /* Exported functions ---------------------------------------------------------*/
227 
228 /** @defgroup I2S_Exported_Functions I2S Exported Functions
229   * @{
230   */
231 
232 /** @defgroup  I2S_Exported_Functions_Group1 Initialization and de-initialization functions
233   *  @brief    Initialization and Configuration functions
234   *
235 @verbatim
236  ===============================================================================
237               ##### Initialization and de-initialization functions #####
238  ===============================================================================
239     [..]  This subsection provides a set of functions allowing to initialize and
240           de-initialize the I2Sx peripheral in simplex mode:
241 
242       (+) User must Implement HAL_I2S_MspInit() function in which he configures
243           all related peripherals resources (CLOCK, GPIO, DMA, IT and NVIC ).
244 
245       (+) Call the function HAL_I2S_Init() to configure the selected device with
246           the selected configuration:
247         (++) Mode
248         (++) Standard
249         (++) Data Format
250         (++) MCLK Output
251         (++) Audio frequency
252         (++) Polarity
253 
254      (+) Call the function HAL_I2S_DeInit() to restore the default configuration
255           of the selected I2Sx peripheral.
256   @endverbatim
257   * @{
258   */
259 
260 /**
261   * @brief  Initializes the I2S according to the specified parameters
262   *         in the I2S_InitTypeDef and create the associated handle.
263   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
264   *         the configuration information for I2S module
265   * @retval HAL status
266   */
HAL_I2S_Init(I2S_HandleTypeDef * hi2s)267 HAL_StatusTypeDef HAL_I2S_Init(I2S_HandleTypeDef *hi2s)
268 {
269   uint32_t i2sdiv;
270   uint32_t i2sodd;
271   uint32_t packetlength;
272   uint32_t tmp;
273   uint32_t i2sclk;
274   uint32_t ispcm;
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_FIRST_BIT(hi2s->Init.FirstBit));
291   assert_param(IS_I2S_WS_INVERSION(hi2s->Init.WSInversion));
292   assert_param(IS_I2S_DATA_24BIT_ALIGNMENT(hi2s->Init.Data24BitAlignment));
293   assert_param(IS_I2S_MASTER_KEEP_IO_STATE(hi2s->Init.MasterKeepIOState));
294 
295   if (hi2s->State == HAL_I2S_STATE_RESET)
296   {
297     /* Allocate lock resource and initialize it */
298     hi2s->Lock = HAL_UNLOCKED;
299 
300 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
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     hi2s->TxRxCpltCallback     = HAL_I2SEx_TxRxCpltCallback;      /* Legacy weak TxRxCpltCallback     */
305     hi2s->TxHalfCpltCallback   = HAL_I2S_TxHalfCpltCallback;      /* Legacy weak TxHalfCpltCallback   */
306     hi2s->RxHalfCpltCallback   = HAL_I2S_RxHalfCpltCallback;      /* Legacy weak RxHalfCpltCallback   */
307     hi2s->TxRxHalfCpltCallback = HAL_I2SEx_TxRxHalfCpltCallback;  /* Legacy weak TxRxHalfCpltCallback */
308     hi2s->ErrorCallback        = HAL_I2S_ErrorCallback;           /* Legacy weak ErrorCallback        */
309 
310     if (hi2s->MspInitCallback == NULL)
311     {
312       hi2s->MspInitCallback = HAL_I2S_MspInit; /* Legacy weak MspInit  */
313     }
314 
315     /* Init the low level hardware : GPIO, CLOCK, NVIC... */
316     hi2s->MspInitCallback(hi2s);
317 #else
318     /* Init the low level hardware : GPIO, CLOCK, CORTEX...etc */
319     HAL_I2S_MspInit(hi2s);
320 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
321   }
322 
323   hi2s->State = HAL_I2S_STATE_BUSY;
324 
325   /* Disable the selected I2S peripheral */
326   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) == SPI_CR1_SPE)
327   {
328     /* Disable I2S peripheral */
329     __HAL_I2S_DISABLE(hi2s);
330   }
331 
332   /* Clear I2S configuration register */
333   CLEAR_REG(hi2s->Instance->I2SCFGR);
334 
335   if (IS_I2S_MASTER(hi2s->Init.Mode))
336   {
337     /*------------------------- I2SDIV and ODD Calculation ---------------------*/
338     /* If the requested audio frequency is not the default, compute the prescaler */
339     if (hi2s->Init.AudioFreq != I2S_AUDIOFREQ_DEFAULT)
340     {
341       /* Check the frame length (For the Prescaler computing) ********************/
342       if (hi2s->Init.DataFormat != I2S_DATAFORMAT_16B)
343       {
344         /* Channel length is 32 bits */
345         packetlength = 2UL;
346       }
347       else
348       {
349         /* Channel length is 16 bits */
350         packetlength = 1UL;
351       }
352 
353       /* Check if PCM standard is used */
354       if ((hi2s->Init.Standard == I2S_STANDARD_PCM_SHORT) ||
355           (hi2s->Init.Standard == I2S_STANDARD_PCM_LONG))
356       {
357         ispcm = 1UL;
358       }
359       else
360       {
361         ispcm = 0UL;
362       }
363 
364       /* Get the source clock value: based on System Clock value */
365 #if defined (SPI_SPI6I2S_SUPPORT)
366       if (hi2s->Instance == SPI6)
367       {
368         /* SPI6 source clock */
369         i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_SPI6);
370       }
371       else
372       {
373         /* SPI1,SPI2 and SPI3 share the same source clock */
374         i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_SPI123);
375       }
376 #else
377       /* SPI1,SPI2 and SPI3 share the same source clock */
378       i2sclk = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_SPI123);
379 #endif  /* SPI_SPI6I2S_SUPPORT */
380 
381       /* Compute the Real divider depending on the MCLK output state, with a floating point */
382       if (hi2s->Init.MCLKOutput == I2S_MCLKOUTPUT_ENABLE)
383       {
384         /* MCLK output is enabled */
385         tmp = (uint32_t)((((i2sclk / (256UL >> ispcm)) * 10UL) / hi2s->Init.AudioFreq) + 5UL);
386       }
387       else
388       {
389         /* MCLK output is disabled */
390         tmp = (uint32_t)((((i2sclk / ((32UL >> ispcm) * packetlength)) * 10UL) / hi2s->Init.AudioFreq) + 5UL);
391       }
392 
393       /* Remove the flatting point */
394       tmp = tmp / 10UL;
395 
396       /* Check the parity of the divider */
397       i2sodd = (uint32_t)(tmp & (uint32_t)1UL);
398 
399       /* Compute the i2sdiv prescaler */
400       i2sdiv = (uint32_t)((tmp - i2sodd) / 2UL);
401     }
402     else
403     {
404       /* Set the default values */
405       i2sdiv = 2UL;
406       i2sodd = 0UL;
407     }
408 
409     /* Test if the obtain values are forbidden or out of range */
410     if (((i2sodd == 1UL) && (i2sdiv == 1UL)) || (i2sdiv > 0xFFUL))
411     {
412       /* Set the error code */
413       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_PRESCALER);
414       return  HAL_ERROR;
415     }
416 
417     /* Force i2smod to 1 just to be sure that (2xi2sdiv + i2sodd) is always higher than 0 */
418     if (i2sdiv == 0UL)
419     {
420       i2sodd = 1UL;
421     }
422 
423     MODIFY_REG(hi2s->Instance->I2SCFGR, (SPI_I2SCFGR_I2SDIV                 | SPI_I2SCFGR_ODD),
424                ((i2sdiv << SPI_I2SCFGR_I2SDIV_Pos) | (i2sodd << SPI_I2SCFGR_ODD_Pos)));
425   }
426 
427   /*-------------------------- I2Sx I2SCFGR Configuration --------------------*/
428   /* Configure I2SMOD, I2SCFG, I2SSTD, PCMSYNC, DATLEN ,CHLEN ,CKPOL, WSINV, DATAFMT, I2SDIV, ODD and MCKOE bits bits */
429   /* And configure the I2S with the I2S_InitStruct values */
430   MODIFY_REG(hi2s->Instance->I2SCFGR, (SPI_I2SCFGR_I2SMOD   | SPI_I2SCFGR_I2SCFG     | \
431                                        SPI_I2SCFGR_I2SSTD   | SPI_I2SCFGR_PCMSYNC    | \
432                                        SPI_I2SCFGR_DATLEN   | SPI_I2SCFGR_CHLEN      | \
433                                        SPI_I2SCFGR_CKPOL    | SPI_I2SCFGR_WSINV      | \
434                                        SPI_I2SCFGR_DATFMT   | SPI_I2SCFGR_MCKOE),
435              (SPI_I2SCFGR_I2SMOD   | hi2s->Init.Mode        | \
436               hi2s->Init.Standard  | hi2s->Init.DataFormat  | \
437               hi2s->Init.CPOL      | hi2s->Init.WSInversion | \
438               hi2s->Init.Data24BitAlignment | hi2s->Init.MCLKOutput));
439   /*Clear status register*/
440   WRITE_REG(hi2s->Instance->IFCR, 0x0FF8);
441 
442   /*---------------------------- I2Sx CFG2 Configuration ----------------------*/
443 
444   /* Unlock the AF configuration to configure CFG2 register*/
445   CLEAR_BIT(hi2s->Instance->CR1, SPI_CR1_IOLOCK);
446 
447   MODIFY_REG(hi2s->Instance->CFG2, SPI_CFG2_LSBFRST, hi2s->Init.FirstBit);
448 
449   /* Insure that AFCNTR is managed only by Master */
450   if (IS_I2S_MASTER(hi2s->Init.Mode))
451   {
452     /* Alternate function GPIOs control */
453     MODIFY_REG(hi2s->Instance->CFG2, SPI_CFG2_AFCNTR, (hi2s->Init.MasterKeepIOState));
454   }
455 
456   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
457   hi2s->State     = HAL_I2S_STATE_READY;
458 
459   return HAL_OK;
460 }
461 
462 /**
463   * @brief DeInitializes the I2S peripheral
464   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
465   *         the configuration information for I2S module
466   * @retval HAL status
467   */
HAL_I2S_DeInit(I2S_HandleTypeDef * hi2s)468 HAL_StatusTypeDef HAL_I2S_DeInit(I2S_HandleTypeDef *hi2s)
469 {
470   /* Check the I2S handle allocation */
471   if (hi2s == NULL)
472   {
473     return HAL_ERROR;
474   }
475 
476   /* Check the parameters */
477   assert_param(IS_I2S_ALL_INSTANCE(hi2s->Instance));
478 
479   hi2s->State = HAL_I2S_STATE_BUSY;
480 
481   /* Disable the I2S Peripheral Clock */
482   __HAL_I2S_DISABLE(hi2s);
483 
484 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
485   if (hi2s->MspDeInitCallback == NULL)
486   {
487     hi2s->MspDeInitCallback = HAL_I2S_MspDeInit; /* Legacy weak MspDeInit  */
488   }
489 
490   /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
491   hi2s->MspDeInitCallback(hi2s);
492 #else
493   /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
494   HAL_I2S_MspDeInit(hi2s);
495 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
496 
497   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
498   hi2s->State     = HAL_I2S_STATE_RESET;
499 
500   /* Release Lock */
501   __HAL_UNLOCK(hi2s);
502 
503   return HAL_OK;
504 }
505 
506 /**
507   * @brief I2S MSP Init
508   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
509   *         the configuration information for I2S module
510   * @retval None
511   */
HAL_I2S_MspInit(I2S_HandleTypeDef * hi2s)512 __weak void HAL_I2S_MspInit(I2S_HandleTypeDef *hi2s)
513 {
514   /* Prevent unused argument(s) compilation warning */
515   UNUSED(hi2s);
516 
517   /* NOTE : This function Should not be modified, when the callback is needed,
518             the HAL_I2S_MspInit could be implemented in the user file
519    */
520 }
521 
522 /**
523   * @brief I2S MSP DeInit
524   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
525   *         the configuration information for I2S module
526   * @retval None
527   */
HAL_I2S_MspDeInit(I2S_HandleTypeDef * hi2s)528 __weak void HAL_I2S_MspDeInit(I2S_HandleTypeDef *hi2s)
529 {
530   /* Prevent unused argument(s) compilation warning */
531   UNUSED(hi2s);
532 
533   /* NOTE : This function Should not be modified, when the callback is needed,
534             the HAL_I2S_MspDeInit could be implemented in the user file
535    */
536 }
537 
538 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
539 /**
540   * @brief  Register a User I2S Callback
541   *         To be used instead of the weak predefined callback
542   * @param  hi2s Pointer to a I2S_HandleTypeDef structure that contains
543   *                the configuration information for the specified I2S.
544   * @param  CallbackID ID of the callback to be registered
545   * @param  pCallback pointer to the Callback function
546   * @retval HAL status
547   */
HAL_I2S_RegisterCallback(I2S_HandleTypeDef * hi2s,HAL_I2S_CallbackIDTypeDef CallbackID,pI2S_CallbackTypeDef pCallback)548 HAL_StatusTypeDef HAL_I2S_RegisterCallback(I2S_HandleTypeDef *hi2s, HAL_I2S_CallbackIDTypeDef CallbackID,
549                                            pI2S_CallbackTypeDef pCallback)
550 {
551   HAL_StatusTypeDef status = HAL_OK;
552 
553   if (pCallback == NULL)
554   {
555     /* Update the error code */
556     hi2s->ErrorCode |= HAL_I2S_ERROR_INVALID_CALLBACK;
557 
558     return HAL_ERROR;
559   }
560   /* Process locked */
561   __HAL_LOCK(hi2s);
562 
563   if (HAL_I2S_STATE_READY == hi2s->State)
564   {
565     switch (CallbackID)
566     {
567       case HAL_I2S_TX_COMPLETE_CB_ID :
568         hi2s->TxCpltCallback = pCallback;
569         break;
570 
571       case HAL_I2S_RX_COMPLETE_CB_ID :
572         hi2s->RxCpltCallback = pCallback;
573         break;
574 
575       case HAL_I2S_TX_RX_COMPLETE_CB_ID :
576         hi2s->TxRxCpltCallback = pCallback;
577         break;
578 
579       case HAL_I2S_TX_HALF_COMPLETE_CB_ID :
580         hi2s->TxHalfCpltCallback = pCallback;
581         break;
582 
583       case HAL_I2S_RX_HALF_COMPLETE_CB_ID :
584         hi2s->RxHalfCpltCallback = pCallback;
585         break;
586 
587 
588       case HAL_I2S_TX_RX_HALF_COMPLETE_CB_ID :
589         hi2s->TxRxHalfCpltCallback = pCallback;
590         break;
591 
592       case HAL_I2S_ERROR_CB_ID :
593         hi2s->ErrorCallback = pCallback;
594         break;
595 
596       case HAL_I2S_MSPINIT_CB_ID :
597         hi2s->MspInitCallback = pCallback;
598         break;
599 
600       case HAL_I2S_MSPDEINIT_CB_ID :
601         hi2s->MspDeInitCallback = pCallback;
602         break;
603 
604       default :
605         /* Update the error code */
606         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
607 
608         /* Return error status */
609         status =  HAL_ERROR;
610         break;
611     }
612   }
613   else if (HAL_I2S_STATE_RESET == hi2s->State)
614   {
615     switch (CallbackID)
616     {
617       case HAL_I2S_MSPINIT_CB_ID :
618         hi2s->MspInitCallback = pCallback;
619         break;
620 
621       case HAL_I2S_MSPDEINIT_CB_ID :
622         hi2s->MspDeInitCallback = pCallback;
623         break;
624 
625       default :
626         /* Update the error code */
627         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
628 
629         /* Return error status */
630         status =  HAL_ERROR;
631         break;
632     }
633   }
634   else
635   {
636     /* Update the error code */
637     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
638 
639     /* Return error status */
640     status =  HAL_ERROR;
641   }
642 
643   /* Release Lock */
644   __HAL_UNLOCK(hi2s);
645   return status;
646 }
647 
648 /**
649   * @brief  Unregister an I2S Callback
650   *         I2S callback is redirected to the weak predefined callback
651   * @param  hi2s Pointer to a I2S_HandleTypeDef structure that contains
652   *                the configuration information for the specified I2S.
653   * @param  CallbackID ID of the callback to be unregistered
654   * @retval HAL status
655   */
HAL_I2S_UnRegisterCallback(I2S_HandleTypeDef * hi2s,HAL_I2S_CallbackIDTypeDef CallbackID)656 HAL_StatusTypeDef HAL_I2S_UnRegisterCallback(I2S_HandleTypeDef *hi2s, HAL_I2S_CallbackIDTypeDef CallbackID)
657 {
658   HAL_StatusTypeDef status = HAL_OK;
659 
660   /* Process locked */
661   __HAL_LOCK(hi2s);
662 
663   if (HAL_I2S_STATE_READY == hi2s->State)
664   {
665     switch (CallbackID)
666     {
667       case HAL_I2S_TX_COMPLETE_CB_ID :
668         hi2s->TxCpltCallback = HAL_I2S_TxCpltCallback;                /* Legacy weak TxCpltCallback       */
669         break;
670 
671       case HAL_I2S_RX_COMPLETE_CB_ID :
672         hi2s->RxCpltCallback = HAL_I2S_RxCpltCallback;                /* Legacy weak RxCpltCallback       */
673         break;
674 
675       case HAL_I2S_TX_RX_COMPLETE_CB_ID :
676         hi2s->TxRxCpltCallback = HAL_I2SEx_TxRxCpltCallback;          /* Legacy weak TxRxCpltCallback     */
677         break;
678 
679       case HAL_I2S_TX_HALF_COMPLETE_CB_ID :
680         hi2s->TxHalfCpltCallback = HAL_I2S_TxHalfCpltCallback;        /* Legacy weak TxHalfCpltCallback   */
681         break;
682 
683       case HAL_I2S_RX_HALF_COMPLETE_CB_ID :
684         hi2s->RxHalfCpltCallback = HAL_I2S_RxHalfCpltCallback;        /* Legacy weak RxHalfCpltCallback   */
685         break;
686 
687       case HAL_I2S_TX_RX_HALF_COMPLETE_CB_ID :
688         hi2s->TxRxHalfCpltCallback = HAL_I2SEx_TxRxHalfCpltCallback;  /* Legacy weak TxRxHalfCpltCallback */
689         break;
690 
691       case HAL_I2S_ERROR_CB_ID :
692         hi2s->ErrorCallback = HAL_I2S_ErrorCallback;                  /* Legacy weak ErrorCallback        */
693         break;
694 
695       case HAL_I2S_MSPINIT_CB_ID :
696         hi2s->MspInitCallback = HAL_I2S_MspInit;                      /* Legacy weak MspInit              */
697         break;
698 
699       case HAL_I2S_MSPDEINIT_CB_ID :
700         hi2s->MspDeInitCallback = HAL_I2S_MspDeInit;                  /* Legacy weak MspDeInit            */
701         break;
702 
703       default :
704         /* Update the error code */
705         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
706 
707         /* Return error status */
708         status =  HAL_ERROR;
709         break;
710     }
711   }
712   else if (HAL_I2S_STATE_RESET == hi2s->State)
713   {
714     switch (CallbackID)
715     {
716       case HAL_I2S_MSPINIT_CB_ID :
717         hi2s->MspInitCallback = HAL_I2S_MspInit;                      /* Legacy weak MspInit              */
718         break;
719 
720       case HAL_I2S_MSPDEINIT_CB_ID :
721         hi2s->MspDeInitCallback = HAL_I2S_MspDeInit;                  /* Legacy weak MspDeInit            */
722         break;
723 
724       default :
725         /* Update the error code */
726         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
727 
728         /* Return error status */
729         status =  HAL_ERROR;
730         break;
731     }
732   }
733   else
734   {
735     /* Update the error code */
736     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_INVALID_CALLBACK);
737 
738     /* Return error status */
739     status =  HAL_ERROR;
740   }
741 
742   /* Release Lock */
743   __HAL_UNLOCK(hi2s);
744   return status;
745 }
746 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
747 /**
748   * @}
749   */
750 
751 /** @defgroup I2S_Exported_Functions_Group2 IO operation functions
752   *  @brief Data transfers functions
753   *
754 @verbatim
755  ===============================================================================
756                       ##### IO operation functions #####
757  ===============================================================================
758     [..]
759     This subsection provides a set of functions allowing to manage the I2S data
760     transfers.
761 
762     (#) There are two modes of transfer:
763        (++) Blocking mode : The communication is performed in the polling mode.
764             The status of all data processing is returned by the same function
765             after finishing transfer.
766        (++) No-Blocking mode : The communication is performed using Interrupts
767             or DMA. These functions return the status of the transfer startup.
768             The end of the data processing will be indicated through the
769             dedicated I2S IRQ when using Interrupt mode or the DMA IRQ when
770             using DMA mode.
771 
772     (#) Blocking mode functions are :
773         (++) HAL_I2S_Transmit()
774         (++) HAL_I2S_Receive()
775         (++) HAL_I2SEx_TransmitReceive()
776 
777     (#) No-Blocking mode functions with Interrupt are :
778         (++) HAL_I2S_Transmit_IT()
779         (++) HAL_I2S_Receive_IT()
780         (++) HAL_I2SEx_TransmitReceive_IT()
781 
782     (#) No-Blocking mode functions with DMA are :
783         (++) HAL_I2S_Transmit_DMA()
784         (++) HAL_I2S_Receive_DMA()
785         (++) HAL_I2SEx_TransmitReceive_DMA()
786 
787     (#) A set of Transfer Complete Callbacks are provided in non Blocking mode:
788         (++) HAL_I2S_TxCpltCallback()
789         (++) HAL_I2S_RxCpltCallback()
790         (++) HAL_I2SEx_TxRxCpltCallback()
791         (++) HAL_I2S_ErrorCallback()
792 
793 @endverbatim
794   * @{
795   */
796 
797 /**
798   * @brief  Transmit an amount of data in blocking mode
799   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
800   *         the configuration information for I2S module
801   * @param  pData a 16-bit pointer to data buffer.
802   * @param  Size number of data sample to be sent:
803   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
804   *         configuration phase, the Size parameter means the number of 16-bit data length
805   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
806   *         the Size parameter means the number of 16-bit data length.
807   * @param  Timeout Timeout duration
808   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
809   *         between Master and Slave(example: audio streaming).
810   * @retval HAL status
811   */
HAL_I2S_Transmit(I2S_HandleTypeDef * hi2s,const uint16_t * pData,uint16_t Size,uint32_t Timeout)812 HAL_StatusTypeDef HAL_I2S_Transmit(I2S_HandleTypeDef *hi2s, const uint16_t *pData, uint16_t Size, uint32_t Timeout)
813 {
814 #if defined (__GNUC__)
815   __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->TXDR));
816 #endif /* __GNUC__ */
817   uint32_t tickstart;
818 
819   if ((pData == NULL) || (Size == 0UL))
820   {
821     return  HAL_ERROR;
822   }
823 
824   if (hi2s->State != HAL_I2S_STATE_READY)
825   {
826     return HAL_BUSY;
827   }
828 
829   /* Process Locked */
830   __HAL_LOCK(hi2s);
831 
832   /* Init tickstart for timeout management*/
833   tickstart = HAL_GetTick();
834 
835   /* Set state and reset error code */
836   hi2s->State       = HAL_I2S_STATE_BUSY_TX;
837   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
838   hi2s->pTxBuffPtr  = (const uint16_t *)pData;
839   hi2s->TxXferSize  = Size;
840   hi2s->TxXferCount = Size;
841 
842   /* Initialize fields not used in handle to zero */
843   hi2s->pRxBuffPtr  = NULL;
844   hi2s->RxXferSize  = (uint16_t) 0UL;
845   hi2s->RxXferCount = (uint16_t) 0UL;
846 
847   /* Check if the I2S is already enabled */
848   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
849   {
850     /* Enable I2S peripheral */
851     __HAL_I2S_ENABLE(hi2s);
852   }
853 
854   /* Start the transfer */
855   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
856 
857 
858   /* Wait until TXP flag is set */
859   if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXP, SET, tickstart, Timeout) != HAL_OK)
860   {
861     /* Set the error code */
862     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
863     hi2s->State = HAL_I2S_STATE_READY;
864     __HAL_UNLOCK(hi2s);
865     return HAL_TIMEOUT;
866   }
867 
868   while (hi2s->TxXferCount > 0UL)
869   {
870     if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
871     {
872       /* Transmit data in 32 Bit mode */
873       hi2s->Instance->TXDR = *((const uint32_t *)hi2s->pTxBuffPtr);
874       hi2s->pTxBuffPtr += 2;
875       hi2s->TxXferCount--;
876     }
877     else
878     {
879       /* Transmit data in 16 Bit mode */
880 #if defined (__GNUC__)
881       *ptxdr_16bits = *((const uint16_t *)hi2s->pTxBuffPtr);
882 #else
883       *((__IO uint16_t *)&hi2s->Instance->TXDR) = *((const uint16_t *)hi2s->pTxBuffPtr);
884 #endif /* __GNUC__ */
885 
886       hi2s->pTxBuffPtr++;
887       hi2s->TxXferCount--;
888     }
889 
890     /* Wait until TXP flag is set */
891     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_TXP, SET, tickstart, Timeout) != HAL_OK)
892     {
893       /* Set the error code */
894       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
895       hi2s->State = HAL_I2S_STATE_READY;
896       __HAL_UNLOCK(hi2s);
897       return HAL_TIMEOUT;
898     }
899 
900     /* Check if an underrun occurs */
901     if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_UDR) == SET)
902     {
903       /* Clear underrun flag */
904       __HAL_I2S_CLEAR_UDRFLAG(hi2s);
905 
906       /* Set the error code */
907       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
908     }
909   }
910 
911   hi2s->State = HAL_I2S_STATE_READY;
912   __HAL_UNLOCK(hi2s);
913   return HAL_OK;
914 }
915 
916 /**
917   * @brief  Receive an amount of data in blocking mode
918   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
919   *         the configuration information for I2S module
920   * @param  pData a 16-bit pointer to data buffer.
921   * @param  Size number of data sample to be sent:
922   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
923   *         configuration phase, the Size parameter means the number of 16-bit data length
924   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
925   *         the Size parameter means the number of 16-bit data length.
926   * @param  Timeout Timeout duration
927   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
928   *         between Master and Slave(example: audio streaming).
929   * @note   In I2S Master Receiver mode, just after enabling the peripheral the clock will be generate
930   *         in continuous way and as the I2S is not disabled at the end of the I2S transaction.
931   * @retval HAL status
932   */
HAL_I2S_Receive(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size,uint32_t Timeout)933 HAL_StatusTypeDef HAL_I2S_Receive(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size, uint32_t Timeout)
934 {
935 #if defined (__GNUC__)
936   __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->RXDR));
937 #endif /* __GNUC__ */
938   uint32_t tickstart;
939 
940   if ((pData == NULL) || (Size == 0UL))
941   {
942     return  HAL_ERROR;
943   }
944 
945   if (hi2s->State != HAL_I2S_STATE_READY)
946   {
947     return HAL_BUSY;
948   }
949 
950   /* Process Locked */
951   __HAL_LOCK(hi2s);
952 
953   /* Init tickstart for timeout management*/
954   tickstart = HAL_GetTick();
955 
956   /* Set state and reset error code */
957   hi2s->State       = HAL_I2S_STATE_BUSY_RX;
958   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
959   hi2s->pRxBuffPtr  = pData;
960   hi2s->RxXferSize  = Size;
961   hi2s->RxXferCount = Size;
962 
963   /* Initialize fields not used in handle to zero */
964   hi2s->pTxBuffPtr  = NULL;
965   hi2s->TxXferSize  = (uint16_t) 0UL;
966   hi2s->TxXferCount = (uint16_t) 0UL;
967 
968   /* Check if the I2S is already enabled */
969   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
970   {
971     /* Enable I2S peripheral */
972     __HAL_I2S_ENABLE(hi2s);
973   }
974 
975   /* Start the transfer */
976   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
977 
978   /* Receive data */
979   while (hi2s->RxXferCount > 0UL)
980   {
981     /* Wait until RXP flag is set */
982     if (I2S_WaitFlagStateUntilTimeout(hi2s, I2S_FLAG_RXP, SET, tickstart, Timeout) != HAL_OK)
983     {
984       /* Set the error code */
985       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
986       hi2s->State = HAL_I2S_STATE_READY;
987       __HAL_UNLOCK(hi2s);
988       return HAL_TIMEOUT;
989     }
990 
991     if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
992     {
993       /* Receive data in 32 Bit mode */
994       *((uint32_t *)hi2s->pRxBuffPtr) = hi2s->Instance->RXDR;
995       hi2s->pRxBuffPtr += 2;
996       hi2s->RxXferCount--;
997     }
998     else
999     {
1000       /* Receive data in 16 Bit mode */
1001 #if defined (__GNUC__)
1002       *((uint16_t *)hi2s->pRxBuffPtr) = *prxdr_16bits;
1003 #else
1004       *((uint16_t *)hi2s->pRxBuffPtr) = *((__IO uint16_t *)&hi2s->Instance->RXDR);
1005 #endif /* __GNUC__ */
1006       hi2s->pRxBuffPtr++;
1007       hi2s->RxXferCount--;
1008     }
1009 
1010     /* Check if an overrun occurs */
1011     if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_OVR) == SET)
1012     {
1013       /* Clear overrun flag */
1014       __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1015 
1016       /* Set the error code */
1017       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
1018     }
1019   }
1020 
1021   hi2s->State = HAL_I2S_STATE_READY;
1022   __HAL_UNLOCK(hi2s);
1023   return HAL_OK;
1024 }
1025 
1026 /**
1027   * @brief  Full-Duplex Transmit/Receive data in blocking mode.
1028   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1029   *         the configuration information for I2S module
1030   * @param  pTxData a 16-bit pointer to the Transmit data buffer.
1031   * @param  pRxData a 16-bit pointer to the Receive data buffer.
1032   * @param  Size number of data sample to be sent:
1033   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1034   *         configuration phase, the Size parameter means the number of 16-bit data length
1035   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1036   *         the Size parameter means the number of 16-bit data length.
1037   * @param  Timeout Timeout duration
1038   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1039   *         between Master and Slave(example: audio streaming).
1040   * @retval HAL status
1041   */
1042 
HAL_I2SEx_TransmitReceive(I2S_HandleTypeDef * hi2s,const uint16_t * pTxData,uint16_t * pRxData,uint16_t Size,uint32_t Timeout)1043 HAL_StatusTypeDef HAL_I2SEx_TransmitReceive(I2S_HandleTypeDef *hi2s, const uint16_t *pTxData, uint16_t *pRxData,
1044                                             uint16_t Size, uint32_t Timeout)
1045 {
1046   uint32_t tmp_TxXferCount;
1047   uint32_t tmp_RxXferCount;
1048   uint32_t tickstart;
1049 
1050 #if defined (__GNUC__)
1051   __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->TXDR));
1052   __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->RXDR));
1053 #endif /* __GNUC__ */
1054 
1055   if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0U))
1056   {
1057     return  HAL_ERROR;
1058   }
1059 
1060   if (hi2s->State != HAL_I2S_STATE_READY)
1061   {
1062     return HAL_BUSY;
1063   }
1064 
1065   /* Process Locked */
1066   __HAL_LOCK(hi2s);
1067 
1068   /* Init tickstart for timeout management*/
1069   tickstart = HAL_GetTick();
1070 
1071   hi2s->TxXferSize  = Size;
1072   hi2s->TxXferCount = Size;
1073   hi2s->pTxBuffPtr  = (const uint16_t *)pTxData;
1074   hi2s->RxXferSize  = Size;
1075   hi2s->RxXferCount = Size;
1076   hi2s->pRxBuffPtr  = pRxData;
1077 
1078   tmp_TxXferCount = hi2s->TxXferCount;
1079   tmp_RxXferCount = hi2s->RxXferCount;
1080 
1081   /* Set state and reset error code */
1082   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1083   hi2s->State = HAL_I2S_STATE_BUSY_TX_RX;
1084 
1085   /* Check if the I2S is already enabled */
1086   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
1087   {
1088     /* Enable I2S peripheral */
1089     __HAL_I2S_ENABLE(hi2s);
1090   }
1091 
1092   /* Start the transfer */
1093   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1094 
1095   while ((tmp_TxXferCount > 0UL) || (tmp_RxXferCount > 0UL))
1096   {
1097     if ((__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_TXP) == SET) && (tmp_TxXferCount != 0UL))
1098     {
1099       if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
1100       {
1101         /* Transmit data in 32 Bit mode */
1102         hi2s->Instance->TXDR = *((const uint32_t *)hi2s->pTxBuffPtr);
1103         hi2s->pTxBuffPtr += 2;
1104         tmp_TxXferCount--;
1105       }
1106       else
1107       {
1108         /* Transmit data in 16 Bit mode */
1109 #if defined (__GNUC__)
1110         *ptxdr_16bits = *((const uint16_t *)hi2s->pTxBuffPtr);
1111 #else
1112         *((__IO uint16_t *)&hi2s->Instance->TXDR) = *((const uint16_t *)hi2s->pTxBuffPtr);
1113 #endif /* __GNUC__ */
1114 
1115         hi2s->pTxBuffPtr++;
1116         tmp_TxXferCount--;
1117       }
1118 
1119       /* Check if an underrun occurs */
1120       if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_UDR) == SET)
1121       {
1122         /* Clear underrun flag */
1123         __HAL_I2S_CLEAR_UDRFLAG(hi2s);
1124 
1125         /* Set the error code */
1126         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
1127       }
1128     }
1129 
1130     if ((__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_RXP) == SET) && (tmp_RxXferCount != 0UL))
1131     {
1132       if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
1133       {
1134         /* Receive data in 32 Bit mode */
1135         *((uint32_t *)hi2s->pRxBuffPtr) = hi2s->Instance->RXDR;
1136         hi2s->pRxBuffPtr += 2;
1137         tmp_RxXferCount--;
1138       }
1139       else
1140       {
1141         /* Receive data in 16 Bit mode */
1142 #if defined (__GNUC__)
1143         *((uint16_t *)hi2s->pRxBuffPtr) = *prxdr_16bits;
1144 #else
1145         *((uint16_t *)hi2s->pRxBuffPtr) = *((__IO uint16_t *)&hi2s->Instance->RXDR);
1146 #endif /* __GNUC__ */
1147         hi2s->pRxBuffPtr++;
1148         tmp_RxXferCount--;
1149       }
1150 
1151       /* Check if an overrun occurs */
1152       if (__HAL_I2S_GET_FLAG(hi2s, I2S_FLAG_OVR) == SET)
1153       {
1154         /* Clear overrun flag */
1155         __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1156 
1157         /* Set the error code */
1158         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
1159       }
1160     }
1161 
1162     /* Timeout management */
1163     if ((((HAL_GetTick() - tickstart) >=  Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1164     {
1165       /* Set the error code */
1166       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1167       hi2s->State = HAL_I2S_STATE_READY;
1168       __HAL_UNLOCK(hi2s);
1169       return HAL_TIMEOUT;
1170     }
1171   }
1172 
1173   hi2s->State = HAL_I2S_STATE_READY;
1174   __HAL_UNLOCK(hi2s);
1175   return HAL_OK;
1176 }
1177 
1178 /**
1179   * @brief  Transmit an amount of data in non-blocking mode with Interrupt
1180   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1181   *         the configuration information for I2S module
1182   * @param  pData a 16-bit pointer to data buffer.
1183   * @param  Size number of data sample to be sent:
1184   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1185   *         configuration phase, the Size parameter means the number of 16-bit data length
1186   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1187   *         the Size parameter means the number of 16-bit data length.
1188   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1189   *         between Master and Slave(example: audio streaming).
1190   * @retval HAL status
1191   */
HAL_I2S_Transmit_IT(I2S_HandleTypeDef * hi2s,const uint16_t * pData,uint16_t Size)1192 HAL_StatusTypeDef HAL_I2S_Transmit_IT(I2S_HandleTypeDef *hi2s, const uint16_t *pData, uint16_t Size)
1193 {
1194   if ((pData == NULL) || (Size == 0UL))
1195   {
1196     return  HAL_ERROR;
1197   }
1198 
1199   if (hi2s->State != HAL_I2S_STATE_READY)
1200   {
1201     return HAL_BUSY;
1202   }
1203 
1204   /* Process Locked */
1205   __HAL_LOCK(hi2s);
1206 
1207   /* Set state and reset error code */
1208   hi2s->State       = HAL_I2S_STATE_BUSY_TX;
1209   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1210   hi2s->pTxBuffPtr  = (const uint16_t *)pData;
1211   hi2s->TxXferSize  = Size;
1212   hi2s->TxXferCount = Size;
1213 
1214   /* Initialize fields not used in handle to zero */
1215   hi2s->pRxBuffPtr  = NULL;
1216   hi2s->RxXferSize  = (uint16_t) 0UL;
1217   hi2s->RxXferCount = (uint16_t) 0UL;
1218 
1219   /* Set the function for IT treatment */
1220   if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
1221   {
1222     hi2s->TxISR = I2S_Transmit_32Bit_IT;
1223   }
1224   else
1225   {
1226     hi2s->TxISR = I2S_Transmit_16Bit_IT;
1227   }
1228 
1229   /* Check if the I2S is already enabled */
1230   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
1231   {
1232     /* Enable I2S peripheral */
1233     __HAL_I2S_ENABLE(hi2s);
1234   }
1235 
1236   /* Enable TXP and UDR interrupt */
1237   __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_UDR));
1238 
1239   /* Enable TIFRE interrupt if the mode is Slave  */
1240   if (hi2s->Init.Mode == I2S_MODE_SLAVE_TX)
1241   {
1242     __HAL_I2S_ENABLE_IT(hi2s, I2S_IT_FRE);
1243   }
1244 
1245   /* Start the transfer */
1246   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1247 
1248   __HAL_UNLOCK(hi2s);
1249   return HAL_OK;
1250 }
1251 
1252 /**
1253   * @brief  Receive an amount of data in non-blocking mode with Interrupt
1254   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1255   *         the configuration information for I2S module
1256   * @param  pData a 16-bit pointer to the Receive data buffer.
1257   * @param  Size number of data sample to be sent:
1258   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1259   *         configuration phase, the Size parameter means the number of 16-bit data length
1260   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1261   *         the Size parameter means the number of 16-bit data length.
1262   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1263   *         between Master and Slave(example: audio streaming).
1264   * @note   It is recommended to use DMA for the I2S receiver to avoid de-synchronization
1265   * between Master and Slave otherwise the I2S interrupt should be optimized.
1266   * @retval HAL status
1267   */
HAL_I2S_Receive_IT(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1268 HAL_StatusTypeDef HAL_I2S_Receive_IT(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1269 {
1270   if ((pData == NULL) || (Size == 0UL))
1271   {
1272     return  HAL_ERROR;
1273   }
1274 
1275   if (hi2s->State != HAL_I2S_STATE_READY)
1276   {
1277     return HAL_BUSY;
1278   }
1279 
1280   /* Process Locked */
1281   __HAL_LOCK(hi2s);
1282 
1283   /* Set state and reset error code */
1284   hi2s->State       = HAL_I2S_STATE_BUSY_RX;
1285   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1286   hi2s->pRxBuffPtr  = pData;
1287   hi2s->RxXferSize  = Size;
1288   hi2s->RxXferCount = Size;
1289 
1290   /* Initialize fields not used in handle to zero */
1291   hi2s->pTxBuffPtr  = NULL;
1292   hi2s->TxXferSize  = (uint16_t) 0UL;
1293   hi2s->TxXferCount = (uint16_t) 0UL;
1294 
1295   /* Set the function for IT treatment */
1296   if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
1297   {
1298     hi2s->RxISR = I2S_Receive_32Bit_IT;
1299   }
1300   else
1301   {
1302     hi2s->RxISR = I2S_Receive_16Bit_IT;
1303   }
1304 
1305   /* Check if the I2S is already enabled */
1306   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
1307   {
1308     /* Enable I2S peripheral */
1309     __HAL_I2S_ENABLE(hi2s);
1310   }
1311   /* Enable RXP and ERR interrupt */
1312   __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_RXP | I2S_IT_OVR));
1313 
1314   /* Enable TIFRE interrupt if the mode is Slave  */
1315   if (hi2s->Init.Mode == I2S_MODE_SLAVE_RX)
1316   {
1317     __HAL_I2S_ENABLE_IT(hi2s, I2S_IT_FRE);
1318   }
1319 
1320   /* Start the transfer */
1321   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1322 
1323   __HAL_UNLOCK(hi2s);
1324   return HAL_OK;
1325 }
1326 
1327 /**
1328   * @brief  Full-Duplex Transmit/Receive data in non-blocking mode using Interrupt
1329   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1330   *         the configuration information for I2S module
1331   * @param  pTxData a 16-bit pointer to the Transmit data buffer.
1332   * @param  pRxData a 16-bit pointer to the Receive data buffer.
1333   * @param  Size number of data sample to be sent:
1334   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1335   *         configuration phase, the Size parameter means the number of 16-bit data length
1336   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1337   *         the Size parameter means the number of 16-bit data length.
1338   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1339   *         between Master and Slave(example: audio streaming).
1340   * @retval HAL status
1341   */
HAL_I2SEx_TransmitReceive_IT(I2S_HandleTypeDef * hi2s,const uint16_t * pTxData,uint16_t * pRxData,uint16_t Size)1342 HAL_StatusTypeDef HAL_I2SEx_TransmitReceive_IT(I2S_HandleTypeDef *hi2s, const uint16_t *pTxData, uint16_t *pRxData,
1343                                                uint16_t Size)
1344 {
1345   if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0U))
1346   {
1347     return  HAL_ERROR;
1348   }
1349 
1350   if (hi2s->State != HAL_I2S_STATE_READY)
1351   {
1352     return HAL_BUSY;
1353   }
1354 
1355   /* Process Locked */
1356   __HAL_LOCK(hi2s);
1357 
1358   hi2s->pTxBuffPtr  = (const uint16_t *)pTxData;
1359   hi2s->pRxBuffPtr  = pRxData;
1360 
1361   hi2s->TxXferSize  = Size;
1362   hi2s->TxXferCount = Size;
1363   hi2s->RxXferSize  = Size;
1364   hi2s->RxXferCount = Size;
1365 
1366   hi2s->ErrorCode = HAL_I2S_ERROR_NONE;
1367   hi2s->State     = HAL_I2S_STATE_BUSY_TX_RX;
1368 
1369 
1370   /* Set the function for IT treatment */
1371   if ((hi2s->Init.DataFormat == I2S_DATAFORMAT_24B) || (hi2s->Init.DataFormat == I2S_DATAFORMAT_32B))
1372   {
1373     hi2s->TxISR = I2S_Transmit_32Bit_IT;
1374     hi2s->RxISR = I2S_Receive_32Bit_IT;
1375   }
1376   else
1377   {
1378     hi2s->TxISR = I2S_Transmit_16Bit_IT;
1379     hi2s->RxISR = I2S_Receive_16Bit_IT;
1380   }
1381 
1382   /* Check if the I2S is already enabled */
1383   if ((hi2s->Instance->CR1 & SPI_CR1_SPE) != SPI_CR1_SPE)
1384   {
1385     /* Enable I2S peripheral */
1386     __HAL_I2S_ENABLE(hi2s);
1387   }
1388 
1389   /* Enable TXP, RXP, DXP, UDR, OVR interrupts */
1390   __HAL_I2S_ENABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_RXP | I2S_IT_DXP | I2S_IT_UDR | I2S_IT_OVR));
1391 
1392   /* Enable TIFRE interrupt if the mode is Slave  */
1393   if (hi2s->Init.Mode == I2S_MODE_SLAVE_FULLDUPLEX)
1394   {
1395     __HAL_I2S_ENABLE_IT(hi2s, I2S_IT_FRE);
1396   }
1397 
1398   /* Start the transfer */
1399   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1400 
1401   __HAL_UNLOCK(hi2s);
1402   return HAL_OK;
1403 
1404 }
1405 
1406 /**
1407   * @brief  Transmit an amount of data in non-blocking mode with DMA
1408   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1409   *         the configuration information for I2S module
1410   * @param  pData a 16-bit pointer to the Transmit data buffer.
1411   * @param  Size number of data sample to be sent:
1412   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1413   *         configuration phase, the Size parameter means the number of 16-bit data length
1414   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1415   *         the Size parameter means the number of 16-bit data length.
1416   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1417   *         between Master and Slave(example: audio streaming).
1418   * @retval HAL status
1419   */
HAL_I2S_Transmit_DMA(I2S_HandleTypeDef * hi2s,const uint16_t * pData,uint16_t Size)1420 HAL_StatusTypeDef HAL_I2S_Transmit_DMA(I2S_HandleTypeDef *hi2s, const uint16_t *pData, uint16_t Size)
1421 {
1422   HAL_StatusTypeDef errorcode = HAL_OK;
1423 
1424   if ((pData == NULL) || (Size == 0UL))
1425   {
1426     return  HAL_ERROR;
1427   }
1428 
1429   if (hi2s->State != HAL_I2S_STATE_READY)
1430   {
1431     return HAL_BUSY;
1432   }
1433 
1434   /* Process Locked */
1435   __HAL_LOCK(hi2s);
1436 
1437   /* Set state and reset error code */
1438   hi2s->State       = HAL_I2S_STATE_BUSY_TX;
1439   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1440   hi2s->pTxBuffPtr  = (const uint16_t *)pData;
1441   hi2s->TxXferSize  = Size;
1442   hi2s->TxXferCount = Size;
1443 
1444   /* Init field not used in handle to zero */
1445   hi2s->pRxBuffPtr  = NULL;
1446   hi2s->RxXferSize  = (uint16_t)0UL;
1447   hi2s->RxXferCount = (uint16_t)0UL;
1448 
1449   /* Set the I2S Tx DMA Half transfer complete callback */
1450   hi2s->hdmatx->XferHalfCpltCallback = I2S_DMATxHalfCplt;
1451 
1452   /* Set the I2S Tx DMA transfer complete callback */
1453   hi2s->hdmatx->XferCpltCallback = I2S_DMATxCplt;
1454 
1455   /* Set the DMA error callback */
1456   hi2s->hdmatx->XferErrorCallback = I2S_DMAError;
1457 
1458   /* Enable the Tx DMA Stream/Channel */
1459   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmatx, (uint32_t)hi2s->pTxBuffPtr, (uint32_t)&hi2s->Instance->TXDR,
1460                                  hi2s->TxXferCount))
1461   {
1462     /* Update I2S error code */
1463     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1464     hi2s->State = HAL_I2S_STATE_READY;
1465 
1466     __HAL_UNLOCK(hi2s);
1467     errorcode = HAL_ERROR;
1468     return errorcode;
1469   }
1470 
1471   /* Check if the I2S Tx request is already enabled */
1472   if (HAL_IS_BIT_CLR(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN))
1473   {
1474     /* Enable Tx DMA Request */
1475     SET_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN);
1476   }
1477 
1478   /* Check if the I2S is already enabled */
1479   if (HAL_IS_BIT_CLR(hi2s->Instance->CR1, SPI_CR1_SPE))
1480   {
1481     /* Enable I2S peripheral */
1482     __HAL_I2S_ENABLE(hi2s);
1483   }
1484 
1485   /* Start the transfer */
1486   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1487 
1488   __HAL_UNLOCK(hi2s);
1489   return errorcode;
1490 }
1491 
1492 /**
1493   * @brief  Receive an amount of data in non-blocking mode with DMA
1494   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1495   *         the configuration information for I2S module
1496   * @param  pData a 16-bit pointer to the Receive data buffer.
1497   * @param  Size number of data sample to be sent:
1498   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1499   *         configuration phase, the Size parameter means the number of 16-bit data length
1500   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1501   *         the Size parameter means the number of 16-bit data length.
1502   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1503   *         between Master and Slave(example: audio streaming).
1504   * @retval HAL status
1505   */
HAL_I2S_Receive_DMA(I2S_HandleTypeDef * hi2s,uint16_t * pData,uint16_t Size)1506 HAL_StatusTypeDef HAL_I2S_Receive_DMA(I2S_HandleTypeDef *hi2s, uint16_t *pData, uint16_t Size)
1507 {
1508   HAL_StatusTypeDef errorcode = HAL_OK;
1509 
1510   if ((pData == NULL) || (Size == 0UL))
1511   {
1512     return HAL_ERROR;
1513   }
1514 
1515   if (hi2s->State != HAL_I2S_STATE_READY)
1516   {
1517     return HAL_BUSY;
1518   }
1519 
1520   /* Process Locked */
1521   __HAL_LOCK(hi2s);
1522 
1523   /* Set state and reset error code */
1524   hi2s->State       = HAL_I2S_STATE_BUSY_RX;
1525   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1526   hi2s->pRxBuffPtr  = pData;
1527   hi2s->RxXferSize  = Size;
1528   hi2s->RxXferCount = Size;
1529 
1530   /* Init field not used in handle to zero */
1531   hi2s->pTxBuffPtr  = NULL;
1532   hi2s->TxXferSize  = (uint16_t)0UL;
1533   hi2s->TxXferCount = (uint16_t)0UL;
1534 
1535 
1536   /* Set the I2S Rx DMA Half transfer complete callback */
1537   hi2s->hdmarx->XferHalfCpltCallback = I2S_DMARxHalfCplt;
1538 
1539   /* Set the I2S Rx DMA transfer complete callback */
1540   hi2s->hdmarx->XferCpltCallback = I2S_DMARxCplt;
1541 
1542   /* Set the DMA error callback */
1543   hi2s->hdmarx->XferErrorCallback = I2S_DMAError;
1544 
1545   /* Enable the Rx DMA Stream/Channel */
1546   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmarx, (uint32_t)&hi2s->Instance->RXDR, (uint32_t)hi2s->pRxBuffPtr,
1547                                  hi2s->RxXferCount))
1548   {
1549     /* Update I2S error code */
1550     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1551     hi2s->State = HAL_I2S_STATE_READY;
1552     errorcode = HAL_ERROR;
1553     __HAL_UNLOCK(hi2s);
1554     return errorcode;
1555   }
1556 
1557   /* Check if the I2S Rx request is already enabled */
1558   if (HAL_IS_BIT_CLR(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN))
1559   {
1560     /* Enable Rx DMA Request */
1561     SET_BIT(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN);
1562   }
1563 
1564   /* Check if the I2S is already enabled */
1565   if (HAL_IS_BIT_CLR(hi2s->Instance->CR1, SPI_CR1_SPE))
1566   {
1567     /* Enable I2S peripheral */
1568     __HAL_I2S_ENABLE(hi2s);
1569   }
1570 
1571   /* Start the transfer */
1572   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1573 
1574   __HAL_UNLOCK(hi2s);
1575   return errorcode;
1576 }
1577 
1578 /**
1579   * @brief  Full-Duplex Transmit/Receive data in non-blocking mode using DMA
1580   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1581   *         the configuration information for I2S module
1582   * @param  pTxData a 16-bit pointer to the Transmit data buffer.
1583   * @param  pRxData a 16-bit pointer to the Receive data buffer.
1584   * @param  Size number of data sample to be sent:
1585   * @note   When a 16-bit data frame or a 16-bit data frame extended is selected during the I2S
1586   *         configuration phase, the Size parameter means the number of 16-bit data length
1587   *         in the transaction and when a 24-bit data frame or a 32-bit data frame is selected
1588   *         the Size parameter means the number of 16-bit data length.
1589   * @note   The I2S is kept enabled at the end of transaction to avoid the clock de-synchronization
1590   *         between Master and Slave(example: audio streaming).
1591   * @retval HAL status
1592   */
HAL_I2SEx_TransmitReceive_DMA(I2S_HandleTypeDef * hi2s,const uint16_t * pTxData,uint16_t * pRxData,uint16_t Size)1593 HAL_StatusTypeDef HAL_I2SEx_TransmitReceive_DMA(I2S_HandleTypeDef *hi2s, const uint16_t *pTxData, uint16_t *pRxData,
1594                                                 uint16_t Size)
1595 {
1596   HAL_StatusTypeDef errorcode = HAL_OK;
1597 
1598 
1599   if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0U))
1600   {
1601     return  HAL_ERROR;
1602   }
1603 
1604   if (hi2s->State != HAL_I2S_STATE_READY)
1605   {
1606     return HAL_BUSY;
1607   }
1608 
1609   /* Process Locked */
1610   __HAL_LOCK(hi2s);
1611 
1612   hi2s->pTxBuffPtr = (const uint16_t *)pTxData;
1613   hi2s->pRxBuffPtr = pRxData;
1614 
1615   hi2s->TxXferSize  = Size;
1616   hi2s->TxXferCount = Size;
1617   hi2s->RxXferSize  = Size;
1618   hi2s->RxXferCount = Size;
1619 
1620   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1621   hi2s->State       = HAL_I2S_STATE_BUSY_TX_RX;
1622 
1623   /* Reset the Tx/Rx DMA bits */
1624   CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
1625 
1626   /* Set the I2S Rx DMA Half transfer complete callback */
1627   hi2s->hdmarx->XferHalfCpltCallback = I2SEx_DMATxRxHalfCplt;
1628 
1629   /* Set the I2S Rx DMA transfer complete callback */
1630   hi2s->hdmarx->XferCpltCallback  = I2SEx_DMATxRxCplt;
1631 
1632   /* Set the I2S Rx DMA error callback */
1633   hi2s->hdmarx->XferErrorCallback = I2S_DMAError;
1634   /* Enable the Tx DMA Stream/Channel */
1635   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmatx, (uint32_t)hi2s->pTxBuffPtr, (uint32_t)&hi2s->Instance->TXDR,
1636                                  hi2s->TxXferCount))
1637   {
1638     /* Update I2S error code */
1639     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1640     hi2s->State = HAL_I2S_STATE_READY;
1641 
1642     __HAL_UNLOCK(hi2s);
1643     errorcode = HAL_ERROR;
1644     return errorcode;
1645   }
1646 
1647   /* Check if the I2S Tx request is already enabled */
1648   if (HAL_IS_BIT_CLR(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN))
1649   {
1650     /* Enable Tx DMA Request */
1651     SET_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN);
1652   }
1653 
1654   /* Enable the Rx DMA Stream/Channel */
1655   if (HAL_OK != HAL_DMA_Start_IT(hi2s->hdmarx, (uint32_t)&hi2s->Instance->RXDR, (uint32_t)hi2s->pRxBuffPtr,
1656                                  hi2s->RxXferCount))
1657   {
1658     /* Update I2S error code */
1659     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1660     hi2s->State = HAL_I2S_STATE_READY;
1661     errorcode = HAL_ERROR;
1662     __HAL_UNLOCK(hi2s);
1663     return errorcode;
1664   }
1665 
1666   /* Check if the I2S Rx request is already enabled */
1667   if (HAL_IS_BIT_CLR(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN))
1668   {
1669     /* Enable Rx DMA Request */
1670     SET_BIT(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN);
1671   }
1672 
1673   /* Check if the I2S is already enabled */
1674   if (HAL_IS_BIT_CLR(hi2s->Instance->CR1, SPI_CR1_SPE))
1675   {
1676     /* Enable I2S peripheral */
1677     __HAL_I2S_ENABLE(hi2s);
1678   }
1679 
1680   /* Start the transfer */
1681   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1682 
1683   __HAL_UNLOCK(hi2s);
1684   return errorcode;
1685 }
1686 
1687 /**
1688   * @brief  Pauses the audio DMA Stream/Channel playing from the Media.
1689   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1690   *         the configuration information for I2S module
1691   * @retval HAL status
1692   */
HAL_I2S_DMAPause(I2S_HandleTypeDef * hi2s)1693 HAL_StatusTypeDef HAL_I2S_DMAPause(I2S_HandleTypeDef *hi2s)
1694 {
1695   /* Process Locked */
1696   __HAL_LOCK(hi2s);
1697 
1698   uint32_t tickstart;
1699 
1700   /* Get tick */
1701   tickstart = HAL_GetTick();
1702 
1703 
1704   /* Check if the I2S peripheral is in master mode */
1705   if (IS_I2S_MASTER(hi2s->Init.Mode))
1706   {
1707     /* Check if there is a transfer on-going */
1708     if (HAL_IS_BIT_SET(hi2s->Instance->CR1, SPI_CR1_CSTART) == 0UL)
1709     {
1710       /* Set error code to no on going transfer */
1711       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_NO_OGT);
1712       hi2s->State = HAL_I2S_STATE_READY;
1713 
1714       __HAL_UNLOCK(hi2s);
1715       return HAL_ERROR;
1716     }
1717 
1718     SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSUSP);
1719 
1720     while (HAL_IS_BIT_SET(hi2s->Instance->CR1, SPI_CR1_CSTART) != 0UL)
1721     {
1722       if ((((HAL_GetTick() - tickstart) >=  I2S_TIMEOUT) && (I2S_TIMEOUT != HAL_MAX_DELAY)) || (I2S_TIMEOUT == 0U))
1723       {
1724         /* Set the I2S State ready */
1725         hi2s->State = HAL_I2S_STATE_READY;
1726 
1727         /* Process Unlocked */
1728         __HAL_UNLOCK(hi2s);
1729 
1730         SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_TIMEOUT);
1731         hi2s->State = HAL_I2S_STATE_READY;
1732         return HAL_TIMEOUT;
1733       }
1734     }
1735 
1736     /* Disable I2S peripheral */
1737     __HAL_I2S_DISABLE(hi2s);
1738 
1739     hi2s->State = HAL_I2S_STATE_READY;
1740 
1741     /* Process Unlocked */
1742     __HAL_UNLOCK(hi2s);
1743 
1744     return HAL_OK;
1745   }
1746   else
1747   {
1748     /* Set error code to not supported */
1749     SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_NOT_SUPPORTED);
1750     hi2s->State = HAL_I2S_STATE_READY;
1751 
1752     /* Process Unlocked */
1753     __HAL_UNLOCK(hi2s);
1754 
1755     return HAL_ERROR;
1756   }
1757 }
1758 
1759 /**
1760   * @brief  Resumes the audio DMA Stream/Channel playing from the Media.
1761   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1762   *         the configuration information for I2S module
1763   * @retval HAL status
1764   */
HAL_I2S_DMAResume(I2S_HandleTypeDef * hi2s)1765 HAL_StatusTypeDef HAL_I2S_DMAResume(I2S_HandleTypeDef *hi2s)
1766 {
1767   /* Process Locked */
1768   __HAL_LOCK(hi2s);
1769 
1770   if (hi2s->State != HAL_I2S_STATE_READY)
1771   {
1772     hi2s->State = HAL_I2S_STATE_READY;
1773 
1774     __HAL_UNLOCK(hi2s);
1775     return HAL_ERROR;
1776   }
1777 
1778   /* Set state and reset error code */
1779   hi2s->State       = HAL_I2S_STATE_BUSY;
1780   hi2s->ErrorCode   = HAL_I2S_ERROR_NONE;
1781 
1782   /* Enable I2S peripheral */
1783   __HAL_I2S_ENABLE(hi2s);
1784 
1785   /* Start the transfer */
1786   SET_BIT(hi2s->Instance->CR1, SPI_CR1_CSTART);
1787 
1788   /* Process Unlocked */
1789   __HAL_UNLOCK(hi2s);
1790 
1791   return HAL_OK;
1792 }
1793 
1794 /**
1795   * @brief  Stops the audio DMA Stream/Channel playing from the Media.
1796   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1797   *         the configuration information for I2S module
1798   * @retval HAL status
1799   */
HAL_I2S_DMAStop(I2S_HandleTypeDef * hi2s)1800 HAL_StatusTypeDef HAL_I2S_DMAStop(I2S_HandleTypeDef *hi2s)
1801 {
1802   HAL_StatusTypeDef errorcode = HAL_OK;
1803   /* The Lock is not implemented on this API to allow the user application
1804      to call the HAL I2S API under callbacks HAL_I2S_TxCpltCallback() or HAL_I2S_RxCpltCallback()
1805      when calling HAL_DMA_Abort() API the DMA TX or RX Transfer complete interrupt is generated
1806      and the correspond call back is executed HAL_I2S_TxCpltCallback() or HAL_I2S_RxCpltCallback()
1807      */
1808 
1809   /* Disable the I2S Tx/Rx DMA requests */
1810   CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN);
1811   CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN);
1812 
1813   /* Abort the I2S DMA tx Stream/Channel */
1814   if (hi2s->hdmatx != NULL)
1815   {
1816     /* Disable the I2S DMA tx Stream/Channel */
1817     if (HAL_OK != HAL_DMA_Abort(hi2s->hdmatx))
1818     {
1819       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1820       errorcode = HAL_ERROR;
1821     }
1822   }
1823 
1824   /* Abort the I2S DMA rx Stream/Channel */
1825   if (hi2s->hdmarx != NULL)
1826   {
1827     /* Disable the I2S DMA rx Stream/Channel */
1828     if (HAL_OK != HAL_DMA_Abort(hi2s->hdmarx))
1829     {
1830       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
1831       errorcode = HAL_ERROR;
1832     }
1833   }
1834 
1835   /* Disable I2S peripheral */
1836   __HAL_I2S_DISABLE(hi2s);
1837 
1838   hi2s->State = HAL_I2S_STATE_READY;
1839 
1840   return errorcode;
1841 }
1842 
1843 /**
1844   * @brief  This function handles I2S interrupt request.
1845   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1846   *         the configuration information for I2S module
1847   * @retval None
1848   */
HAL_I2S_IRQHandler(I2S_HandleTypeDef * hi2s)1849 void HAL_I2S_IRQHandler(I2S_HandleTypeDef *hi2s)
1850 {
1851   uint32_t i2sier   = hi2s->Instance->IER;
1852   uint32_t i2ssr    = hi2s->Instance->SR;
1853   uint32_t trigger  = i2sier & i2ssr;
1854 
1855   if (hi2s->State == HAL_I2S_STATE_BUSY_RX)
1856   {
1857     /* I2S in mode Receiver ------------------------------------------------*/
1858     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_RXP) && HAL_IS_BIT_CLR(trigger, I2S_FLAG_OVR))
1859     {
1860       hi2s->RxISR(hi2s);
1861     }
1862 
1863     /* I2S Overrun error interrupt occurred -------------------------------------*/
1864     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_OVR))
1865     {
1866       /* Disable RXP and ERR interrupt */
1867       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXP | I2S_IT_ERR));
1868 
1869       /* Clear Overrun flag */
1870       __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1871 
1872       /* Set the I2S State ready */
1873       hi2s->State = HAL_I2S_STATE_READY;
1874 
1875 
1876       /* Set the error code and execute error callback*/
1877       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
1878       /* Call user error callback */
1879 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
1880       hi2s->ErrorCallback(hi2s);
1881 #else
1882       HAL_I2S_ErrorCallback(hi2s);
1883 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1884     }
1885   }
1886 
1887   if (hi2s->State == HAL_I2S_STATE_BUSY_TX)
1888   {
1889     /* I2S in mode Transmitter -----------------------------------------------*/
1890     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_TXP) && HAL_IS_BIT_CLR(trigger, I2S_FLAG_UDR))
1891     {
1892       hi2s->TxISR(hi2s);
1893     }
1894 
1895     /* I2S Underrun error interrupt occurred --------------------------------*/
1896     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_UDR))
1897     {
1898       /* Disable TXP and ERR interrupt */
1899       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_ERR));
1900 
1901       /* Clear Underrun flag */
1902       __HAL_I2S_CLEAR_UDRFLAG(hi2s);
1903 
1904       /* Set the I2S State ready */
1905       hi2s->State = HAL_I2S_STATE_READY;
1906 
1907       /* Set the error code and execute error callback*/
1908       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
1909       /* Call user error callback */
1910 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
1911       hi2s->ErrorCallback(hi2s);
1912 #else
1913       HAL_I2S_ErrorCallback(hi2s);
1914 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1915     }
1916   }
1917   if (hi2s->State == HAL_I2S_STATE_BUSY_TX_RX)
1918   {
1919     /* I2S in mode Transmitter -----------------------------------------------*/
1920     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_DXP))
1921     {
1922       hi2s->TxISR(hi2s);
1923       hi2s->RxISR(hi2s);
1924     }
1925     /* I2S in mode Receiver ------------------------------------------------*/
1926     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_RXP) && HAL_IS_BIT_CLR(trigger, I2S_FLAG_DXP))
1927     {
1928       hi2s->RxISR(hi2s);
1929     }
1930     /* I2S in mode Transmitter -----------------------------------------------*/
1931     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_TXP) && HAL_IS_BIT_CLR(trigger, I2S_FLAG_DXP))
1932     {
1933       hi2s->TxISR(hi2s);
1934     }
1935 
1936     /* I2S Underrun error interrupt occurred --------------------------------*/
1937     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_UDR))
1938     {
1939       /* Disable TXP, RXP and ERR interrupt */
1940       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_RXP | I2S_IT_ERR));
1941 
1942       /* Clear Underrun flag */
1943       __HAL_I2S_CLEAR_UDRFLAG(hi2s);
1944 
1945       /* Set the I2S State ready */
1946       hi2s->State = HAL_I2S_STATE_READY;
1947 
1948       /* Set the error code and execute error callback*/
1949       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_UDR);
1950       /* Call user error callback */
1951 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
1952       hi2s->ErrorCallback(hi2s);
1953 #else
1954       HAL_I2S_ErrorCallback(hi2s);
1955 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1956     }
1957 
1958     /* I2S Overrun error interrupt occurred -------------------------------------*/
1959     if (HAL_IS_BIT_SET(trigger, I2S_FLAG_OVR))
1960     {
1961       /* Disable TXP, RXP and ERR interrupt */
1962       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_RXP | I2S_IT_ERR));
1963 
1964       /* Clear Overrun flag */
1965       __HAL_I2S_CLEAR_OVRFLAG(hi2s);
1966 
1967       /* Set the I2S State ready */
1968       hi2s->State = HAL_I2S_STATE_READY;
1969 
1970 
1971       /* Set the error code and execute error callback*/
1972       SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_OVR);
1973 
1974       /* Call user error callback */
1975 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
1976       hi2s->ErrorCallback(hi2s);
1977 #else
1978       HAL_I2S_ErrorCallback(hi2s);
1979 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
1980     }
1981   }
1982 }
1983 
1984 /**
1985   * @brief  Tx Transfer Half completed callbacks
1986   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
1987   *         the configuration information for I2S module
1988   * @retval None
1989   */
HAL_I2S_TxHalfCpltCallback(I2S_HandleTypeDef * hi2s)1990 __weak void HAL_I2S_TxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
1991 {
1992   /* Prevent unused argument(s) compilation warning */
1993   UNUSED(hi2s);
1994 
1995   /* NOTE : This function Should not be modified, when the callback is needed,
1996             the HAL_I2S_TxHalfCpltCallback could be implemented in the user file
1997    */
1998 }
1999 
2000 /**
2001   * @brief  Tx Transfer completed callbacks
2002   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2003   *         the configuration information for I2S module
2004   * @retval None
2005   */
HAL_I2S_TxCpltCallback(I2S_HandleTypeDef * hi2s)2006 __weak void HAL_I2S_TxCpltCallback(I2S_HandleTypeDef *hi2s)
2007 {
2008   /* Prevent unused argument(s) compilation warning */
2009   UNUSED(hi2s);
2010 
2011   /* NOTE : This function Should not be modified, when the callback is needed,
2012             the HAL_I2S_TxCpltCallback could be implemented in the user file
2013    */
2014 }
2015 
2016 /**
2017   * @brief  Rx Transfer half completed callbacks
2018   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2019   *         the configuration information for I2S module
2020   * @retval None
2021   */
HAL_I2S_RxHalfCpltCallback(I2S_HandleTypeDef * hi2s)2022 __weak void HAL_I2S_RxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
2023 {
2024   /* Prevent unused argument(s) compilation warning */
2025   UNUSED(hi2s);
2026 
2027   /* NOTE : This function Should not be modified, when the callback is needed,
2028             the HAL_I2S_RxHalfCpltCallback could be implemented in the user file
2029    */
2030 }
2031 
2032 /**
2033   * @brief  Rx Transfer completed callbacks
2034   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2035   *         the configuration information for I2S module
2036   * @retval None
2037   */
HAL_I2S_RxCpltCallback(I2S_HandleTypeDef * hi2s)2038 __weak void HAL_I2S_RxCpltCallback(I2S_HandleTypeDef *hi2s)
2039 {
2040   /* Prevent unused argument(s) compilation warning */
2041   UNUSED(hi2s);
2042 
2043   /* NOTE : This function Should not be modified, when the callback is needed,
2044             the HAL_I2S_RxCpltCallback could be implemented in the user file
2045    */
2046 }
2047 
2048 /**
2049   * @brief  Rx Transfer half completed callbacks
2050   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2051   *         the configuration information for I2S module
2052   * @retval None
2053   */
HAL_I2SEx_TxRxHalfCpltCallback(I2S_HandleTypeDef * hi2s)2054 __weak void HAL_I2SEx_TxRxHalfCpltCallback(I2S_HandleTypeDef *hi2s)
2055 {
2056   /* Prevent unused argument(s) compilation warning */
2057   UNUSED(hi2s);
2058 
2059   /* NOTE : This function Should not be modified, when the callback is needed,
2060             the HAL_I2S_RxHalfCpltCallback could be implemented in the user file
2061    */
2062 }
2063 
2064 /**
2065   * @brief  Rx Transfer completed callbacks
2066   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2067   *         the configuration information for I2S module
2068   * @retval None
2069   */
HAL_I2SEx_TxRxCpltCallback(I2S_HandleTypeDef * hi2s)2070 __weak void HAL_I2SEx_TxRxCpltCallback(I2S_HandleTypeDef *hi2s)
2071 {
2072   /* Prevent unused argument(s) compilation warning */
2073   UNUSED(hi2s);
2074 
2075   /* NOTE : This function Should not be modified, when the callback is needed,
2076             the HAL_I2S_RxCpltCallback could be implemented in the user file
2077    */
2078 }
2079 
2080 /**
2081   * @brief  I2S error callbacks
2082   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2083   *         the configuration information for I2S module
2084   * @retval None
2085   */
HAL_I2S_ErrorCallback(I2S_HandleTypeDef * hi2s)2086 __weak void HAL_I2S_ErrorCallback(I2S_HandleTypeDef *hi2s)
2087 {
2088   /* Prevent unused argument(s) compilation warning */
2089   UNUSED(hi2s);
2090 
2091   /* NOTE : This function Should not be modified, when the callback is needed,
2092             the HAL_I2S_ErrorCallback could be implemented in the user file
2093    */
2094 }
2095 
2096 /**
2097   * @}
2098   */
2099 
2100 /** @defgroup I2S_Exported_Functions_Group3 Peripheral State and Errors functions
2101   *  @brief   Peripheral State functions
2102   *
2103 @verbatim
2104  ===============================================================================
2105                       ##### Peripheral State and Errors functions #####
2106  ===============================================================================
2107     [..]
2108     This subsection permits to get in run-time the status of the peripheral
2109     and the data flow.
2110 
2111 @endverbatim
2112   * @{
2113   */
2114 
2115 /**
2116   * @brief  Return the I2S state
2117   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2118   *         the configuration information for I2S module
2119   * @retval HAL state
2120   */
HAL_I2S_GetState(const I2S_HandleTypeDef * hi2s)2121 HAL_I2S_StateTypeDef HAL_I2S_GetState(const I2S_HandleTypeDef *hi2s)
2122 {
2123   return hi2s->State;
2124 }
2125 
2126 /**
2127   * @brief  Return the I2S error code
2128   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2129   *         the configuration information for I2S module
2130   * @retval I2S Error Code
2131   */
HAL_I2S_GetError(const I2S_HandleTypeDef * hi2s)2132 uint32_t HAL_I2S_GetError(const I2S_HandleTypeDef *hi2s)
2133 {
2134   return hi2s->ErrorCode;
2135 }
2136 /**
2137   * @}
2138   */
2139 
2140 /**
2141   * @}
2142   */
2143 
2144 /** @addtogroup I2S_Private_Functions
2145   * @{
2146   */
2147 /**
2148   * @brief  DMA I2S transmit process complete callback
2149   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2150   *                the configuration information for the specified DMA module.
2151   * @retval None
2152   */
I2S_DMATxCplt(DMA_HandleTypeDef * hdma)2153 static void I2S_DMATxCplt(DMA_HandleTypeDef *hdma)
2154 {
2155   /* Derogation MISRAC2012-Rule-11.5 */
2156   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2157 
2158   /* if DMA is configured in DMA_NORMAL Mode */
2159   if (hdma->Init.Mode == DMA_NORMAL)
2160   {
2161     /* Disable Tx DMA Request */
2162     CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN);
2163 
2164     hi2s->TxXferCount = (uint16_t) 0UL;
2165     hi2s->State = HAL_I2S_STATE_READY;
2166   }
2167   /* Call user Tx complete callback */
2168 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2169   hi2s->TxCpltCallback(hi2s);
2170 #else
2171   HAL_I2S_TxCpltCallback(hi2s);
2172 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2173 }
2174 
2175 /**
2176   * @brief  DMA I2S transmit process half complete callback
2177   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2178   *         the configuration information for the specified DMA module.
2179   * @retval None
2180   */
I2S_DMATxHalfCplt(DMA_HandleTypeDef * hdma)2181 static void I2S_DMATxHalfCplt(DMA_HandleTypeDef *hdma)
2182 {
2183   /* Derogation MISRAC2012-Rule-11.5 */
2184   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2185 
2186   /* Call user Tx half complete callback */
2187 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2188   hi2s->TxHalfCpltCallback(hi2s);
2189 #else
2190   HAL_I2S_TxHalfCpltCallback(hi2s);
2191 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2192 }
2193 
2194 /**
2195   * @brief  DMA I2S receive process complete callback
2196   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2197   *         the configuration information for the specified DMA module.
2198   * @retval None
2199   */
I2S_DMARxCplt(DMA_HandleTypeDef * hdma)2200 static void I2S_DMARxCplt(DMA_HandleTypeDef *hdma)
2201 {
2202   /* Derogation MISRAC2012-Rule-11.5 */
2203   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2204 
2205   /* if DMA is configured in DMA_NORMAL Mode */
2206   if (hdma->Init.Mode == DMA_NORMAL)
2207   {
2208     /* Disable Rx DMA Request */
2209     CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN);
2210     hi2s->RxXferCount = (uint16_t)0UL;
2211     hi2s->State = HAL_I2S_STATE_READY;
2212   }
2213   /* Call user Rx complete callback */
2214 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2215   hi2s->RxCpltCallback(hi2s);
2216 #else
2217   HAL_I2S_RxCpltCallback(hi2s);
2218 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2219 }
2220 
2221 /**
2222   * @brief  DMA I2S receive process half complete callback
2223   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2224   *         the configuration information for the specified DMA module.
2225   * @retval None
2226   */
I2S_DMARxHalfCplt(DMA_HandleTypeDef * hdma)2227 static void I2S_DMARxHalfCplt(DMA_HandleTypeDef *hdma)
2228 {
2229   /* Derogation MISRAC2012-Rule-11.5 */
2230   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2231 
2232   /* Call user Rx half complete callback */
2233 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2234   hi2s->RxHalfCpltCallback(hi2s);
2235 #else
2236   HAL_I2S_RxHalfCpltCallback(hi2s);
2237 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2238 }
2239 
2240 /**
2241   * @brief  DMA I2S transmit receive process complete callback
2242   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2243   *               the configuration information for the specified DMA module.
2244   * @retval None
2245   */
I2SEx_DMATxRxCplt(DMA_HandleTypeDef * hdma)2246 static void I2SEx_DMATxRxCplt(DMA_HandleTypeDef *hdma)
2247 {
2248   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2249 
2250   /* if DMA is configured in DMA_NORMAL Mode */
2251   if (hdma->Init.Mode == DMA_NORMAL)
2252   {
2253     /* Disable Tx DMA Request */
2254     CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_TXDMAEN);
2255     hi2s->TxXferCount = (uint16_t) 0UL;
2256 
2257     /* Disable Rx DMA Request */
2258     CLEAR_BIT(hi2s->Instance->CFG1, SPI_CFG1_RXDMAEN);
2259     hi2s->RxXferCount = (uint16_t)0UL;
2260 
2261     /* Updated HAL State */
2262     hi2s->State = HAL_I2S_STATE_READY;
2263   }
2264 
2265   /* Call user TxRx complete callback */
2266 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
2267   hi2s->TxRxCpltCallback(hi2s);
2268 #else
2269   HAL_I2SEx_TxRxCpltCallback(hi2s);
2270 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2271 }
2272 
2273 /**
2274   * @brief  DMA I2S transmit receive process half complete callback
2275   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2276   *               the configuration information for the specified DMA module.
2277   * @retval None
2278   */
I2SEx_DMATxRxHalfCplt(DMA_HandleTypeDef * hdma)2279 static void I2SEx_DMATxRxHalfCplt(DMA_HandleTypeDef *hdma)
2280 {
2281   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2282 
2283   /* Call user TxRx Half complete callback */
2284 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1U)
2285   hi2s->TxRxHalfCpltCallback(hi2s);
2286 #else
2287   HAL_I2SEx_TxRxHalfCpltCallback(hi2s);
2288 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2289 }
2290 
2291 /**
2292   * @brief  DMA I2S communication error callback
2293   * @param  hdma pointer to a DMA_HandleTypeDef structure that contains
2294   *         the configuration information for the specified DMA module.
2295   * @retval None
2296   */
I2S_DMAError(DMA_HandleTypeDef * hdma)2297 static void I2S_DMAError(DMA_HandleTypeDef *hdma)
2298 {
2299   /* Derogation MISRAC2012-Rule-11.5 */
2300   I2S_HandleTypeDef *hi2s = (I2S_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
2301 
2302   /* Disable Rx and Tx DMA Request */
2303   CLEAR_BIT(hi2s->Instance->CFG1, (SPI_CFG1_RXDMAEN | SPI_CFG1_TXDMAEN));
2304   hi2s->TxXferCount = (uint16_t) 0UL;
2305   hi2s->RxXferCount = (uint16_t) 0UL;
2306 
2307   hi2s->State = HAL_I2S_STATE_READY;
2308 
2309   /* Set the error code and execute error callback*/
2310   SET_BIT(hi2s->ErrorCode, HAL_I2S_ERROR_DMA);
2311   /* Call user error callback */
2312 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2313   hi2s->ErrorCallback(hi2s);
2314 #else
2315   HAL_I2S_ErrorCallback(hi2s);
2316 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2317 }
2318 
2319 /**
2320   * @brief  Manage the transmission 16-bit in Interrupt context
2321   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2322   *         the configuration information for I2S module
2323   * @retval None
2324   */
I2S_Transmit_16Bit_IT(I2S_HandleTypeDef * hi2s)2325 static void I2S_Transmit_16Bit_IT(I2S_HandleTypeDef *hi2s)
2326 {
2327   /* Transmit data */
2328 #if defined (__GNUC__)
2329   __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->TXDR));
2330 
2331   *ptxdr_16bits = *((const uint16_t *)hi2s->pTxBuffPtr);
2332 #else
2333   *((__IO uint16_t *)&hi2s->Instance->TXDR) = *((const uint16_t *)hi2s->pTxBuffPtr);
2334 #endif /* __GNUC__ */
2335   hi2s->pTxBuffPtr++;
2336   hi2s->TxXferCount--;
2337 
2338   if (hi2s->TxXferCount == 0UL)
2339   {
2340     /* Disable TXP and ERR interrupt */
2341     __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_ERR));
2342 
2343     if ((hi2s->Init.Mode == I2S_MODE_SLAVE_TX) || (hi2s->Init.Mode == I2S_MODE_MASTER_TX))
2344     {
2345       hi2s->State = HAL_I2S_STATE_READY;
2346 
2347       /* Call user Tx complete callback */
2348 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2349       hi2s->TxCpltCallback(hi2s);
2350 #else
2351       HAL_I2S_TxCpltCallback(hi2s);
2352 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2353     }
2354   }
2355 }
2356 
2357 /**
2358   * @brief  Manage the transmission 32-bit in Interrupt context
2359   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2360   *         the configuration information for I2S module
2361   * @retval None
2362   */
I2S_Transmit_32Bit_IT(I2S_HandleTypeDef * hi2s)2363 static void I2S_Transmit_32Bit_IT(I2S_HandleTypeDef *hi2s)
2364 {
2365   /* Transmit data */
2366   hi2s->Instance->TXDR = *((const uint32_t *)hi2s->pTxBuffPtr);
2367   hi2s->pTxBuffPtr += 2;
2368   hi2s->TxXferCount--;
2369 
2370   if (hi2s->TxXferCount == 0UL)
2371   {
2372     /* Disable TXP and ERR interrupt */
2373     __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_ERR));
2374 
2375     if ((hi2s->Init.Mode == I2S_MODE_SLAVE_TX) || (hi2s->Init.Mode == I2S_MODE_MASTER_TX))
2376     {
2377       hi2s->State = HAL_I2S_STATE_READY;
2378 
2379       /* Call user Tx complete callback */
2380 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2381       hi2s->TxCpltCallback(hi2s);
2382 #else
2383       HAL_I2S_TxCpltCallback(hi2s);
2384 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2385     }
2386   }
2387 }
2388 
2389 /**
2390   * @brief  Manage the reception 16-bit in Interrupt context
2391   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2392   *         the configuration information for I2S module
2393   * @retval None
2394   */
I2S_Receive_16Bit_IT(I2S_HandleTypeDef * hi2s)2395 static void I2S_Receive_16Bit_IT(I2S_HandleTypeDef *hi2s)
2396 {
2397   /* Receive data */
2398 #if defined (__GNUC__)
2399   __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hi2s->Instance->RXDR));
2400 
2401   *((uint16_t *)hi2s->pRxBuffPtr) = *prxdr_16bits;
2402 #else
2403   *((uint16_t *)hi2s->pRxBuffPtr) = *((__IO uint16_t *)&hi2s->Instance->RXDR);
2404 #endif /* __GNUC__ */
2405   hi2s->pRxBuffPtr++;
2406   hi2s->RxXferCount--;
2407 
2408   if (hi2s->RxXferCount == 0UL)
2409   {
2410     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2411     {
2412       /* Disable TXP, RXP, DXP, ERR interrupts */
2413       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_RXP | I2S_IT_DXP | I2S_IT_ERR));
2414     }
2415     else
2416     {
2417       /* Disable RXP and ERR interrupt */
2418       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXP | I2S_IT_ERR));
2419     }
2420 
2421     hi2s->State = HAL_I2S_STATE_READY;
2422     /* Call user Rx complete callback */
2423 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2424     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2425     {
2426       hi2s->TxRxCpltCallback(hi2s);
2427     }
2428     else
2429     {
2430       hi2s->RxCpltCallback(hi2s);
2431     }
2432 #else
2433     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2434     {
2435       HAL_I2SEx_TxRxCpltCallback(hi2s);
2436     }
2437     else
2438     {
2439       HAL_I2S_RxCpltCallback(hi2s);
2440     }
2441 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2442   }
2443 }
2444 
2445 /**
2446   * @brief  Manage the reception 32-bit in Interrupt context
2447   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2448   *         the configuration information for I2S module
2449   * @retval None
2450   */
I2S_Receive_32Bit_IT(I2S_HandleTypeDef * hi2s)2451 static void I2S_Receive_32Bit_IT(I2S_HandleTypeDef *hi2s)
2452 {
2453   /* Receive data */
2454   *((uint32_t *)hi2s->pRxBuffPtr) = hi2s->Instance->RXDR;
2455   hi2s->pRxBuffPtr += 2;
2456   hi2s->RxXferCount--;
2457 
2458   if (hi2s->RxXferCount == 0UL)
2459   {
2460     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2461     {
2462       /* Disable TXP, RXP, DXP, ERR interrupts */
2463       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_TXP | I2S_IT_RXP | I2S_IT_DXP | I2S_IT_ERR));
2464     }
2465     else
2466     {
2467       /* Disable RXP and ERR interrupt */
2468       __HAL_I2S_DISABLE_IT(hi2s, (I2S_IT_RXP | I2S_IT_ERR));
2469     }
2470 
2471     hi2s->State = HAL_I2S_STATE_READY;
2472     /* Call user Rx complete callback */
2473 #if (USE_HAL_I2S_REGISTER_CALLBACKS == 1UL)
2474     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2475     {
2476       hi2s->TxRxCpltCallback(hi2s);
2477     }
2478     else
2479     {
2480       hi2s->RxCpltCallback(hi2s);
2481     }
2482 #else
2483     if (IS_I2S_FULLDUPLEX(hi2s->Init.Mode))
2484     {
2485       HAL_I2SEx_TxRxCpltCallback(hi2s);
2486     }
2487     else
2488     {
2489       HAL_I2S_RxCpltCallback(hi2s);
2490     }
2491 #endif /* USE_HAL_I2S_REGISTER_CALLBACKS */
2492   }
2493 }
2494 
2495 /**
2496   * @brief  This function handles I2S Communication Timeout.
2497   * @param  hi2s pointer to a I2S_HandleTypeDef structure that contains
2498   *         the configuration information for I2S module
2499   * @param  Flag Flag checked
2500   * @param  State Value of the flag expected
2501   * @param  Tickstart Tick start value
2502   * @param  Timeout Duration of the timeout
2503   * @retval HAL status
2504   */
I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef * hi2s,uint32_t Flag,FlagStatus State,uint32_t Tickstart,uint32_t Timeout)2505 static HAL_StatusTypeDef I2S_WaitFlagStateUntilTimeout(I2S_HandleTypeDef *hi2s, uint32_t Flag, FlagStatus State,
2506                                                        uint32_t Tickstart, uint32_t Timeout)
2507 {
2508   /* Wait until flag is set to status*/
2509   while (((__HAL_I2S_GET_FLAG(hi2s, Flag)) ? SET : RESET) != State)
2510   {
2511     if (Timeout != HAL_MAX_DELAY)
2512     {
2513       if (((HAL_GetTick() - Tickstart) >= Timeout) || (Timeout == 0UL))
2514       {
2515         /* Set the I2S State ready */
2516         hi2s->State = HAL_I2S_STATE_READY;
2517 
2518         /* Process Unlocked */
2519         __HAL_UNLOCK(hi2s);
2520 
2521         return HAL_TIMEOUT;
2522       }
2523     }
2524   }
2525   return HAL_OK;
2526 }
2527 
2528 /**
2529   * @}
2530   */
2531 
2532 /**
2533   * @}
2534   */
2535 
2536 /**
2537   * @}
2538   */
2539 
2540 #endif /* HAL_I2S_MODULE_ENABLED */
2541 
2542