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