1 /**
2 ******************************************************************************
3 * @file stm32mp1xx_hal_spi.c
4 * @author MCD Application Team
5 * @brief SPI HAL module driver.
6 * This file provides firmware functions to manage the following
7 * functionalities of the Serial Peripheral Interface (SPI) peripheral:
8 * + Initialization and de-initialization functions
9 * + IO operation functions
10 * + Peripheral Control functions
11 * + Peripheral State functions
12 *
13 ******************************************************************************
14 * @attention
15 *
16 * Copyright (c) 2019 STMicroelectronics.
17 * All rights reserved.
18 *
19 * This software is licensed under terms that can be found in the LICENSE file
20 * in the root directory of this software component.
21 * If no LICENSE file comes with this software, it is provided AS-IS.
22 *
23 ******************************************************************************
24 @verbatim
25 ==============================================================================
26 ##### How to use this driver #####
27 ==============================================================================
28 [..]
29 The SPI HAL driver can be used as follows:
30
31 (#) Declare a SPI_HandleTypeDef handle structure, for example:
32 SPI_HandleTypeDef hspi;
33
34 (#)Initialize the SPI low level resources by implementing the HAL_SPI_MspInit() API:
35 (##) Enable the SPIx interface clock
36 (##) SPI pins configuration
37 (+++) Enable the clock for the SPI GPIOs
38 (+++) Configure these SPI pins as alternate function push-pull
39 (##) NVIC configuration if you need to use interrupt process or DMA process
40 (+++) Configure the SPIx interrupt priority
41 (+++) Enable the NVIC SPI IRQ handle
42 (##) DMA Configuration if you need to use DMA process
43 (+++) Declare a DMA_HandleTypeDef handle structure for the transmit or receive Stream/Channel
44 (+++) Enable the DMAx clock
45 (+++) Configure the DMA handle parameters
46 (+++) Configure the DMA Tx or Rx Stream/Channel
47 (+++) Associate the initialized hdma_tx handle to the hspi DMA Tx or Rx handle
48 (+++) Configure the priority and enable the NVIC for the transfer complete interrupt on the DMA Tx
49 or Rx Stream/Channel
50
51 (#) Program the Mode, BidirectionalMode , Data size, Baudrate Prescaler, NSS
52 management, Clock polarity and phase, FirstBit and CRC configuration in the hspi Init structure.
53
54 (#) Initialize the SPI registers by calling the HAL_SPI_Init() API:
55 (++) This API configures also the low level Hardware GPIO, CLOCK, CORTEX...etc)
56 by calling the customized HAL_SPI_MspInit() API.
57 [..]
58 Callback registration:
59
60 (#) The compilation flag USE_HAL_SPI_REGISTER_CALLBACKS when set to 1UL
61 allows the user to configure dynamically the driver callbacks.
62 Use Functions HAL_SPI_RegisterCallback() to register an interrupt callback.
63
64 Function HAL_SPI_RegisterCallback() allows to register following callbacks:
65 (+) TxCpltCallback : SPI Tx Completed callback
66 (+) RxCpltCallback : SPI Rx Completed callback
67 (+) TxRxCpltCallback : SPI TxRx Completed callback
68 (+) TxHalfCpltCallback : SPI Tx Half Completed callback
69 (+) RxHalfCpltCallback : SPI Rx Half Completed callback
70 (+) TxRxHalfCpltCallback : SPI TxRx Half Completed callback
71 (+) ErrorCallback : SPI Error callback
72 (+) AbortCpltCallback : SPI Abort callback
73 (+) SuspendCallback : SPI Suspend callback
74 (+) MspInitCallback : SPI Msp Init callback
75 (+) MspDeInitCallback : SPI Msp DeInit callback
76 This function takes as parameters the HAL peripheral handle, the Callback ID
77 and a pointer to the user callback function.
78
79
80 (#) Use function HAL_SPI_UnRegisterCallback to reset a callback to the default
81 weak function.
82 HAL_SPI_UnRegisterCallback takes as parameters the HAL peripheral handle,
83 and the Callback ID.
84 This function allows to reset following callbacks:
85 (+) TxCpltCallback : SPI Tx Completed callback
86 (+) RxCpltCallback : SPI Rx Completed callback
87 (+) TxRxCpltCallback : SPI TxRx Completed callback
88 (+) TxHalfCpltCallback : SPI Tx Half Completed callback
89 (+) RxHalfCpltCallback : SPI Rx Half Completed callback
90 (+) TxRxHalfCpltCallback : SPI TxRx Half Completed callback
91 (+) ErrorCallback : SPI Error callback
92 (+) AbortCpltCallback : SPI Abort callback
93 (+) SuspendCallback : SPI Suspend callback
94 (+) MspInitCallback : SPI Msp Init callback
95 (+) MspDeInitCallback : SPI Msp DeInit callback
96
97 By default, after the HAL_SPI_Init() and when the state is HAL_SPI_STATE_RESET
98 all callbacks are set to the corresponding weak functions:
99 examples HAL_SPI_MasterTxCpltCallback(), HAL_SPI_MasterRxCpltCallback().
100 Exception done for MspInit and MspDeInit functions that are
101 reset to the legacy weak functions in the HAL_SPI_Init()/ HAL_SPI_DeInit() only when
102 these callbacks are null (not registered beforehand).
103 If MspInit or MspDeInit are not null, the HAL_SPI_Init()/ HAL_SPI_DeInit()
104 keep and use the user MspInit/MspDeInit callbacks (registered beforehand) whatever the state.
105
106 Callbacks can be registered/unregistered in HAL_SPI_STATE_READY state only.
107 Exception done MspInit/MspDeInit functions that can be registered/unregistered
108 in HAL_SPI_STATE_READY or HAL_SPI_STATE_RESET state,
109 thus registered (user) MspInit/DeInit callbacks can be used during the Init/DeInit.
110 Then, the user first registers the MspInit/MspDeInit user callbacks
111 using HAL_SPI_RegisterCallback() before calling HAL_SPI_DeInit()
112 or HAL_SPI_Init() function.
113
114 When The compilation define USE_HAL_PPP_REGISTER_CALLBACKS is set to 0 or
115 not defined, the callback registering feature is not available
116 and weak (surcharged) callbacks are used.
117
118 SuspendCallback restriction:
119 SuspendCallback is called only when MasterReceiverAutoSusp is enabled and
120 EOT interrupt is activated. SuspendCallback is used in relation with functions
121 HAL_SPI_Transmit_IT, HAL_SPI_Receive_IT and HAL_SPI_TransmitReceive_IT.
122
123 [..]
124 Circular mode restriction:
125 (+) The DMA circular mode cannot be used when the SPI is configured in these modes:
126 (++) Master 2Lines RxOnly
127 (++) Master 1Line Rx
128 (+) The CRC feature is not managed when the DMA circular mode is enabled
129 (+) The functions HAL_SPI_DMAPause()/ HAL_SPI_DMAResume() are not supported. Return always
130 HAL_ERROR with ErrorCode set to HAL_SPI_ERROR_NOT_SUPPORTED.
131 Those functions are maintained for backward compatibility reasons.
132
133 @endverbatim
134 */
135
136 /* Includes ------------------------------------------------------------------*/
137 #include "stm32mp1xx_hal.h"
138
139 /** @addtogroup STM32MP1xx_HAL_Driver
140 * @{
141 */
142
143 /** @defgroup SPI SPI
144 * @brief SPI HAL module driver
145 * @{
146 */
147 #ifdef HAL_SPI_MODULE_ENABLED
148
149 /* Private typedef -----------------------------------------------------------*/
150 /* Private defines -----------------------------------------------------------*/
151 /** @defgroup SPI_Private_Constants SPI Private Constants
152 * @{
153 */
154 #define SPI_DEFAULT_TIMEOUT 100UL
155 #define MAX_FIFO_LENGTH 16UL
156 /**
157 * @}
158 */
159
160 /* Private macros ------------------------------------------------------------*/
161 /* Private variables ---------------------------------------------------------*/
162 /* Private function prototypes -----------------------------------------------*/
163 /** @defgroup SPI_Private_Functions SPI Private Functions
164 * @{
165 */
166 static void SPI_DMATransmitCplt(DMA_HandleTypeDef *hdma);
167 static void SPI_DMAReceiveCplt(DMA_HandleTypeDef *hdma);
168 static void SPI_DMATransmitReceiveCplt(DMA_HandleTypeDef *hdma);
169 static void SPI_DMAHalfTransmitCplt(DMA_HandleTypeDef *hdma);
170 static void SPI_DMAHalfReceiveCplt(DMA_HandleTypeDef *hdma);
171 static void SPI_DMAHalfTransmitReceiveCplt(DMA_HandleTypeDef *hdma);
172 static void SPI_DMAError(DMA_HandleTypeDef *hdma);
173 static void SPI_DMAAbortOnError(DMA_HandleTypeDef *hdma);
174 static void SPI_DMATxAbortCallback(DMA_HandleTypeDef *hdma);
175 static void SPI_DMARxAbortCallback(DMA_HandleTypeDef *hdma);
176 static HAL_StatusTypeDef SPI_WaitOnFlagUntilTimeout(SPI_HandleTypeDef *hspi, uint32_t Flag, FlagStatus FlagStatus,
177 uint32_t Timeout, uint32_t Tickstart);
178 static void SPI_TxISR_8BIT(SPI_HandleTypeDef *hspi);
179 static void SPI_TxISR_16BIT(SPI_HandleTypeDef *hspi);
180 static void SPI_TxISR_32BIT(SPI_HandleTypeDef *hspi);
181 static void SPI_RxISR_8BIT(SPI_HandleTypeDef *hspi);
182 static void SPI_RxISR_16BIT(SPI_HandleTypeDef *hspi);
183 static void SPI_RxISR_32BIT(SPI_HandleTypeDef *hspi);
184 static void SPI_AbortTransfer(SPI_HandleTypeDef *hspi);
185 static void SPI_CloseTransfer(SPI_HandleTypeDef *hspi);
186 static uint32_t SPI_GetPacketSize(SPI_HandleTypeDef *hspi);
187
188
189 /**
190 * @}
191 */
192
193 /* Exported functions --------------------------------------------------------*/
194 /** @defgroup SPI_Exported_Functions SPI Exported Functions
195 * @{
196 */
197
198 /** @defgroup SPI_Exported_Functions_Group1 Initialization and de-initialization functions
199 * @brief Initialization and Configuration functions
200 *
201 @verbatim
202 ===============================================================================
203 ##### Initialization and de-initialization functions #####
204 ===============================================================================
205 [..] This subsection provides a set of functions allowing to initialize and
206 de-initialize the SPIx peripheral:
207
208 (+) User must implement HAL_SPI_MspInit() function in which he configures
209 all related peripherals resources (CLOCK, GPIO, DMA, IT and NVIC ).
210
211 (+) Call the function HAL_SPI_Init() to configure the selected device with
212 the selected configuration:
213 (++) Mode
214 (++) Direction
215 (++) Data Size
216 (++) Clock Polarity and Phase
217 (++) NSS Management
218 (++) BaudRate Prescaler
219 (++) FirstBit
220 (++) TIMode
221 (++) CRC Calculation
222 (++) CRC Polynomial if CRC enabled
223 (++) CRC Length, used only with Data8 and Data16
224 (++) FIFO reception threshold
225 (++) FIFO transmission threshold
226
227 (+) Call the function HAL_SPI_DeInit() to restore the default configuration
228 of the selected SPIx peripheral.
229
230 @endverbatim
231 * @{
232 */
233
234 /**
235 * @brief Initialize the SPI according to the specified parameters
236 * in the SPI_InitTypeDef and initialize the associated handle.
237 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
238 * the configuration information for SPI module.
239 * @retval HAL status
240 */
HAL_SPI_Init(SPI_HandleTypeDef * hspi)241 HAL_StatusTypeDef HAL_SPI_Init(SPI_HandleTypeDef *hspi)
242 {
243 uint32_t crc_length;
244 uint32_t packet_length;
245
246 /* Check the SPI handle allocation */
247 if (hspi == NULL)
248 {
249 return HAL_ERROR;
250 }
251
252 /* Check the parameters */
253 assert_param(IS_SPI_ALL_INSTANCE(hspi->Instance));
254 assert_param(IS_SPI_MODE(hspi->Init.Mode));
255 assert_param(IS_SPI_DIRECTION(hspi->Init.Direction));
256 assert_param(IS_SPI_DATASIZE(hspi->Init.DataSize));
257 assert_param(IS_SPI_FIFOTHRESHOLD(hspi->Init.FifoThreshold));
258 assert_param(IS_SPI_NSS(hspi->Init.NSS));
259 assert_param(IS_SPI_NSSP(hspi->Init.NSSPMode));
260 assert_param(IS_SPI_BAUDRATE_PRESCALER(hspi->Init.BaudRatePrescaler));
261 assert_param(IS_SPI_FIRST_BIT(hspi->Init.FirstBit));
262 assert_param(IS_SPI_TIMODE(hspi->Init.TIMode));
263 if (hspi->Init.TIMode == SPI_TIMODE_DISABLE)
264 {
265 assert_param(IS_SPI_CPOL(hspi->Init.CLKPolarity));
266 assert_param(IS_SPI_CPHA(hspi->Init.CLKPhase));
267 }
268 #if (USE_SPI_CRC != 0UL)
269 assert_param(IS_SPI_CRC_CALCULATION(hspi->Init.CRCCalculation));
270 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE)
271 {
272 assert_param(IS_SPI_CRC_LENGTH(hspi->Init.CRCLength));
273 assert_param(IS_SPI_CRC_POLYNOMIAL(hspi->Init.CRCPolynomial));
274 assert_param(IS_SPI_CRC_INITIALIZATION_PATTERN(hspi->Init.TxCRCInitializationPattern));
275 assert_param(IS_SPI_CRC_INITIALIZATION_PATTERN(hspi->Init.RxCRCInitializationPattern));
276 }
277 #else
278 hspi->Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;
279 #endif /* USE_SPI_CRC */
280
281 /* Verify that the SPI instance supports Data Size higher than 16bits */
282 if ((!IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (hspi->Init.DataSize > SPI_DATASIZE_16BIT))
283 {
284 return HAL_ERROR;
285 }
286
287 /* Verify that the SPI instance supports requested data packing */
288 packet_length = SPI_GetPacketSize(hspi);
289 if (((!IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (packet_length > SPI_LOWEND_FIFO_SIZE)) ||
290 ((IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (packet_length > SPI_HIGHEND_FIFO_SIZE)))
291 {
292 return HAL_ERROR;
293 }
294
295 #if (USE_SPI_CRC != 0UL)
296 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE)
297 {
298 /* Verify that the SPI instance supports CRC Length higher than 16bits */
299 if ((!IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (hspi->Init.CRCLength > SPI_CRC_LENGTH_16BIT))
300 {
301 return HAL_ERROR;
302 }
303
304 /* Align the CRC Length on the data size */
305 if (hspi->Init.CRCLength == SPI_CRC_LENGTH_DATASIZE)
306 {
307 crc_length = (hspi->Init.DataSize >> SPI_CFG1_DSIZE_Pos) << SPI_CFG1_CRCSIZE_Pos;
308 }
309 else
310 {
311 crc_length = hspi->Init.CRCLength;
312 }
313
314 /* Verify that the CRC Length is higher than DataSize */
315 if ((hspi->Init.DataSize >> SPI_CFG1_DSIZE_Pos) > (crc_length >> SPI_CFG1_CRCSIZE_Pos))
316 {
317 return HAL_ERROR;
318 }
319 }
320 else
321 {
322 crc_length = hspi->Init.DataSize << SPI_CFG1_CRCSIZE_Pos;
323 }
324 #endif /* USE_SPI_CRC */
325
326 if (hspi->State == HAL_SPI_STATE_RESET)
327 {
328 /* Allocate lock resource and initialize it */
329 hspi->Lock = HAL_UNLOCKED;
330
331 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
332 /* Init the SPI Callback settings */
333 hspi->TxCpltCallback = HAL_SPI_TxCpltCallback; /* Legacy weak TxCpltCallback */
334 hspi->RxCpltCallback = HAL_SPI_RxCpltCallback; /* Legacy weak RxCpltCallback */
335 hspi->TxRxCpltCallback = HAL_SPI_TxRxCpltCallback; /* Legacy weak TxRxCpltCallback */
336 hspi->TxHalfCpltCallback = HAL_SPI_TxHalfCpltCallback; /* Legacy weak TxHalfCpltCallback */
337 hspi->RxHalfCpltCallback = HAL_SPI_RxHalfCpltCallback; /* Legacy weak RxHalfCpltCallback */
338 hspi->TxRxHalfCpltCallback = HAL_SPI_TxRxHalfCpltCallback; /* Legacy weak TxRxHalfCpltCallback */
339 hspi->ErrorCallback = HAL_SPI_ErrorCallback; /* Legacy weak ErrorCallback */
340 hspi->AbortCpltCallback = HAL_SPI_AbortCpltCallback; /* Legacy weak AbortCpltCallback */
341 hspi->SuspendCallback = HAL_SPI_SuspendCallback; /* Legacy weak SuspendCallback */
342
343 if (hspi->MspInitCallback == NULL)
344 {
345 hspi->MspInitCallback = HAL_SPI_MspInit; /* Legacy weak MspInit */
346 }
347
348 /* Init the low level hardware : GPIO, CLOCK, NVIC... */
349 hspi->MspInitCallback(hspi);
350 #else
351 /* Init the low level hardware : GPIO, CLOCK, NVIC... */
352 HAL_SPI_MspInit(hspi);
353 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
354 }
355
356 hspi->State = HAL_SPI_STATE_BUSY;
357
358 /* Disable the selected SPI peripheral */
359 __HAL_SPI_DISABLE(hspi);
360
361 #if (USE_SPI_CRC == 0)
362 /* Keep the default value of CRCSIZE in case of CRC is not used */
363 crc_length = hspi->Instance->CFG1 & SPI_CFG1_CRCSIZE;
364 #endif /* USE_SPI_CRC */
365
366 /*----------------------- SPIx CR1 & CR2 Configuration ---------------------*/
367 /* Configure : SPI Mode, Communication Mode, Clock polarity and phase, NSS management,
368 Communication speed, First bit, CRC calculation state, CRC Length */
369
370 /* SPIx NSS Software Management Configuration */
371 if ((hspi->Init.NSS == SPI_NSS_SOFT) && (((hspi->Init.Mode == SPI_MODE_MASTER) && \
372 (hspi->Init.NSSPolarity == SPI_NSS_POLARITY_LOW)) || \
373 ((hspi->Init.Mode == SPI_MODE_SLAVE) && \
374 (hspi->Init.NSSPolarity == SPI_NSS_POLARITY_HIGH))))
375 {
376 SET_BIT(hspi->Instance->CR1, SPI_CR1_SSI);
377 }
378
379 /* SPIx Master Rx Auto Suspend Configuration */
380 if (((hspi->Init.Mode & SPI_MODE_MASTER) == SPI_MODE_MASTER) && (hspi->Init.DataSize >= SPI_DATASIZE_8BIT))
381 {
382 MODIFY_REG(hspi->Instance->CR1, SPI_CR1_MASRX, hspi->Init.MasterReceiverAutoSusp);
383 }
384 else
385 {
386 CLEAR_BIT(hspi->Instance->CR1, SPI_CR1_MASRX);
387 }
388
389 /* SPIx CFG1 Configuration */
390 WRITE_REG(hspi->Instance->CFG1, (hspi->Init.BaudRatePrescaler | hspi->Init.CRCCalculation | crc_length |
391 hspi->Init.FifoThreshold | hspi->Init.DataSize));
392
393 /* SPIx CFG2 Configuration */
394 WRITE_REG(hspi->Instance->CFG2, (hspi->Init.NSSPMode | hspi->Init.TIMode |
395 hspi->Init.NSSPolarity | hspi->Init.NSS |
396 hspi->Init.CLKPolarity | hspi->Init.CLKPhase |
397 hspi->Init.FirstBit | hspi->Init.Mode |
398 hspi->Init.MasterInterDataIdleness | hspi->Init.Direction |
399 hspi->Init.MasterSSIdleness | hspi->Init.IOSwap));
400
401 #if (USE_SPI_CRC != 0UL)
402 /*---------------------------- SPIx CRCPOLY Configuration ------------------*/
403 /* Configure : CRC Polynomial */
404 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE)
405 {
406 /* Initialize TXCRC Pattern Initial Value */
407 if (hspi->Init.TxCRCInitializationPattern == SPI_CRC_INITIALIZATION_ALL_ONE_PATTERN)
408 {
409 SET_BIT(hspi->Instance->CR1, SPI_CR1_TCRCINI);
410 }
411 else
412 {
413 CLEAR_BIT(hspi->Instance->CR1, SPI_CR1_TCRCINI);
414 }
415
416 /* Initialize RXCRC Pattern Initial Value */
417 if (hspi->Init.RxCRCInitializationPattern == SPI_CRC_INITIALIZATION_ALL_ONE_PATTERN)
418 {
419 SET_BIT(hspi->Instance->CR1, SPI_CR1_RCRCINI);
420 }
421 else
422 {
423 CLEAR_BIT(hspi->Instance->CR1, SPI_CR1_RCRCINI);
424 }
425
426 /* Enable 33/17 bits CRC computation */
427 if (((!IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (crc_length == SPI_CRC_LENGTH_16BIT)) ||
428 ((IS_SPI_HIGHEND_INSTANCE(hspi->Instance)) && (crc_length == SPI_CRC_LENGTH_32BIT)))
429 {
430 SET_BIT(hspi->Instance->CR1, SPI_CR1_CRC33_17);
431 }
432 else
433 {
434 CLEAR_BIT(hspi->Instance->CR1, SPI_CR1_CRC33_17);
435 }
436
437 /* Write CRC polynomial in SPI Register */
438 WRITE_REG(hspi->Instance->CRCPOLY, hspi->Init.CRCPolynomial);
439 }
440 #endif /* USE_SPI_CRC */
441
442 /* Insure that Underrun configuration is managed only by Salve */
443 if (hspi->Init.Mode == SPI_MODE_SLAVE)
444 {
445 /* Set Default Underrun configuration */
446 #if (USE_SPI_CRC != 0UL)
447 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_DISABLE)
448 #endif /* USE_SPI_CRC */
449 {
450 MODIFY_REG(hspi->Instance->CFG1, SPI_CFG1_UDRDET, SPI_CFG1_UDRDET_0);
451 }
452 MODIFY_REG(hspi->Instance->CFG1, SPI_CFG1_UDRCFG, SPI_CFG1_UDRCFG_1);
453 }
454
455 #if defined(SPI_I2SCFGR_I2SMOD)
456 /* Activate the SPI mode (Make sure that I2SMOD bit in I2SCFGR register is reset) */
457 CLEAR_BIT(hspi->Instance->I2SCFGR, SPI_I2SCFGR_I2SMOD);
458 #endif /* SPI_I2SCFGR_I2SMOD */
459
460 /* Insure that AFCNTR is managed only by Master */
461 if ((hspi->Init.Mode & SPI_MODE_MASTER) == SPI_MODE_MASTER)
462 {
463 /* Alternate function GPIOs control */
464 MODIFY_REG(hspi->Instance->CFG2, SPI_CFG2_AFCNTR, (hspi->Init.MasterKeepIOState));
465 }
466
467 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
468 hspi->State = HAL_SPI_STATE_READY;
469
470 return HAL_OK;
471 }
472
473 /**
474 * @brief De-Initialize the SPI peripheral.
475 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
476 * the configuration information for SPI module.
477 * @retval HAL status
478 */
HAL_SPI_DeInit(SPI_HandleTypeDef * hspi)479 HAL_StatusTypeDef HAL_SPI_DeInit(SPI_HandleTypeDef *hspi)
480 {
481 /* Check the SPI handle allocation */
482 if (hspi == NULL)
483 {
484 return HAL_ERROR;
485 }
486
487 /* Check SPI Instance parameter */
488 assert_param(IS_SPI_ALL_INSTANCE(hspi->Instance));
489
490 hspi->State = HAL_SPI_STATE_BUSY;
491
492 /* Disable the SPI Peripheral Clock */
493 __HAL_SPI_DISABLE(hspi);
494
495 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
496 if (hspi->MspDeInitCallback == NULL)
497 {
498 hspi->MspDeInitCallback = HAL_SPI_MspDeInit; /* Legacy weak MspDeInit */
499 }
500
501 /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
502 hspi->MspDeInitCallback(hspi);
503 #else
504 /* DeInit the low level hardware: GPIO, CLOCK, NVIC... */
505 HAL_SPI_MspDeInit(hspi);
506 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
507
508 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
509 hspi->State = HAL_SPI_STATE_RESET;
510
511 /* Release Lock */
512 __HAL_UNLOCK(hspi);
513
514 return HAL_OK;
515 }
516
517 /**
518 * @brief Initialize the SPI MSP.
519 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
520 * the configuration information for SPI module.
521 * @retval None
522 */
HAL_SPI_MspInit(SPI_HandleTypeDef * hspi)523 __weak void HAL_SPI_MspInit(SPI_HandleTypeDef *hspi)
524 {
525 /* Prevent unused argument(s) compilation warning */
526 UNUSED(hspi);
527
528 /* NOTE : This function should not be modified, when the callback is needed,
529 the HAL_SPI_MspInit should be implemented in the user file
530 */
531 }
532
533 /**
534 * @brief De-Initialize the SPI MSP.
535 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
536 * the configuration information for SPI module.
537 * @retval None
538 */
HAL_SPI_MspDeInit(SPI_HandleTypeDef * hspi)539 __weak void HAL_SPI_MspDeInit(SPI_HandleTypeDef *hspi)
540 {
541 /* Prevent unused argument(s) compilation warning */
542 UNUSED(hspi);
543
544 /* NOTE : This function should not be modified, when the callback is needed,
545 the HAL_SPI_MspDeInit should be implemented in the user file
546 */
547 }
548
549 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
550 /**
551 * @brief Register a User SPI Callback
552 * To be used instead of the weak predefined callback
553 * @param hspi Pointer to a SPI_HandleTypeDef structure that contains
554 * the configuration information for the specified SPI.
555 * @param CallbackID ID of the callback to be registered
556 * @param pCallback pointer to the Callback function
557 * @retval HAL status
558 */
HAL_SPI_RegisterCallback(SPI_HandleTypeDef * hspi,HAL_SPI_CallbackIDTypeDef CallbackID,pSPI_CallbackTypeDef pCallback)559 HAL_StatusTypeDef HAL_SPI_RegisterCallback(SPI_HandleTypeDef *hspi, HAL_SPI_CallbackIDTypeDef CallbackID,
560 pSPI_CallbackTypeDef pCallback)
561 {
562 HAL_StatusTypeDef status = HAL_OK;
563
564 if (pCallback == NULL)
565 {
566 /* Update the error code */
567 hspi->ErrorCode |= HAL_SPI_ERROR_INVALID_CALLBACK;
568
569 return HAL_ERROR;
570 }
571 /* Lock the process */
572 __HAL_LOCK(hspi);
573
574 if (HAL_SPI_STATE_READY == hspi->State)
575 {
576 switch (CallbackID)
577 {
578 case HAL_SPI_TX_COMPLETE_CB_ID :
579 hspi->TxCpltCallback = pCallback;
580 break;
581
582 case HAL_SPI_RX_COMPLETE_CB_ID :
583 hspi->RxCpltCallback = pCallback;
584 break;
585
586 case HAL_SPI_TX_RX_COMPLETE_CB_ID :
587 hspi->TxRxCpltCallback = pCallback;
588 break;
589
590 case HAL_SPI_TX_HALF_COMPLETE_CB_ID :
591 hspi->TxHalfCpltCallback = pCallback;
592 break;
593
594 case HAL_SPI_RX_HALF_COMPLETE_CB_ID :
595 hspi->RxHalfCpltCallback = pCallback;
596 break;
597
598 case HAL_SPI_TX_RX_HALF_COMPLETE_CB_ID :
599 hspi->TxRxHalfCpltCallback = pCallback;
600 break;
601
602 case HAL_SPI_ERROR_CB_ID :
603 hspi->ErrorCallback = pCallback;
604 break;
605
606 case HAL_SPI_ABORT_CB_ID :
607 hspi->AbortCpltCallback = pCallback;
608 break;
609
610 case HAL_SPI_SUSPEND_CB_ID :
611 hspi->SuspendCallback = pCallback;
612 break;
613
614 case HAL_SPI_MSPINIT_CB_ID :
615 hspi->MspInitCallback = pCallback;
616 break;
617
618 case HAL_SPI_MSPDEINIT_CB_ID :
619 hspi->MspDeInitCallback = pCallback;
620 break;
621
622 default :
623 /* Update the error code */
624 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
625
626 /* Return error status */
627 status = HAL_ERROR;
628 break;
629 }
630 }
631 else if (HAL_SPI_STATE_RESET == hspi->State)
632 {
633 switch (CallbackID)
634 {
635 case HAL_SPI_MSPINIT_CB_ID :
636 hspi->MspInitCallback = pCallback;
637 break;
638
639 case HAL_SPI_MSPDEINIT_CB_ID :
640 hspi->MspDeInitCallback = pCallback;
641 break;
642
643 default :
644 /* Update the error code */
645 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
646
647 /* Return error status */
648 status = HAL_ERROR;
649 break;
650 }
651 }
652 else
653 {
654 /* Update the error code */
655 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
656
657 /* Return error status */
658 status = HAL_ERROR;
659 }
660
661 /* Release Lock */
662 __HAL_UNLOCK(hspi);
663 return status;
664 }
665
666 /**
667 * @brief Unregister an SPI Callback
668 * SPI callback is redirected to the weak predefined callback
669 * @param hspi Pointer to a SPI_HandleTypeDef structure that contains
670 * the configuration information for the specified SPI.
671 * @param CallbackID ID of the callback to be unregistered
672 * @retval HAL status
673 */
HAL_SPI_UnRegisterCallback(SPI_HandleTypeDef * hspi,HAL_SPI_CallbackIDTypeDef CallbackID)674 HAL_StatusTypeDef HAL_SPI_UnRegisterCallback(SPI_HandleTypeDef *hspi, HAL_SPI_CallbackIDTypeDef CallbackID)
675 {
676 HAL_StatusTypeDef status = HAL_OK;
677
678 /* Lock the process */
679 __HAL_LOCK(hspi);
680
681 if (HAL_SPI_STATE_READY == hspi->State)
682 {
683 switch (CallbackID)
684 {
685 case HAL_SPI_TX_COMPLETE_CB_ID :
686 hspi->TxCpltCallback = HAL_SPI_TxCpltCallback; /* Legacy weak TxCpltCallback */
687 break;
688
689 case HAL_SPI_RX_COMPLETE_CB_ID :
690 hspi->RxCpltCallback = HAL_SPI_RxCpltCallback; /* Legacy weak RxCpltCallback */
691 break;
692
693 case HAL_SPI_TX_RX_COMPLETE_CB_ID :
694 hspi->TxRxCpltCallback = HAL_SPI_TxRxCpltCallback; /* Legacy weak TxRxCpltCallback */
695 break;
696
697 case HAL_SPI_TX_HALF_COMPLETE_CB_ID :
698 hspi->TxHalfCpltCallback = HAL_SPI_TxHalfCpltCallback; /* Legacy weak TxHalfCpltCallback */
699 break;
700
701 case HAL_SPI_RX_HALF_COMPLETE_CB_ID :
702 hspi->RxHalfCpltCallback = HAL_SPI_RxHalfCpltCallback; /* Legacy weak RxHalfCpltCallback */
703 break;
704
705 case HAL_SPI_TX_RX_HALF_COMPLETE_CB_ID :
706 hspi->TxRxHalfCpltCallback = HAL_SPI_TxRxHalfCpltCallback; /* Legacy weak TxRxHalfCpltCallback */
707 break;
708
709 case HAL_SPI_ERROR_CB_ID :
710 hspi->ErrorCallback = HAL_SPI_ErrorCallback; /* Legacy weak ErrorCallback */
711 break;
712
713 case HAL_SPI_ABORT_CB_ID :
714 hspi->AbortCpltCallback = HAL_SPI_AbortCpltCallback; /* Legacy weak AbortCpltCallback */
715 break;
716
717 case HAL_SPI_SUSPEND_CB_ID :
718 hspi->SuspendCallback = HAL_SPI_SuspendCallback; /* Legacy weak SuspendCallback */
719 break;
720
721 case HAL_SPI_MSPINIT_CB_ID :
722 hspi->MspInitCallback = HAL_SPI_MspInit; /* Legacy weak MspInit */
723 break;
724
725 case HAL_SPI_MSPDEINIT_CB_ID :
726 hspi->MspDeInitCallback = HAL_SPI_MspDeInit; /* Legacy weak MspDeInit */
727 break;
728
729 default :
730 /* Update the error code */
731 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
732
733 /* Return error status */
734 status = HAL_ERROR;
735 break;
736 }
737 }
738 else if (HAL_SPI_STATE_RESET == hspi->State)
739 {
740 switch (CallbackID)
741 {
742 case HAL_SPI_MSPINIT_CB_ID :
743 hspi->MspInitCallback = HAL_SPI_MspInit; /* Legacy weak MspInit */
744 break;
745
746 case HAL_SPI_MSPDEINIT_CB_ID :
747 hspi->MspDeInitCallback = HAL_SPI_MspDeInit; /* Legacy weak MspDeInit */
748 break;
749
750 default :
751 /* Update the error code */
752 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
753
754 /* Return error status */
755 status = HAL_ERROR;
756 break;
757 }
758 }
759 else
760 {
761 /* Update the error code */
762 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_INVALID_CALLBACK);
763
764 /* Return error status */
765 status = HAL_ERROR;
766 }
767
768 /* Release Lock */
769 __HAL_UNLOCK(hspi);
770 return status;
771 }
772 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
773 /**
774 * @}
775 */
776
777 /** @defgroup SPI_Exported_Functions_Group2 IO operation functions
778 * @brief Data transfers functions
779 *
780 @verbatim
781 ==============================================================================
782 ##### IO operation functions #####
783 ===============================================================================
784 [..]
785 This subsection provides a set of functions allowing to manage the SPI
786 data transfers.
787
788 [..] The SPI supports master and slave mode :
789
790 (#) There are two modes of transfer:
791 (##) Blocking mode: The communication is performed in polling mode.
792 The HAL status of all data processing is returned by the same function
793 after finishing transfer.
794 (##) No-Blocking mode: The communication is performed using Interrupts
795 or DMA, These APIs return the HAL status.
796 The end of the data processing will be indicated through the
797 dedicated SPI IRQ when using Interrupt mode or the DMA IRQ when
798 using DMA mode.
799 The HAL_SPI_TxCpltCallback(), HAL_SPI_RxCpltCallback() and HAL_SPI_TxRxCpltCallback() user callbacks
800 will be executed respectively at the end of the transmit or Receive process
801 The HAL_SPI_ErrorCallback()user callback will be executed when a communication error is detected
802
803 (#) APIs provided for these 2 transfer modes (Blocking mode or Non blocking mode using either Interrupt or DMA)
804 exist for 1Line (simplex) and 2Lines (full duplex) modes.
805
806 @endverbatim
807 * @{
808 */
809
810 /**
811 * @brief Transmit an amount of data in blocking mode.
812 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
813 * the configuration information for SPI module.
814 * @param pData : pointer to data buffer
815 * @param Size : amount of data to be sent
816 * @param Timeout: Timeout duration
817 * @retval HAL status
818 */
HAL_SPI_Transmit(SPI_HandleTypeDef * hspi,const uint8_t * pData,uint16_t Size,uint32_t Timeout)819 HAL_StatusTypeDef HAL_SPI_Transmit(SPI_HandleTypeDef *hspi, const uint8_t *pData, uint16_t Size, uint32_t Timeout)
820 {
821 #if defined (__GNUC__)
822 __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->TXDR));
823 #endif /* __GNUC__ */
824
825 uint32_t tickstart;
826 HAL_StatusTypeDef errorcode = HAL_OK;
827
828 /* Check Direction parameter */
829 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_TXONLY(hspi->Init.Direction));
830
831 /* Lock the process */
832 __HAL_LOCK(hspi);
833
834 /* Init tickstart for timeout management*/
835 tickstart = HAL_GetTick();
836
837 if (hspi->State != HAL_SPI_STATE_READY)
838 {
839 errorcode = HAL_BUSY;
840 __HAL_UNLOCK(hspi);
841 return errorcode;
842 }
843
844 if ((pData == NULL) || (Size == 0UL))
845 {
846 errorcode = HAL_ERROR;
847 __HAL_UNLOCK(hspi);
848 return errorcode;
849 }
850
851 /* Set the transaction information */
852 hspi->State = HAL_SPI_STATE_BUSY_TX;
853 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
854 hspi->pTxBuffPtr = (const uint8_t *)pData;
855 hspi->TxXferSize = Size;
856 hspi->TxXferCount = Size;
857
858 /*Init field not used in handle to zero */
859 hspi->pRxBuffPtr = NULL;
860 hspi->RxXferSize = (uint16_t) 0UL;
861 hspi->RxXferCount = (uint16_t) 0UL;
862 hspi->TxISR = NULL;
863 hspi->RxISR = NULL;
864
865 /* Configure communication direction : 1Line */
866 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
867 {
868 SPI_1LINE_TX(hspi);
869 }
870 else
871 {
872 SPI_2LINES_TX(hspi);
873 }
874
875 /* Set the number of data at current transfer */
876 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
877
878 /* Enable SPI peripheral */
879 __HAL_SPI_ENABLE(hspi);
880
881 if (hspi->Init.Mode == SPI_MODE_MASTER)
882 {
883 /* Master transfer start */
884 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
885 }
886
887 /* Transmit data in 32 Bit mode */
888 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
889 {
890 /* Transmit data in 32 Bit mode */
891 while (hspi->TxXferCount > 0UL)
892 {
893 /* Wait until TXP flag is set to send data */
894 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP))
895 {
896 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
897 hspi->pTxBuffPtr += sizeof(uint32_t);
898 hspi->TxXferCount--;
899 }
900 else
901 {
902 /* Timeout management */
903 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
904 {
905 /* Call standard close procedure with error check */
906 SPI_CloseTransfer(hspi);
907
908 /* Unlock the process */
909 __HAL_UNLOCK(hspi);
910
911 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
912 hspi->State = HAL_SPI_STATE_READY;
913 return HAL_TIMEOUT;
914 }
915 }
916 }
917 }
918 /* Transmit data in 16 Bit mode */
919 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
920 {
921 /* Transmit data in 16 Bit mode */
922 while (hspi->TxXferCount > 0UL)
923 {
924 /* Wait until TXP flag is set to send data */
925 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP))
926 {
927 if ((hspi->TxXferCount > 1UL) && (hspi->Init.FifoThreshold > SPI_FIFO_THRESHOLD_01DATA))
928 {
929 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
930 hspi->pTxBuffPtr += sizeof(uint32_t);
931 hspi->TxXferCount -= (uint16_t)2UL;
932 }
933 else
934 {
935 #if defined (__GNUC__)
936 *ptxdr_16bits = *((const uint16_t *)hspi->pTxBuffPtr);
937 #else
938 *((__IO uint16_t *)&hspi->Instance->TXDR) = *((const uint16_t *)hspi->pTxBuffPtr);
939 #endif /* __GNUC__ */
940 hspi->pTxBuffPtr += sizeof(uint16_t);
941 hspi->TxXferCount--;
942 }
943 }
944 else
945 {
946 /* Timeout management */
947 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
948 {
949 /* Call standard close procedure with error check */
950 SPI_CloseTransfer(hspi);
951
952 /* Unlock the process */
953 __HAL_UNLOCK(hspi);
954
955 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
956 hspi->State = HAL_SPI_STATE_READY;
957 return HAL_TIMEOUT;
958 }
959 }
960 }
961 }
962 /* Transmit data in 8 Bit mode */
963 else
964 {
965 while (hspi->TxXferCount > 0UL)
966 {
967 /* Wait until TXP flag is set to send data */
968 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP))
969 {
970 if ((hspi->TxXferCount > 3UL) && (hspi->Init.FifoThreshold > SPI_FIFO_THRESHOLD_03DATA))
971 {
972 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
973 hspi->pTxBuffPtr += sizeof(uint32_t);
974 hspi->TxXferCount -= (uint16_t)4UL;
975 }
976 else if ((hspi->TxXferCount > 1UL) && (hspi->Init.FifoThreshold > SPI_FIFO_THRESHOLD_01DATA))
977 {
978 #if defined (__GNUC__)
979 *ptxdr_16bits = *((const uint16_t *)hspi->pTxBuffPtr);
980 #else
981 *((__IO uint16_t *)&hspi->Instance->TXDR) = *((const uint16_t *)hspi->pTxBuffPtr);
982 #endif /* __GNUC__ */
983 hspi->pTxBuffPtr += sizeof(uint16_t);
984 hspi->TxXferCount -= (uint16_t)2UL;
985 }
986 else
987 {
988 *((__IO uint8_t *)&hspi->Instance->TXDR) = *((const uint8_t *)hspi->pTxBuffPtr);
989 hspi->pTxBuffPtr += sizeof(uint8_t);
990 hspi->TxXferCount--;
991 }
992 }
993 else
994 {
995 /* Timeout management */
996 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
997 {
998 /* Call standard close procedure with error check */
999 SPI_CloseTransfer(hspi);
1000
1001 /* Unlock the process */
1002 __HAL_UNLOCK(hspi);
1003
1004 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1005 hspi->State = HAL_SPI_STATE_READY;
1006 return HAL_TIMEOUT;
1007 }
1008 }
1009 }
1010 }
1011
1012 /* Wait for Tx (and CRC) data to be sent */
1013 if (SPI_WaitOnFlagUntilTimeout(hspi, SPI_FLAG_EOT, RESET, tickstart, Timeout) != HAL_OK)
1014 {
1015 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FLAG);
1016 }
1017
1018 /* Call standard close procedure with error check */
1019 SPI_CloseTransfer(hspi);
1020
1021 /* Unlock the process */
1022 __HAL_UNLOCK(hspi);
1023
1024 hspi->State = HAL_SPI_STATE_READY;
1025
1026 if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
1027 {
1028 return HAL_ERROR;
1029 }
1030 return errorcode;
1031 }
1032
1033 /**
1034 * @brief Receive an amount of data in blocking mode.
1035 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1036 * the configuration information for SPI module.
1037 * @param pData : pointer to data buffer
1038 * @param Size : amount of data to be received
1039 * @param Timeout: Timeout duration
1040 * @retval HAL status
1041 */
HAL_SPI_Receive(SPI_HandleTypeDef * hspi,uint8_t * pData,uint16_t Size,uint32_t Timeout)1042 HAL_StatusTypeDef HAL_SPI_Receive(SPI_HandleTypeDef *hspi, uint8_t *pData, uint16_t Size, uint32_t Timeout)
1043 {
1044 uint32_t tickstart;
1045 HAL_StatusTypeDef errorcode = HAL_OK;
1046 #if defined (__GNUC__)
1047 __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->RXDR));
1048 #endif /* __GNUC__ */
1049
1050 /* Check Direction parameter */
1051 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_RXONLY(hspi->Init.Direction));
1052
1053 /* Lock the process */
1054 __HAL_LOCK(hspi);
1055
1056 /* Init tickstart for timeout management*/
1057 tickstart = HAL_GetTick();
1058
1059 if (hspi->State != HAL_SPI_STATE_READY)
1060 {
1061 errorcode = HAL_BUSY;
1062 __HAL_UNLOCK(hspi);
1063 return errorcode;
1064 }
1065
1066 if ((pData == NULL) || (Size == 0UL))
1067 {
1068 errorcode = HAL_ERROR;
1069 __HAL_UNLOCK(hspi);
1070 return errorcode;
1071 }
1072
1073 /* Set the transaction information */
1074 hspi->State = HAL_SPI_STATE_BUSY_RX;
1075 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1076 hspi->pRxBuffPtr = (uint8_t *)pData;
1077 hspi->RxXferSize = Size;
1078 hspi->RxXferCount = Size;
1079
1080 /*Init field not used in handle to zero */
1081 hspi->pTxBuffPtr = NULL;
1082 hspi->TxXferSize = (uint16_t) 0UL;
1083 hspi->TxXferCount = (uint16_t) 0UL;
1084 hspi->RxISR = NULL;
1085 hspi->TxISR = NULL;
1086
1087 /* Configure communication direction: 1Line */
1088 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
1089 {
1090 SPI_1LINE_RX(hspi);
1091 }
1092 else
1093 {
1094 SPI_2LINES_RX(hspi);
1095 }
1096
1097 /* Set the number of data at current transfer */
1098 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
1099
1100 /* Enable SPI peripheral */
1101 __HAL_SPI_ENABLE(hspi);
1102
1103 if (hspi->Init.Mode == SPI_MODE_MASTER)
1104 {
1105 /* Master transfer start */
1106 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
1107 }
1108
1109 /* Receive data in 32 Bit mode */
1110 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1111 {
1112 /* Transfer loop */
1113 while (hspi->RxXferCount > 0UL)
1114 {
1115 /* Check the RXWNE/EOT flag */
1116 if ((hspi->Instance->SR & (SPI_FLAG_RXWNE | SPI_FLAG_EOT)) != 0UL)
1117 {
1118 *((uint32_t *)hspi->pRxBuffPtr) = *((__IO uint32_t *)&hspi->Instance->RXDR);
1119 hspi->pRxBuffPtr += sizeof(uint32_t);
1120 hspi->RxXferCount--;
1121 }
1122 else
1123 {
1124 /* Timeout management */
1125 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1126 {
1127 /* Call standard close procedure with error check */
1128 SPI_CloseTransfer(hspi);
1129
1130 /* Unlock the process */
1131 __HAL_UNLOCK(hspi);
1132
1133 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1134 hspi->State = HAL_SPI_STATE_READY;
1135 return HAL_TIMEOUT;
1136 }
1137 }
1138 }
1139 }
1140 /* Receive data in 16 Bit mode */
1141 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1142 {
1143 /* Transfer loop */
1144 while (hspi->RxXferCount > 0UL)
1145 {
1146 /* Check the RXP flag */
1147 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_RXP))
1148 {
1149 #if defined (__GNUC__)
1150 *((uint16_t *)hspi->pRxBuffPtr) = *prxdr_16bits;
1151 #else
1152 *((uint16_t *)hspi->pRxBuffPtr) = *((__IO uint16_t *)&hspi->Instance->RXDR);
1153 #endif /* __GNUC__ */
1154 hspi->pRxBuffPtr += sizeof(uint16_t);
1155 hspi->RxXferCount--;
1156 }
1157 else
1158 {
1159 /* Timeout management */
1160 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1161 {
1162 /* Call standard close procedure with error check */
1163 SPI_CloseTransfer(hspi);
1164
1165 /* Unlock the process */
1166 __HAL_UNLOCK(hspi);
1167
1168 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1169 hspi->State = HAL_SPI_STATE_READY;
1170 return HAL_TIMEOUT;
1171 }
1172 }
1173 }
1174 }
1175 /* Receive data in 8 Bit mode */
1176 else
1177 {
1178 /* Transfer loop */
1179 while (hspi->RxXferCount > 0UL)
1180 {
1181 /* Check the RXP flag */
1182 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_RXP))
1183 {
1184 *((uint8_t *)hspi->pRxBuffPtr) = *((__IO uint8_t *)&hspi->Instance->RXDR);
1185 hspi->pRxBuffPtr += sizeof(uint8_t);
1186 hspi->RxXferCount--;
1187 }
1188 else
1189 {
1190 /* Timeout management */
1191 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1192 {
1193 /* Call standard close procedure with error check */
1194 SPI_CloseTransfer(hspi);
1195
1196 /* Unlock the process */
1197 __HAL_UNLOCK(hspi);
1198
1199 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1200 hspi->State = HAL_SPI_STATE_READY;
1201 return HAL_TIMEOUT;
1202 }
1203 }
1204 }
1205 }
1206
1207 #if (USE_SPI_CRC != 0UL)
1208 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE)
1209 {
1210 /* Wait for crc data to be received */
1211 if (SPI_WaitOnFlagUntilTimeout(hspi, SPI_FLAG_EOT, RESET, tickstart, Timeout) != HAL_OK)
1212 {
1213 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FLAG);
1214 }
1215 }
1216 #endif /* USE_SPI_CRC */
1217
1218 /* Call standard close procedure with error check */
1219 SPI_CloseTransfer(hspi);
1220
1221 /* Unlock the process */
1222 __HAL_UNLOCK(hspi);
1223
1224 hspi->State = HAL_SPI_STATE_READY;
1225
1226 if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
1227 {
1228 return HAL_ERROR;
1229 }
1230 return errorcode;
1231 }
1232
1233 /**
1234 * @brief Transmit and Receive an amount of data in blocking mode.
1235 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1236 * the configuration information for SPI module.
1237 * @param pTxData: pointer to transmission data buffer
1238 * @param pRxData: pointer to reception data buffer
1239 * @param Size : amount of data to be sent and received
1240 * @param Timeout: Timeout duration
1241 * @retval HAL status
1242 */
HAL_SPI_TransmitReceive(SPI_HandleTypeDef * hspi,const uint8_t * pTxData,uint8_t * pRxData,uint16_t Size,uint32_t Timeout)1243 HAL_StatusTypeDef HAL_SPI_TransmitReceive(SPI_HandleTypeDef *hspi, const uint8_t *pTxData, uint8_t *pRxData,
1244 uint16_t Size, uint32_t Timeout)
1245 {
1246 HAL_StatusTypeDef errorcode = HAL_OK;
1247 #if defined (__GNUC__)
1248 __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->TXDR));
1249 __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->RXDR));
1250 #endif /* __GNUC__ */
1251
1252 uint32_t tickstart;
1253 uint16_t initial_TxXferCount;
1254 uint16_t initial_RxXferCount;
1255
1256 /* Check Direction parameter */
1257 assert_param(IS_SPI_DIRECTION_2LINES(hspi->Init.Direction));
1258
1259 /* Lock the process */
1260 __HAL_LOCK(hspi);
1261
1262 /* Init tickstart for timeout management*/
1263 tickstart = HAL_GetTick();
1264
1265 initial_TxXferCount = Size;
1266 initial_RxXferCount = Size;
1267
1268 if (hspi->State != HAL_SPI_STATE_READY)
1269 {
1270 errorcode = HAL_BUSY;
1271 __HAL_UNLOCK(hspi);
1272 return errorcode;
1273 }
1274
1275 if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0UL))
1276 {
1277 errorcode = HAL_ERROR;
1278 __HAL_UNLOCK(hspi);
1279 return errorcode;
1280 }
1281
1282 /* Set the transaction information */
1283 hspi->State = HAL_SPI_STATE_BUSY_TX_RX;
1284 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1285 hspi->pRxBuffPtr = (uint8_t *)pRxData;
1286 hspi->RxXferCount = Size;
1287 hspi->RxXferSize = Size;
1288 hspi->pTxBuffPtr = (const uint8_t *)pTxData;
1289 hspi->TxXferCount = Size;
1290 hspi->TxXferSize = Size;
1291
1292 /*Init field not used in handle to zero */
1293 hspi->RxISR = NULL;
1294 hspi->TxISR = NULL;
1295
1296 /* Set Full-Duplex mode */
1297 SPI_2LINES(hspi);
1298
1299 /* Set the number of data at current transfer */
1300 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
1301
1302 __HAL_SPI_ENABLE(hspi);
1303
1304 if (hspi->Init.Mode == SPI_MODE_MASTER)
1305 {
1306 /* Master transfer start */
1307 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
1308 }
1309
1310 /* Transmit and Receive data in 32 Bit mode */
1311 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1312 {
1313 while ((initial_TxXferCount > 0UL) || (initial_RxXferCount > 0UL))
1314 {
1315 /* Check TXP flag */
1316 if ((__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP)) && (initial_TxXferCount > 0UL))
1317 {
1318 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
1319 hspi->pTxBuffPtr += sizeof(uint32_t);
1320 hspi->TxXferCount --;
1321 initial_TxXferCount = hspi->TxXferCount;
1322 }
1323
1324 /* Check RXWNE/EOT flag */
1325 if (((hspi->Instance->SR & (SPI_FLAG_RXWNE | SPI_FLAG_EOT)) != 0UL) && (initial_RxXferCount > 0UL))
1326 {
1327 *((uint32_t *)hspi->pRxBuffPtr) = *((__IO uint32_t *)&hspi->Instance->RXDR);
1328 hspi->pRxBuffPtr += sizeof(uint32_t);
1329 hspi->RxXferCount --;
1330 initial_RxXferCount = hspi->RxXferCount;
1331 }
1332
1333 /* Timeout management */
1334 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1335 {
1336 /* Call standard close procedure with error check */
1337 SPI_CloseTransfer(hspi);
1338
1339 /* Unlock the process */
1340 __HAL_UNLOCK(hspi);
1341
1342 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1343 hspi->State = HAL_SPI_STATE_READY;
1344 return HAL_TIMEOUT;
1345 }
1346 }
1347 }
1348 /* Transmit and Receive data in 16 Bit mode */
1349 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1350 {
1351 while ((initial_TxXferCount > 0UL) || (initial_RxXferCount > 0UL))
1352 {
1353 /* Check the TXP flag */
1354 if (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP) && (initial_TxXferCount > 0UL))
1355 {
1356 #if defined (__GNUC__)
1357 *ptxdr_16bits = *((const uint16_t *)hspi->pTxBuffPtr);
1358 #else
1359 *((__IO uint16_t *)&hspi->Instance->TXDR) = *((const uint16_t *)hspi->pTxBuffPtr);
1360 #endif /* __GNUC__ */
1361 hspi->pTxBuffPtr += sizeof(uint16_t);
1362 hspi->TxXferCount--;
1363 initial_TxXferCount = hspi->TxXferCount;
1364 }
1365
1366 /* Check the RXP flag */
1367 if ((__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_RXP)) && (initial_RxXferCount > 0UL))
1368 {
1369 #if defined (__GNUC__)
1370 *((uint16_t *)hspi->pRxBuffPtr) = *prxdr_16bits;
1371 #else
1372 *((uint16_t *)hspi->pRxBuffPtr) = *((__IO uint16_t *)&hspi->Instance->RXDR);
1373 #endif /* __GNUC__ */
1374 hspi->pRxBuffPtr += sizeof(uint16_t);
1375 hspi->RxXferCount--;
1376 initial_RxXferCount = hspi->RxXferCount;
1377 }
1378
1379 /* Timeout management */
1380 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1381 {
1382 /* Call standard close procedure with error check */
1383 SPI_CloseTransfer(hspi);
1384
1385 /* Unlock the process */
1386 __HAL_UNLOCK(hspi);
1387
1388 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1389 hspi->State = HAL_SPI_STATE_READY;
1390 return HAL_TIMEOUT;
1391 }
1392 }
1393 }
1394 /* Transmit and Receive data in 8 Bit mode */
1395 else
1396 {
1397 while ((initial_TxXferCount > 0UL) || (initial_RxXferCount > 0UL))
1398 {
1399 /* Check the TXP flag */
1400 if ((__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP)) && (initial_TxXferCount > 0UL))
1401 {
1402 *((__IO uint8_t *)&hspi->Instance->TXDR) = *((const uint8_t *)hspi->pTxBuffPtr);
1403 hspi->pTxBuffPtr += sizeof(uint8_t);
1404 hspi->TxXferCount--;
1405 initial_TxXferCount = hspi->TxXferCount;
1406 }
1407
1408 /* Check the RXP flag */
1409 if ((__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_RXP)) && (initial_RxXferCount > 0UL))
1410 {
1411 *((uint8_t *)hspi->pRxBuffPtr) = *((__IO uint8_t *)&hspi->Instance->RXDR);
1412 hspi->pRxBuffPtr += sizeof(uint8_t);
1413 hspi->RxXferCount--;
1414 initial_RxXferCount = hspi->RxXferCount;
1415 }
1416
1417 /* Timeout management */
1418 if ((((HAL_GetTick() - tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
1419 {
1420 /* Call standard close procedure with error check */
1421 SPI_CloseTransfer(hspi);
1422
1423 /* Unlock the process */
1424 __HAL_UNLOCK(hspi);
1425
1426 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_TIMEOUT);
1427 hspi->State = HAL_SPI_STATE_READY;
1428 return HAL_TIMEOUT;
1429 }
1430 }
1431 }
1432
1433 /* Wait for Tx/Rx (and CRC) data to be sent/received */
1434 if (SPI_WaitOnFlagUntilTimeout(hspi, SPI_FLAG_EOT, RESET, tickstart, Timeout) != HAL_OK)
1435 {
1436 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FLAG);
1437 }
1438
1439 /* Call standard close procedure with error check */
1440 SPI_CloseTransfer(hspi);
1441
1442 /* Unlock the process */
1443 __HAL_UNLOCK(hspi);
1444
1445 hspi->State = HAL_SPI_STATE_READY;
1446
1447 if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
1448 {
1449 return HAL_ERROR;
1450 }
1451 return errorcode;
1452 }
1453
1454 /**
1455 * @brief Transmit an amount of data in non-blocking mode with Interrupt.
1456 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1457 * the configuration information for SPI module.
1458 * @param pData: pointer to data buffer
1459 * @param Size : amount of data to be sent
1460 * @retval HAL status
1461 */
HAL_SPI_Transmit_IT(SPI_HandleTypeDef * hspi,const uint8_t * pData,uint16_t Size)1462 HAL_StatusTypeDef HAL_SPI_Transmit_IT(SPI_HandleTypeDef *hspi, const uint8_t *pData, uint16_t Size)
1463 {
1464 HAL_StatusTypeDef errorcode = HAL_OK;
1465
1466 /* Check Direction parameter */
1467 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_TXONLY(hspi->Init.Direction));
1468
1469 /* Lock the process */
1470 __HAL_LOCK(hspi);
1471
1472 if ((pData == NULL) || (Size == 0UL))
1473 {
1474 errorcode = HAL_ERROR;
1475 __HAL_UNLOCK(hspi);
1476 return errorcode;
1477 }
1478
1479 if (hspi->State != HAL_SPI_STATE_READY)
1480 {
1481 errorcode = HAL_BUSY;
1482 __HAL_UNLOCK(hspi);
1483 return errorcode;
1484 }
1485
1486 /* Set the transaction information */
1487 hspi->State = HAL_SPI_STATE_BUSY_TX;
1488 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1489 hspi->pTxBuffPtr = (const uint8_t *)pData;
1490 hspi->TxXferSize = Size;
1491 hspi->TxXferCount = Size;
1492
1493 /* Init field not used in handle to zero */
1494 hspi->pRxBuffPtr = NULL;
1495 hspi->RxXferSize = (uint16_t) 0UL;
1496 hspi->RxXferCount = (uint16_t) 0UL;
1497 hspi->RxISR = NULL;
1498
1499 /* Set the function for IT treatment */
1500 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1501 {
1502 hspi->TxISR = SPI_TxISR_32BIT;
1503 }
1504 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1505 {
1506 hspi->TxISR = SPI_TxISR_16BIT;
1507 }
1508 else
1509 {
1510 hspi->TxISR = SPI_TxISR_8BIT;
1511 }
1512
1513 /* Configure communication direction : 1Line */
1514 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
1515 {
1516 SPI_1LINE_TX(hspi);
1517 }
1518 else
1519 {
1520 SPI_2LINES_TX(hspi);
1521 }
1522
1523 /* Set the number of data at current transfer */
1524 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
1525
1526 /* Enable SPI peripheral */
1527 __HAL_SPI_ENABLE(hspi);
1528
1529 /* Enable EOT, TXP, FRE, MODF, UDR and TSERF interrupts */
1530 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_TXP | SPI_IT_UDR | SPI_IT_FRE | SPI_IT_MODF | SPI_IT_TSERF));
1531
1532 if (hspi->Init.Mode == SPI_MODE_MASTER)
1533 {
1534 /* Master transfer start */
1535 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
1536 }
1537
1538 __HAL_UNLOCK(hspi);
1539 return errorcode;
1540 }
1541
1542 /**
1543 * @brief Receive an amount of data in non-blocking mode with Interrupt.
1544 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1545 * the configuration information for SPI module.
1546 * @param pData: pointer to data buffer
1547 * @param Size : amount of data to be sent
1548 * @retval HAL status
1549 */
HAL_SPI_Receive_IT(SPI_HandleTypeDef * hspi,uint8_t * pData,uint16_t Size)1550 HAL_StatusTypeDef HAL_SPI_Receive_IT(SPI_HandleTypeDef *hspi, uint8_t *pData, uint16_t Size)
1551 {
1552 HAL_StatusTypeDef errorcode = HAL_OK;
1553
1554 /* Check Direction parameter */
1555 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_RXONLY(hspi->Init.Direction));
1556
1557 /* Lock the process */
1558 __HAL_LOCK(hspi);
1559
1560 if (hspi->State != HAL_SPI_STATE_READY)
1561 {
1562 errorcode = HAL_BUSY;
1563 __HAL_UNLOCK(hspi);
1564 return errorcode;
1565 }
1566
1567 if ((pData == NULL) || (Size == 0UL))
1568 {
1569 errorcode = HAL_ERROR;
1570 __HAL_UNLOCK(hspi);
1571 return errorcode;
1572 }
1573
1574 /* Set the transaction information */
1575 hspi->State = HAL_SPI_STATE_BUSY_RX;
1576 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1577 hspi->pRxBuffPtr = (uint8_t *)pData;
1578 hspi->RxXferSize = Size;
1579 hspi->RxXferCount = Size;
1580
1581 /* Init field not used in handle to zero */
1582 hspi->pTxBuffPtr = NULL;
1583 hspi->TxXferSize = (uint16_t) 0UL;
1584 hspi->TxXferCount = (uint16_t) 0UL;
1585 hspi->TxISR = NULL;
1586
1587 /* Set the function for IT treatment */
1588 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1589 {
1590 hspi->RxISR = SPI_RxISR_32BIT;
1591 }
1592 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1593 {
1594 hspi->RxISR = SPI_RxISR_16BIT;
1595 }
1596 else
1597 {
1598 hspi->RxISR = SPI_RxISR_8BIT;
1599 }
1600
1601 /* Configure communication direction : 1Line */
1602 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
1603 {
1604 SPI_1LINE_RX(hspi);
1605 }
1606 else
1607 {
1608 SPI_2LINES_RX(hspi);
1609 }
1610
1611 /* Note : The SPI must be enabled after unlocking current process
1612 to avoid the risk of SPI interrupt handle execution before current
1613 process unlock */
1614
1615 /* Set the number of data at current transfer */
1616 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
1617
1618 /* Enable SPI peripheral */
1619 __HAL_SPI_ENABLE(hspi);
1620
1621 /* Enable EOT, RXP, OVR, FRE, MODF and TSERF interrupts */
1622 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_RXP | SPI_IT_OVR | SPI_IT_FRE | SPI_IT_MODF | SPI_IT_TSERF));
1623
1624 if (hspi->Init.Mode == SPI_MODE_MASTER)
1625 {
1626 /* Master transfer start */
1627 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
1628 }
1629
1630 /* Unlock the process */
1631 __HAL_UNLOCK(hspi);
1632 return errorcode;
1633 }
1634
1635 /**
1636 * @brief Transmit and Receive an amount of data in non-blocking mode with Interrupt.
1637 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1638 * the configuration information for SPI module.
1639 * @param pTxData: pointer to transmission data buffer
1640 * @param pRxData: pointer to reception data buffer
1641 * @param Size : amount of data to be sent and received
1642 * @retval HAL status
1643 */
HAL_SPI_TransmitReceive_IT(SPI_HandleTypeDef * hspi,const uint8_t * pTxData,uint8_t * pRxData,uint16_t Size)1644 HAL_StatusTypeDef HAL_SPI_TransmitReceive_IT(SPI_HandleTypeDef *hspi, const uint8_t *pTxData, uint8_t *pRxData,
1645 uint16_t Size)
1646 {
1647 HAL_StatusTypeDef errorcode = HAL_OK;
1648 uint32_t tmp_TxXferCount;
1649
1650 #if defined (__GNUC__)
1651 __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->TXDR));
1652 #endif /* __GNUC__ */
1653
1654 /* Check Direction parameter */
1655 assert_param(IS_SPI_DIRECTION_2LINES(hspi->Init.Direction));
1656
1657 /* Lock the process */
1658 __HAL_LOCK(hspi);
1659
1660 if (hspi->State != HAL_SPI_STATE_READY)
1661 {
1662 errorcode = HAL_BUSY;
1663 __HAL_UNLOCK(hspi);
1664 return errorcode;
1665 }
1666
1667 if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0UL))
1668 {
1669 errorcode = HAL_ERROR;
1670 __HAL_UNLOCK(hspi);
1671 return errorcode;
1672 }
1673
1674 /* Set the transaction information */
1675 hspi->State = HAL_SPI_STATE_BUSY_TX_RX;
1676 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1677 hspi->pTxBuffPtr = (const uint8_t *)pTxData;
1678 hspi->TxXferSize = Size;
1679 hspi->TxXferCount = Size;
1680 hspi->pRxBuffPtr = (uint8_t *)pRxData;
1681 hspi->RxXferSize = Size;
1682 hspi->RxXferCount = Size;
1683 tmp_TxXferCount = hspi->TxXferCount;
1684
1685 /* Set the function for IT treatment */
1686 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1687 {
1688 hspi->TxISR = SPI_TxISR_32BIT;
1689 hspi->RxISR = SPI_RxISR_32BIT;
1690 }
1691 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1692 {
1693 hspi->RxISR = SPI_RxISR_16BIT;
1694 hspi->TxISR = SPI_TxISR_16BIT;
1695 }
1696 else
1697 {
1698 hspi->RxISR = SPI_RxISR_8BIT;
1699 hspi->TxISR = SPI_TxISR_8BIT;
1700 }
1701
1702 /* Set Full-Duplex mode */
1703 SPI_2LINES(hspi);
1704
1705 /* Set the number of data at current transfer */
1706 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
1707
1708 /* Enable SPI peripheral */
1709 __HAL_SPI_ENABLE(hspi);
1710
1711 /* Fill in the TxFIFO */
1712 while ((__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_TXP)) && (tmp_TxXferCount != 0UL))
1713 {
1714 /* Transmit data in 32 Bit mode */
1715 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
1716 {
1717 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
1718 hspi->pTxBuffPtr += sizeof(uint32_t);
1719 hspi->TxXferCount--;
1720 tmp_TxXferCount = hspi->TxXferCount;
1721 }
1722 /* Transmit data in 16 Bit mode */
1723 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
1724 {
1725 #if defined (__GNUC__)
1726 *ptxdr_16bits = *((const uint16_t *)hspi->pTxBuffPtr);
1727 #else
1728 *((__IO uint16_t *)&hspi->Instance->TXDR) = *((const uint16_t *)hspi->pTxBuffPtr);
1729 #endif /* __GNUC__ */
1730 hspi->pTxBuffPtr += sizeof(uint16_t);
1731 hspi->TxXferCount--;
1732 tmp_TxXferCount = hspi->TxXferCount;
1733 }
1734 /* Transmit data in 8 Bit mode */
1735 else
1736 {
1737 *((__IO uint8_t *)&hspi->Instance->TXDR) = *((const uint8_t *)hspi->pTxBuffPtr);
1738 hspi->pTxBuffPtr += sizeof(uint8_t);
1739 hspi->TxXferCount--;
1740 tmp_TxXferCount = hspi->TxXferCount;
1741 }
1742 }
1743
1744 /* Enable EOT, DXP, UDR, OVR, FRE, MODF and TSERF interrupts */
1745 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_DXP | SPI_IT_UDR | SPI_IT_OVR |
1746 SPI_IT_FRE | SPI_IT_MODF | SPI_IT_TSERF));
1747
1748 if (hspi->Init.Mode == SPI_MODE_MASTER)
1749 {
1750 /* Start Master transfer */
1751 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
1752 }
1753
1754 /* Unlock the process */
1755 __HAL_UNLOCK(hspi);
1756 return errorcode;
1757 }
1758
1759 #if defined(USE_SPI_RELOAD_TRANSFER)
1760 /**
1761 * @brief Transmit an additional amount of data in blocking mode.
1762 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1763 * the configuration information for SPI module.
1764 * @param pData: pointer to data buffer
1765 * @param Size : amount of data to be sent
1766 * @retval HAL status
1767 */
HAL_SPI_Reload_Transmit_IT(SPI_HandleTypeDef * hspi,const uint8_t * pData,uint16_t Size)1768 HAL_StatusTypeDef HAL_SPI_Reload_Transmit_IT(SPI_HandleTypeDef *hspi, const uint8_t *pData, uint16_t Size)
1769 {
1770 HAL_StatusTypeDef errorcode = HAL_OK;
1771 HAL_SPI_StateTypeDef tmp_state;
1772
1773 /* Lock the process */
1774 __HAL_LOCK(hspi);
1775
1776 if ((pData == NULL) || (Size == 0UL))
1777 {
1778 errorcode = HAL_ERROR;
1779 __HAL_UNLOCK(hspi);
1780 return errorcode;
1781 }
1782
1783 if (hspi->State == HAL_SPI_STATE_BUSY_TX)
1784 {
1785 /* check if there is already a request to reload */
1786 if (hspi->Reload.Requested == 1UL)
1787 {
1788 errorcode = HAL_ERROR;
1789 __HAL_UNLOCK(hspi);
1790 return errorcode;
1791 }
1792
1793 /* Insert the new number of data to be sent just after the current one */
1794 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, (Size & 0xFFFFFFFFUL) << 16UL);
1795
1796 /* Set the transaction information */
1797 hspi->Reload.Requested = 1UL;
1798 hspi->Reload.pTxBuffPtr = (const uint8_t *)pData;
1799 hspi->Reload.TxXferSize = Size;
1800
1801 tmp_state = hspi->State;
1802
1803 /* Check if the current transmit is already completed */
1804 if (((hspi->Instance->CR2 & SPI_CR2_TSER) != 0UL) && (tmp_state == HAL_SPI_STATE_READY))
1805 {
1806 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TSERF);
1807 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, 0UL);
1808 hspi->Reload.Requested = 0UL;
1809 errorcode = HAL_ERROR;
1810 __HAL_UNLOCK(hspi);
1811 return errorcode;
1812 }
1813 }
1814 else
1815 {
1816 errorcode = HAL_ERROR;
1817 return errorcode;
1818 }
1819
1820 __HAL_UNLOCK(hspi);
1821 return errorcode;
1822 }
1823 #endif /* USE_SPI_RELOAD_TRANSFER */
1824
1825 #if defined(USE_SPI_RELOAD_TRANSFER)
1826 /**
1827 * @brief Receive an additional amount of data in blocking mode.
1828 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1829 * the configuration information for SPI module.
1830 * @param pData: pointer to data buffer
1831 * @param Size : amount of data to be sent
1832 * @retval HAL status
1833 */
HAL_SPI_Reload_Receive_IT(SPI_HandleTypeDef * hspi,uint8_t * pData,uint16_t Size)1834 HAL_StatusTypeDef HAL_SPI_Reload_Receive_IT(SPI_HandleTypeDef *hspi, uint8_t *pData, uint16_t Size)
1835 {
1836 HAL_StatusTypeDef errorcode = HAL_OK;
1837 HAL_SPI_StateTypeDef tmp_state;
1838
1839 /* Lock the process */
1840 __HAL_LOCK(hspi);
1841
1842 if ((pData == NULL) || (Size == 0UL))
1843 {
1844 errorcode = HAL_ERROR;
1845 __HAL_UNLOCK(hspi);
1846 return errorcode;
1847 }
1848
1849 if (hspi->State == HAL_SPI_STATE_BUSY_RX)
1850 {
1851 /* check if there is already a request to reload */
1852 if (hspi->Reload.Requested == 1UL)
1853 {
1854 errorcode = HAL_ERROR;
1855 __HAL_UNLOCK(hspi);
1856 return errorcode;
1857 }
1858
1859 /* Insert the new number of data that will be received just after the current one */
1860 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, (Size & 0xFFFFFFFFUL) << 16UL);
1861
1862 /* Set the transaction information */
1863 hspi->Reload.Requested = 1UL;
1864 hspi->Reload.pRxBuffPtr = (uint8_t *)pData;
1865 hspi->Reload.RxXferSize = Size;
1866
1867 tmp_state = hspi->State;
1868
1869 /* Check if the current reception is already completed */
1870 if (((hspi->Instance->CR2 & SPI_CR2_TSER) != 0UL) && (tmp_state == HAL_SPI_STATE_READY))
1871 {
1872 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TSERF);
1873 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, 0UL);
1874 hspi->Reload.Requested = 0UL;
1875 errorcode = HAL_ERROR;
1876 __HAL_UNLOCK(hspi);
1877 return errorcode;
1878 }
1879 }
1880 else
1881 {
1882 errorcode = HAL_ERROR;
1883 return errorcode;
1884 }
1885
1886 __HAL_UNLOCK(hspi);
1887 return errorcode;
1888 }
1889 #endif /* USE_SPI_RELOAD_TRANSFER */
1890
1891 #if defined(USE_SPI_RELOAD_TRANSFER)
1892 /**
1893 * @brief Transmit and receive an additional amount of data in blocking mode.
1894 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1895 * the configuration information for SPI module.
1896 * @param pTxData: pointer to transmission data buffer
1897 * @param pRxData: pointer to reception data buffer
1898 * @param Size : amount of data to be sent and received
1899 * @retval HAL status
1900 */
HAL_SPI_Reload_TransmitReceive_IT(SPI_HandleTypeDef * hspi,const uint8_t * pTxData,uint8_t * pRxData,uint16_t Size)1901 HAL_StatusTypeDef HAL_SPI_Reload_TransmitReceive_IT(SPI_HandleTypeDef *hspi, const uint8_t *pTxData,
1902 uint8_t *pRxData, uint16_t Size)
1903 {
1904 HAL_StatusTypeDef errorcode = HAL_OK;
1905 HAL_SPI_StateTypeDef tmp_state;
1906
1907 /* Lock the process */
1908 __HAL_LOCK(hspi);
1909
1910 if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0UL))
1911 {
1912 errorcode = HAL_ERROR;
1913 __HAL_UNLOCK(hspi);
1914 return errorcode;
1915 }
1916
1917 if (hspi->State == HAL_SPI_STATE_BUSY_TX_RX)
1918 {
1919 /* check if there is already a request to reload */
1920 if (hspi->Reload.Requested == 1UL)
1921 {
1922 errorcode = HAL_ERROR;
1923 __HAL_UNLOCK(hspi);
1924 return errorcode;
1925 }
1926
1927 /* Insert the new number of data that will be sent and received just after the current one */
1928 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, (Size & 0xFFFFFFFFUL) << 16UL);
1929
1930 /* Set the transaction information */
1931 hspi->Reload.Requested = 1UL;
1932 hspi->Reload.pTxBuffPtr = (const uint8_t *)pTxData;
1933 hspi->Reload.TxXferSize = Size;
1934 hspi->Reload.pRxBuffPtr = (uint8_t *)pRxData;
1935 hspi->Reload.RxXferSize = Size;
1936
1937 tmp_state = hspi->State;
1938
1939 /* Check if the current transmit is already completed */
1940 if (((hspi->Instance->CR2 & SPI_CR2_TSER) != 0UL) && (tmp_state == HAL_SPI_STATE_READY))
1941 {
1942 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TSERF);
1943 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSER, 0UL);
1944 hspi->Reload.Requested = 0UL;
1945 errorcode = HAL_ERROR;
1946 __HAL_UNLOCK(hspi);
1947 return errorcode;
1948 }
1949 }
1950 else
1951 {
1952 errorcode = HAL_ERROR;
1953 return errorcode;
1954 }
1955
1956 __HAL_UNLOCK(hspi);
1957 return errorcode;
1958 }
1959 #endif /* USE_SPI_RELOAD_TRANSFER */
1960
1961 /**
1962 * @brief Transmit an amount of data in non-blocking mode with DMA.
1963 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
1964 * the configuration information for SPI module.
1965 * @param pData: pointer to data buffer
1966 * @param Size : amount of data to be sent
1967 * @retval HAL status
1968 */
HAL_SPI_Transmit_DMA(SPI_HandleTypeDef * hspi,const uint8_t * pData,uint16_t Size)1969 HAL_StatusTypeDef HAL_SPI_Transmit_DMA(SPI_HandleTypeDef *hspi, const uint8_t *pData, uint16_t Size)
1970 {
1971 HAL_StatusTypeDef errorcode = HAL_OK;
1972
1973 /* Check Direction parameter */
1974 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_TXONLY(hspi->Init.Direction));
1975
1976 /* Lock the process */
1977 __HAL_LOCK(hspi);
1978
1979 if (hspi->State != HAL_SPI_STATE_READY)
1980 {
1981 errorcode = HAL_BUSY;
1982 __HAL_UNLOCK(hspi);
1983 return errorcode;
1984 }
1985
1986 if ((pData == NULL) || (Size == 0UL))
1987 {
1988 errorcode = HAL_ERROR;
1989 __HAL_UNLOCK(hspi);
1990 return errorcode;
1991 }
1992
1993 /* Set the transaction information */
1994 hspi->State = HAL_SPI_STATE_BUSY_TX;
1995 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
1996 hspi->pTxBuffPtr = (const uint8_t *)pData;
1997 hspi->TxXferSize = Size;
1998 hspi->TxXferCount = Size;
1999
2000 /* Init field not used in handle to zero */
2001 hspi->pRxBuffPtr = NULL;
2002 hspi->TxISR = NULL;
2003 hspi->RxISR = NULL;
2004 hspi->RxXferSize = (uint16_t)0UL;
2005 hspi->RxXferCount = (uint16_t)0UL;
2006
2007 /* Configure communication direction : 1Line */
2008 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
2009 {
2010 SPI_1LINE_TX(hspi);
2011 }
2012 else
2013 {
2014 SPI_2LINES_TX(hspi);
2015 }
2016
2017 /* Packing mode management is enabled by the DMA settings */
2018 if (((hspi->Init.DataSize > SPI_DATASIZE_16BIT) && (hspi->hdmatx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD)) || \
2019 ((hspi->Init.DataSize > SPI_DATASIZE_8BIT) && ((hspi->hdmatx->Init.MemDataAlignment != DMA_MDATAALIGN_HALFWORD) && \
2020 (hspi->hdmatx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD))))
2021 {
2022 /* Restriction the DMA data received is not allowed in this mode */
2023 errorcode = HAL_ERROR;
2024 __HAL_UNLOCK(hspi);
2025 return errorcode;
2026 }
2027
2028 /* Adjust XferCount according to DMA alignment / Data size */
2029 if (hspi->Init.DataSize <= SPI_DATASIZE_8BIT)
2030 {
2031 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_HALFWORD)
2032 {
2033 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 1UL) >> 1UL;
2034 }
2035 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2036 {
2037 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 3UL) >> 2UL;
2038 }
2039 }
2040 else if (hspi->Init.DataSize <= SPI_DATASIZE_16BIT)
2041 {
2042 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2043 {
2044 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 1UL) >> 1UL;
2045 }
2046 }
2047 else
2048 {
2049 /* Adjustment done */
2050 }
2051
2052 /* Set the SPI TxDMA Half transfer complete callback */
2053 hspi->hdmatx->XferHalfCpltCallback = SPI_DMAHalfTransmitCplt;
2054
2055 /* Set the SPI TxDMA transfer complete callback */
2056 hspi->hdmatx->XferCpltCallback = SPI_DMATransmitCplt;
2057
2058 /* Set the DMA error callback */
2059 hspi->hdmatx->XferErrorCallback = SPI_DMAError;
2060
2061 /* Set the DMA AbortCpltCallback */
2062 hspi->hdmatx->XferAbortCallback = NULL;
2063
2064 /* Clear TXDMAEN bit*/
2065 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN);
2066
2067 /* Enable the Tx DMA Stream/Channel */
2068 if (HAL_OK != HAL_DMA_Start_IT(hspi->hdmatx, (uint32_t)hspi->pTxBuffPtr, (uint32_t)&hspi->Instance->TXDR,
2069 hspi->TxXferCount))
2070 {
2071 /* Update SPI error code */
2072 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_DMA);
2073
2074 /* Unlock the process */
2075 __HAL_UNLOCK(hspi);
2076
2077 hspi->State = HAL_SPI_STATE_READY;
2078 errorcode = HAL_ERROR;
2079 return errorcode;
2080 }
2081
2082 /* Set the number of data at current transfer */
2083 if (hspi->hdmatx->Init.Mode == DMA_CIRCULAR)
2084 {
2085 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, 0UL);
2086 }
2087 else
2088 {
2089 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
2090 }
2091
2092 /* Enable Tx DMA Request */
2093 SET_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN);
2094
2095 /* Enable the SPI Error Interrupt Bit */
2096 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_UDR | SPI_IT_FRE | SPI_IT_MODF));
2097
2098 /* Enable SPI peripheral */
2099 __HAL_SPI_ENABLE(hspi);
2100
2101 if (hspi->Init.Mode == SPI_MODE_MASTER)
2102 {
2103 /* Master transfer start */
2104 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
2105 }
2106
2107 /* Unlock the process */
2108 __HAL_UNLOCK(hspi);
2109 return errorcode;
2110 }
2111
2112 /**
2113 * @brief Receive an amount of data in non-blocking mode with DMA.
2114 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
2115 * the configuration information for SPI module.
2116 * @param pData: pointer to data buffer
2117 * @param Size : amount of data to be sent
2118 * @note When the CRC feature is enabled the pData Length must be Size + 1.
2119 * @retval HAL status
2120 */
HAL_SPI_Receive_DMA(SPI_HandleTypeDef * hspi,uint8_t * pData,uint16_t Size)2121 HAL_StatusTypeDef HAL_SPI_Receive_DMA(SPI_HandleTypeDef *hspi, uint8_t *pData, uint16_t Size)
2122 {
2123 HAL_StatusTypeDef errorcode = HAL_OK;
2124
2125 /* Check Direction parameter */
2126 assert_param(IS_SPI_DIRECTION_2LINES_OR_1LINE_2LINES_RXONLY(hspi->Init.Direction));
2127
2128 /* Lock the process */
2129 __HAL_LOCK(hspi);
2130
2131 if (hspi->State != HAL_SPI_STATE_READY)
2132 {
2133 errorcode = HAL_BUSY;
2134 __HAL_UNLOCK(hspi);
2135 return errorcode;
2136 }
2137
2138 if ((pData == NULL) || (Size == 0UL))
2139 {
2140 errorcode = HAL_ERROR;
2141 __HAL_UNLOCK(hspi);
2142 return errorcode;
2143 }
2144
2145 /* Set the transaction information */
2146 hspi->State = HAL_SPI_STATE_BUSY_RX;
2147 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
2148 hspi->pRxBuffPtr = (uint8_t *)pData;
2149 hspi->RxXferSize = Size;
2150 hspi->RxXferCount = Size;
2151
2152 /*Init field not used in handle to zero */
2153 hspi->RxISR = NULL;
2154 hspi->TxISR = NULL;
2155 hspi->TxXferSize = (uint16_t) 0UL;
2156 hspi->TxXferCount = (uint16_t) 0UL;
2157
2158 /* Configure communication direction : 1Line */
2159 if (hspi->Init.Direction == SPI_DIRECTION_1LINE)
2160 {
2161 SPI_1LINE_RX(hspi);
2162 }
2163 else
2164 {
2165 SPI_2LINES_RX(hspi);
2166 }
2167
2168 /* Packing mode management is enabled by the DMA settings */
2169 if (((hspi->Init.DataSize > SPI_DATASIZE_16BIT) && (hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD)) || \
2170 ((hspi->Init.DataSize > SPI_DATASIZE_8BIT) && ((hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_HALFWORD) && \
2171 (hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD))))
2172 {
2173 /* Restriction the DMA data received is not allowed in this mode */
2174 errorcode = HAL_ERROR;
2175 __HAL_UNLOCK(hspi);
2176 return errorcode;
2177 }
2178
2179 /* Clear RXDMAEN bit */
2180 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_RXDMAEN);
2181
2182 /* Adjust XferCount according to DMA alignment / Data size */
2183 if (hspi->Init.DataSize <= SPI_DATASIZE_8BIT)
2184 {
2185 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_HALFWORD)
2186 {
2187 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 1UL) >> 1UL;
2188 }
2189 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2190 {
2191 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 3UL) >> 2UL;
2192 }
2193 }
2194 else if (hspi->Init.DataSize <= SPI_DATASIZE_16BIT)
2195 {
2196 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2197 {
2198 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 1UL) >> 1UL;
2199 }
2200 }
2201 else
2202 {
2203 /* Adjustment done */
2204 }
2205
2206 /* Set the SPI RxDMA Half transfer complete callback */
2207 hspi->hdmarx->XferHalfCpltCallback = SPI_DMAHalfReceiveCplt;
2208
2209 /* Set the SPI Rx DMA transfer complete callback */
2210 hspi->hdmarx->XferCpltCallback = SPI_DMAReceiveCplt;
2211
2212 /* Set the DMA error callback */
2213 hspi->hdmarx->XferErrorCallback = SPI_DMAError;
2214
2215 /* Set the DMA AbortCpltCallback */
2216 hspi->hdmarx->XferAbortCallback = NULL;
2217
2218 /* Enable the Rx DMA Stream/Channel */
2219 if (HAL_OK != HAL_DMA_Start_IT(hspi->hdmarx, (uint32_t)&hspi->Instance->RXDR, (uint32_t)hspi->pRxBuffPtr,
2220 hspi->RxXferCount))
2221 {
2222 /* Update SPI error code */
2223 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_DMA);
2224
2225 /* Unlock the process */
2226 __HAL_UNLOCK(hspi);
2227
2228 hspi->State = HAL_SPI_STATE_READY;
2229 errorcode = HAL_ERROR;
2230 return errorcode;
2231 }
2232
2233 /* Set the number of data at current transfer */
2234 if (hspi->hdmarx->Init.Mode == DMA_CIRCULAR)
2235 {
2236 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, 0UL);
2237 }
2238 else
2239 {
2240 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
2241 }
2242
2243 /* Enable Rx DMA Request */
2244 SET_BIT(hspi->Instance->CFG1, SPI_CFG1_RXDMAEN);
2245
2246 /* Enable the SPI Error Interrupt Bit */
2247 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_OVR | SPI_IT_FRE | SPI_IT_MODF));
2248
2249 /* Enable SPI peripheral */
2250 __HAL_SPI_ENABLE(hspi);
2251
2252 if (hspi->Init.Mode == SPI_MODE_MASTER)
2253 {
2254 /* Master transfer start */
2255 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
2256 }
2257
2258 /* Unlock the process */
2259 __HAL_UNLOCK(hspi);
2260 return errorcode;
2261 }
2262
2263 /**
2264 * @brief Transmit and Receive an amount of data in non-blocking mode with DMA.
2265 * @param hspi : pointer to a SPI_HandleTypeDef structure that contains
2266 * the configuration information for SPI module.
2267 * @param pTxData: pointer to transmission data buffer
2268 * @param pRxData: pointer to reception data buffer
2269 * @param Size : amount of data to be sent
2270 * @note When the CRC feature is enabled the pRxData Length must be Size + 1
2271 * @retval HAL status
2272 */
HAL_SPI_TransmitReceive_DMA(SPI_HandleTypeDef * hspi,const uint8_t * pTxData,uint8_t * pRxData,uint16_t Size)2273 HAL_StatusTypeDef HAL_SPI_TransmitReceive_DMA(SPI_HandleTypeDef *hspi, const uint8_t *pTxData, uint8_t *pRxData,
2274 uint16_t Size)
2275 {
2276 HAL_StatusTypeDef errorcode = HAL_OK;
2277
2278 /* Check Direction parameter */
2279 assert_param(IS_SPI_DIRECTION_2LINES(hspi->Init.Direction));
2280
2281 /* Lock the process */
2282 __HAL_LOCK(hspi);
2283
2284 if (hspi->State != HAL_SPI_STATE_READY)
2285 {
2286 errorcode = HAL_BUSY;
2287 __HAL_UNLOCK(hspi);
2288 return errorcode;
2289 }
2290
2291 if ((pTxData == NULL) || (pRxData == NULL) || (Size == 0UL))
2292 {
2293 errorcode = HAL_ERROR;
2294 __HAL_UNLOCK(hspi);
2295 return errorcode;
2296 }
2297
2298 /* Set the transaction information */
2299 hspi->State = HAL_SPI_STATE_BUSY_TX_RX;
2300 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
2301 hspi->pTxBuffPtr = (const uint8_t *)pTxData;
2302 hspi->TxXferSize = Size;
2303 hspi->TxXferCount = Size;
2304 hspi->pRxBuffPtr = (uint8_t *)pRxData;
2305 hspi->RxXferSize = Size;
2306 hspi->RxXferCount = Size;
2307
2308 /* Init field not used in handle to zero */
2309 hspi->RxISR = NULL;
2310 hspi->TxISR = NULL;
2311
2312 /* Set Full-Duplex mode */
2313 SPI_2LINES(hspi);
2314
2315 /* Reset the Tx/Rx DMA bits */
2316 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
2317
2318 /* Packing mode management is enabled by the DMA settings */
2319 if (((hspi->Init.DataSize > SPI_DATASIZE_16BIT) && (hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD)) || \
2320 ((hspi->Init.DataSize > SPI_DATASIZE_8BIT) && ((hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_HALFWORD) && \
2321 (hspi->hdmarx->Init.MemDataAlignment != DMA_MDATAALIGN_WORD))))
2322 {
2323 /* Restriction the DMA data received is not allowed in this mode */
2324 errorcode = HAL_ERROR;
2325 /* Unlock the process */
2326 __HAL_UNLOCK(hspi);
2327 return errorcode;
2328 }
2329
2330 /* Adjust XferCount according to DMA alignment / Data size */
2331 if (hspi->Init.DataSize <= SPI_DATASIZE_8BIT)
2332 {
2333 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_HALFWORD)
2334 {
2335 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 1UL) >> 1UL;
2336 }
2337 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2338 {
2339 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 3UL) >> 2UL;
2340 }
2341 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_HALFWORD)
2342 {
2343 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 1UL) >> 1UL;
2344 }
2345 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2346 {
2347 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 3UL) >> 2UL;
2348 }
2349 }
2350 else if (hspi->Init.DataSize <= SPI_DATASIZE_16BIT)
2351 {
2352 if (hspi->hdmatx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2353 {
2354 hspi->TxXferCount = (hspi->TxXferCount + (uint16_t) 1UL) >> 1UL;
2355 }
2356 if (hspi->hdmarx->Init.MemDataAlignment == DMA_MDATAALIGN_WORD)
2357 {
2358 hspi->RxXferCount = (hspi->RxXferCount + (uint16_t) 1UL) >> 1UL;
2359 }
2360 }
2361 else
2362 {
2363 /* Adjustment done */
2364 }
2365
2366 /* Check if we are in Rx only or in Rx/Tx Mode and configure the DMA transfer complete callback */
2367 if (hspi->State == HAL_SPI_STATE_BUSY_RX)
2368 {
2369 /* Set the SPI Rx DMA Half transfer complete callback */
2370 hspi->hdmarx->XferHalfCpltCallback = SPI_DMAHalfReceiveCplt;
2371 hspi->hdmarx->XferCpltCallback = SPI_DMAReceiveCplt;
2372 }
2373 else
2374 {
2375 /* Set the SPI Tx/Rx DMA Half transfer complete callback */
2376 hspi->hdmarx->XferHalfCpltCallback = SPI_DMAHalfTransmitReceiveCplt;
2377 hspi->hdmarx->XferCpltCallback = SPI_DMATransmitReceiveCplt;
2378 }
2379
2380 /* Set the DMA error callback */
2381 hspi->hdmarx->XferErrorCallback = SPI_DMAError;
2382
2383 /* Set the DMA AbortCallback */
2384 hspi->hdmarx->XferAbortCallback = NULL;
2385
2386 /* Enable the Rx DMA Stream/Channel */
2387 if (HAL_OK != HAL_DMA_Start_IT(hspi->hdmarx, (uint32_t)&hspi->Instance->RXDR, (uint32_t)hspi->pRxBuffPtr,
2388 hspi->RxXferCount))
2389 {
2390 /* Update SPI error code */
2391 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_DMA);
2392
2393 /* Unlock the process */
2394 __HAL_UNLOCK(hspi);
2395
2396 hspi->State = HAL_SPI_STATE_READY;
2397 errorcode = HAL_ERROR;
2398 return errorcode;
2399 }
2400
2401 /* Enable Rx DMA Request */
2402 SET_BIT(hspi->Instance->CFG1, SPI_CFG1_RXDMAEN);
2403
2404 /* Set the SPI Tx DMA transfer complete callback as NULL because the communication closing
2405 is performed in DMA reception complete callback */
2406 hspi->hdmatx->XferHalfCpltCallback = NULL;
2407 hspi->hdmatx->XferCpltCallback = NULL;
2408 hspi->hdmatx->XferAbortCallback = NULL;
2409
2410 /* Set the DMA error callback */
2411 hspi->hdmatx->XferErrorCallback = SPI_DMAError;
2412
2413 /* Enable the Tx DMA Stream/Channel */
2414 if (HAL_OK != HAL_DMA_Start_IT(hspi->hdmatx, (uint32_t)hspi->pTxBuffPtr, (uint32_t)&hspi->Instance->TXDR,
2415 hspi->TxXferCount))
2416 {
2417 /* Update SPI error code */
2418 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_DMA);
2419
2420 /* Unlock the process */
2421 __HAL_UNLOCK(hspi);
2422
2423 hspi->State = HAL_SPI_STATE_READY;
2424 errorcode = HAL_ERROR;
2425 return errorcode;
2426 }
2427
2428 if (hspi->hdmatx->Init.Mode == DMA_CIRCULAR)
2429 {
2430 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, 0UL);
2431 }
2432 else
2433 {
2434 MODIFY_REG(hspi->Instance->CR2, SPI_CR2_TSIZE, Size);
2435 }
2436
2437 /* Enable Tx DMA Request */
2438 SET_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN);
2439
2440 /* Enable the SPI Error Interrupt Bit */
2441 __HAL_SPI_ENABLE_IT(hspi, (SPI_IT_OVR | SPI_IT_UDR | SPI_IT_FRE | SPI_IT_MODF));
2442
2443 /* Enable SPI peripheral */
2444 __HAL_SPI_ENABLE(hspi);
2445
2446 if (hspi->Init.Mode == SPI_MODE_MASTER)
2447 {
2448 /* Master transfer start */
2449 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSTART);
2450 }
2451
2452 /* Unlock the process */
2453 __HAL_UNLOCK(hspi);
2454 return errorcode;
2455 }
2456
2457 /**
2458 * @brief Abort ongoing transfer (blocking mode).
2459 * @param hspi SPI handle.
2460 * @note This procedure could be used for aborting any ongoing transfer (Tx and Rx),
2461 * started in Interrupt or DMA mode.
2462 * @note This procedure performs following operations :
2463 * + Disable SPI Interrupts (depending of transfer direction)
2464 * + Disable the DMA transfer in the peripheral register (if enabled)
2465 * + Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
2466 * + Set handle State to READY.
2467 * @note This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
2468 * @retval HAL status
2469 */
HAL_SPI_Abort(SPI_HandleTypeDef * hspi)2470 HAL_StatusTypeDef HAL_SPI_Abort(SPI_HandleTypeDef *hspi)
2471 {
2472 HAL_StatusTypeDef errorcode;
2473
2474 __IO uint32_t count;
2475
2476 /* Lock the process */
2477 __HAL_LOCK(hspi);
2478
2479 /* Set hspi->state to aborting to avoid any interaction */
2480 hspi->State = HAL_SPI_STATE_ABORT;
2481
2482 /* Initialized local variable */
2483 errorcode = HAL_OK;
2484 count = SPI_DEFAULT_TIMEOUT * (SystemCoreClock / 24UL / 1000UL);
2485
2486 /* If master communication on going, make sure current frame is done before closing the connection */
2487 if (HAL_IS_BIT_SET(hspi->Instance->CR1, SPI_CR1_CSTART))
2488 {
2489 /* Disable EOT interrupt */
2490 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_EOT);
2491 do
2492 {
2493 count--;
2494 if (count == 0UL)
2495 {
2496 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2497 break;
2498 }
2499 }
2500 while (HAL_IS_BIT_SET(hspi->Instance->IER, SPI_IT_EOT));
2501
2502 /* Request a Suspend transfer */
2503 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSUSP);
2504 do
2505 {
2506 count--;
2507 if (count == 0UL)
2508 {
2509 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2510 break;
2511 }
2512 }
2513 while (HAL_IS_BIT_SET(hspi->Instance->CR1, SPI_CR1_CSTART));
2514
2515 /* Clear SUSP flag */
2516 __HAL_SPI_CLEAR_SUSPFLAG(hspi);
2517 do
2518 {
2519 count--;
2520 if (count == 0UL)
2521 {
2522 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2523 break;
2524 }
2525 }
2526 while (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_SUSP));
2527 }
2528
2529 /* Disable the SPI DMA Tx request if enabled */
2530 if (HAL_IS_BIT_SET(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN))
2531 {
2532 if (hspi->hdmatx != NULL)
2533 {
2534 /* Abort the SPI DMA Tx Stream/Channel : use blocking DMA Abort API (no callback) */
2535 hspi->hdmatx->XferAbortCallback = NULL;
2536
2537 /* Abort DMA Tx Handle linked to SPI Peripheral */
2538 if (HAL_DMA_Abort(hspi->hdmatx) != HAL_OK)
2539 {
2540 if (HAL_DMA_GetError(hspi->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
2541 {
2542 hspi->ErrorCode = HAL_SPI_ERROR_ABORT;
2543 }
2544 }
2545 }
2546 }
2547
2548 /* Disable the SPI DMA Rx request if enabled */
2549 if (HAL_IS_BIT_SET(hspi->Instance->CFG1, SPI_CFG1_RXDMAEN))
2550 {
2551 if (hspi->hdmarx != NULL)
2552 {
2553 /* Abort the SPI DMA Rx Stream/Channel : use blocking DMA Abort API (no callback) */
2554 hspi->hdmarx->XferAbortCallback = NULL;
2555
2556 /* Abort DMA Rx Handle linked to SPI Peripheral */
2557 if (HAL_DMA_Abort(hspi->hdmarx) != HAL_OK)
2558 {
2559 if (HAL_DMA_GetError(hspi->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
2560 {
2561 hspi->ErrorCode = HAL_SPI_ERROR_ABORT;
2562 }
2563 }
2564 }
2565 }
2566
2567 /* Proceed with abort procedure */
2568 SPI_AbortTransfer(hspi);
2569
2570 /* Check error during Abort procedure */
2571 if (hspi->ErrorCode == HAL_SPI_ERROR_ABORT)
2572 {
2573 /* return HAL_Error in case of error during Abort procedure */
2574 errorcode = HAL_ERROR;
2575 }
2576 else
2577 {
2578 /* Reset errorCode */
2579 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
2580 }
2581
2582 /* Unlock the process */
2583 __HAL_UNLOCK(hspi);
2584
2585 /* Restore hspi->state to ready */
2586 hspi->State = HAL_SPI_STATE_READY;
2587
2588 return errorcode;
2589 }
2590
2591 /**
2592 * @brief Abort ongoing transfer (Interrupt mode).
2593 * @param hspi SPI handle.
2594 * @note This procedure could be used for aborting any ongoing transfer (Tx and Rx),
2595 * started in Interrupt or DMA mode.
2596 * @note This procedure performs following operations :
2597 * + Disable SPI Interrupts (depending of transfer direction)
2598 * + Disable the DMA transfer in the peripheral register (if enabled)
2599 * + Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
2600 * + Set handle State to READY
2601 * + At abort completion, call user abort complete callback.
2602 * @note This procedure is executed in Interrupt mode, meaning that abort procedure could be
2603 * considered as completed only when user abort complete callback is executed (not when exiting function).
2604 * @retval HAL status
2605 */
HAL_SPI_Abort_IT(SPI_HandleTypeDef * hspi)2606 HAL_StatusTypeDef HAL_SPI_Abort_IT(SPI_HandleTypeDef *hspi)
2607 {
2608 HAL_StatusTypeDef errorcode;
2609 __IO uint32_t count;
2610 uint32_t dma_tx_abort_done = 1UL;
2611 uint32_t dma_rx_abort_done = 1UL;
2612
2613 /* Set hspi->state to aborting to avoid any interaction */
2614 hspi->State = HAL_SPI_STATE_ABORT;
2615
2616 /* Initialized local variable */
2617 errorcode = HAL_OK;
2618 count = SPI_DEFAULT_TIMEOUT * (SystemCoreClock / 24UL / 1000UL);
2619
2620 /* If master communication on going, make sure current frame is done before closing the connection */
2621 if (HAL_IS_BIT_SET(hspi->Instance->CR1, SPI_CR1_CSTART))
2622 {
2623 /* Disable EOT interrupt */
2624 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_EOT);
2625 do
2626 {
2627 count--;
2628 if (count == 0UL)
2629 {
2630 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2631 break;
2632 }
2633 }
2634 while (HAL_IS_BIT_SET(hspi->Instance->IER, SPI_IT_EOT));
2635
2636 /* Request a Suspend transfer */
2637 SET_BIT(hspi->Instance->CR1, SPI_CR1_CSUSP);
2638 do
2639 {
2640 count--;
2641 if (count == 0UL)
2642 {
2643 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2644 break;
2645 }
2646 }
2647 while (HAL_IS_BIT_SET(hspi->Instance->CR1, SPI_CR1_CSTART));
2648
2649 /* Clear SUSP flag */
2650 __HAL_SPI_CLEAR_SUSPFLAG(hspi);
2651 do
2652 {
2653 count--;
2654 if (count == 0UL)
2655 {
2656 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
2657 break;
2658 }
2659 }
2660 while (__HAL_SPI_GET_FLAG(hspi, SPI_FLAG_SUSP));
2661 }
2662
2663 /* If DMA Tx and/or DMA Rx Handles are associated to SPI Handle, DMA Abort complete callbacks should be initialized
2664 before any call to DMA Abort functions */
2665
2666 if (hspi->hdmatx != NULL)
2667 {
2668 if (HAL_IS_BIT_SET(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN))
2669 {
2670 /* Set DMA Abort Complete callback if SPI DMA Tx request if enabled */
2671 hspi->hdmatx->XferAbortCallback = SPI_DMATxAbortCallback;
2672
2673 dma_tx_abort_done = 0UL;
2674
2675 /* Abort DMA Tx Handle linked to SPI Peripheral */
2676 if (HAL_DMA_Abort_IT(hspi->hdmatx) != HAL_OK)
2677 {
2678 if (HAL_DMA_GetError(hspi->hdmatx) == HAL_DMA_ERROR_NO_XFER)
2679 {
2680 dma_tx_abort_done = 1UL;
2681 hspi->hdmatx->XferAbortCallback = NULL;
2682 }
2683 }
2684 }
2685 else
2686 {
2687 hspi->hdmatx->XferAbortCallback = NULL;
2688 }
2689 }
2690
2691 if (hspi->hdmarx != NULL)
2692 {
2693 if (HAL_IS_BIT_SET(hspi->Instance->CFG1, SPI_CFG1_RXDMAEN))
2694 {
2695 /* Set DMA Abort Complete callback if SPI DMA Rx request if enabled */
2696 hspi->hdmarx->XferAbortCallback = SPI_DMARxAbortCallback;
2697
2698 dma_rx_abort_done = 0UL;
2699
2700 /* Abort DMA Rx Handle linked to SPI Peripheral */
2701 if (HAL_DMA_Abort_IT(hspi->hdmarx) != HAL_OK)
2702 {
2703 if (HAL_DMA_GetError(hspi->hdmarx) == HAL_DMA_ERROR_NO_XFER)
2704 {
2705 dma_rx_abort_done = 1UL;
2706 hspi->hdmarx->XferAbortCallback = NULL;
2707 }
2708 }
2709 }
2710 else
2711 {
2712 hspi->hdmarx->XferAbortCallback = NULL;
2713 }
2714 }
2715
2716 /* If no running DMA transfer, finish cleanup and call callbacks */
2717 if ((dma_tx_abort_done == 1UL) && (dma_rx_abort_done == 1UL))
2718 {
2719 /* Proceed with abort procedure */
2720 SPI_AbortTransfer(hspi);
2721
2722 /* Check error during Abort procedure */
2723 if (hspi->ErrorCode == HAL_SPI_ERROR_ABORT)
2724 {
2725 /* return HAL_Error in case of error during Abort procedure */
2726 errorcode = HAL_ERROR;
2727 }
2728 else
2729 {
2730 /* Reset errorCode */
2731 hspi->ErrorCode = HAL_SPI_ERROR_NONE;
2732 }
2733
2734 /* Restore hspi->state to ready */
2735 hspi->State = HAL_SPI_STATE_READY;
2736
2737 /* Call user Abort complete callback */
2738 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
2739 hspi->AbortCpltCallback(hspi);
2740 #else
2741 HAL_SPI_AbortCpltCallback(hspi);
2742 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
2743 }
2744
2745 return errorcode;
2746 }
2747
2748 /**
2749 * @brief Pause the DMA Transfer.
2750 * This API is not supported, it is maintained for backward compatibility.
2751 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
2752 * the configuration information for the specified SPI module.
2753 * @retval HAL_ERROR
2754 */
HAL_SPI_DMAPause(SPI_HandleTypeDef * hspi)2755 HAL_StatusTypeDef HAL_SPI_DMAPause(SPI_HandleTypeDef *hspi)
2756 {
2757 /* Set error code to not supported */
2758 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_NOT_SUPPORTED);
2759
2760 return HAL_ERROR;
2761 }
2762
2763 /**
2764 * @brief Resume the DMA Transfer.
2765 * This API is not supported, it is maintained for backward compatibility.
2766 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
2767 * the configuration information for the specified SPI module.
2768 * @retval HAL_ERROR
2769 */
HAL_SPI_DMAResume(SPI_HandleTypeDef * hspi)2770 HAL_StatusTypeDef HAL_SPI_DMAResume(SPI_HandleTypeDef *hspi)
2771 {
2772 /* Set error code to not supported */
2773 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_NOT_SUPPORTED);
2774
2775 return HAL_ERROR;
2776 }
2777
2778 /**
2779 * @brief Stop the DMA Transfer.
2780 * This API is not supported, it is maintained for backward compatibility.
2781 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
2782 * the configuration information for the specified SPI module.
2783 * @retval HAL_ERROR
2784 */
HAL_SPI_DMAStop(SPI_HandleTypeDef * hspi)2785 HAL_StatusTypeDef HAL_SPI_DMAStop(SPI_HandleTypeDef *hspi)
2786 {
2787 /* Set error code to not supported */
2788 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_NOT_SUPPORTED);
2789
2790 return HAL_ERROR;
2791 }
2792
2793 /**
2794 * @brief Handle SPI interrupt request.
2795 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
2796 * the configuration information for the specified SPI module.
2797 * @retval None
2798 */
HAL_SPI_IRQHandler(SPI_HandleTypeDef * hspi)2799 void HAL_SPI_IRQHandler(SPI_HandleTypeDef *hspi)
2800 {
2801 uint32_t itsource = hspi->Instance->IER;
2802 uint32_t itflag = hspi->Instance->SR;
2803 uint32_t trigger = itsource & itflag;
2804 uint32_t cfg1 = hspi->Instance->CFG1;
2805 uint32_t handled = 0UL;
2806
2807 HAL_SPI_StateTypeDef State = hspi->State;
2808 #if defined (__GNUC__)
2809 __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->RXDR));
2810 #endif /* __GNUC__ */
2811
2812 /* SPI in SUSPEND mode ----------------------------------------------------*/
2813 if (HAL_IS_BIT_SET(itflag, SPI_FLAG_SUSP) && HAL_IS_BIT_SET(itsource, SPI_FLAG_EOT))
2814 {
2815 /* Clear the Suspend flag */
2816 __HAL_SPI_CLEAR_SUSPFLAG(hspi);
2817
2818 /* Suspend on going, Call the Suspend callback */
2819 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
2820 hspi->SuspendCallback(hspi);
2821 #else
2822 HAL_SPI_SuspendCallback(hspi);
2823 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
2824 return;
2825 }
2826
2827 /* SPI in mode Transmitter and Receiver ------------------------------------*/
2828 if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_OVR) && HAL_IS_BIT_CLR(trigger, SPI_FLAG_UDR) && \
2829 HAL_IS_BIT_SET(trigger, SPI_FLAG_DXP))
2830 {
2831 hspi->TxISR(hspi);
2832 hspi->RxISR(hspi);
2833 handled = 1UL;
2834 }
2835
2836 /* SPI in mode Receiver ----------------------------------------------------*/
2837 if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_OVR) && HAL_IS_BIT_SET(trigger, SPI_FLAG_RXP) && \
2838 HAL_IS_BIT_CLR(trigger, SPI_FLAG_DXP))
2839 {
2840 hspi->RxISR(hspi);
2841 handled = 1UL;
2842 }
2843
2844 /* SPI in mode Transmitter -------------------------------------------------*/
2845 if (HAL_IS_BIT_CLR(trigger, SPI_FLAG_UDR) && HAL_IS_BIT_SET(trigger, SPI_FLAG_TXP) && \
2846 HAL_IS_BIT_CLR(trigger, SPI_FLAG_DXP))
2847 {
2848 hspi->TxISR(hspi);
2849 handled = 1UL;
2850 }
2851
2852 #if defined(USE_SPI_RELOAD_TRANSFER)
2853 /* SPI Reload -------------------------------------------------*/
2854 if (HAL_IS_BIT_SET(trigger, SPI_FLAG_TSERF))
2855 {
2856 hspi->Reload.Requested = 0UL;
2857 __HAL_SPI_CLEAR_TSERFFLAG(hspi);
2858 }
2859 #endif /* USE_SPI_RELOAD_TRANSFER */
2860
2861 if (handled != 0UL)
2862 {
2863 return;
2864 }
2865
2866 /* SPI End Of Transfer: DMA or IT based transfer */
2867 if (HAL_IS_BIT_SET(trigger, SPI_FLAG_EOT))
2868 {
2869 /* Clear EOT/TXTF/SUSP flag */
2870 __HAL_SPI_CLEAR_EOTFLAG(hspi);
2871 __HAL_SPI_CLEAR_TXTFFLAG(hspi);
2872 __HAL_SPI_CLEAR_SUSPFLAG(hspi);
2873
2874 /* Disable EOT interrupt */
2875 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_EOT);
2876
2877 /* For the IT based receive extra polling maybe required for last packet */
2878 if (HAL_IS_BIT_CLR(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN))
2879 {
2880 /* Pooling remaining data */
2881 while (hspi->RxXferCount != 0UL)
2882 {
2883 /* Receive data in 32 Bit mode */
2884 if (hspi->Init.DataSize > SPI_DATASIZE_16BIT)
2885 {
2886 *((uint32_t *)hspi->pRxBuffPtr) = *((__IO uint32_t *)&hspi->Instance->RXDR);
2887 hspi->pRxBuffPtr += sizeof(uint32_t);
2888 }
2889 /* Receive data in 16 Bit mode */
2890 else if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
2891 {
2892 #if defined (__GNUC__)
2893 *((uint16_t *)hspi->pRxBuffPtr) = *prxdr_16bits;
2894 #else
2895 *((uint16_t *)hspi->pRxBuffPtr) = *((__IO uint16_t *)&hspi->Instance->RXDR);
2896 #endif /* __GNUC__ */
2897 hspi->pRxBuffPtr += sizeof(uint16_t);
2898 }
2899 /* Receive data in 8 Bit mode */
2900 else
2901 {
2902 *((uint8_t *)hspi->pRxBuffPtr) = *((__IO uint8_t *)&hspi->Instance->RXDR);
2903 hspi->pRxBuffPtr += sizeof(uint8_t);
2904 }
2905
2906 hspi->RxXferCount--;
2907 }
2908 }
2909
2910 /* Call SPI Standard close procedure */
2911 SPI_CloseTransfer(hspi);
2912
2913 hspi->State = HAL_SPI_STATE_READY;
2914 if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
2915 {
2916 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
2917 hspi->ErrorCallback(hspi);
2918 #else
2919 HAL_SPI_ErrorCallback(hspi);
2920 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
2921 return;
2922 }
2923
2924 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
2925 /* Call appropriate user callback */
2926 if (State == HAL_SPI_STATE_BUSY_TX_RX)
2927 {
2928 hspi->TxRxCpltCallback(hspi);
2929 }
2930 else if (State == HAL_SPI_STATE_BUSY_RX)
2931 {
2932 hspi->RxCpltCallback(hspi);
2933 }
2934 else if (State == HAL_SPI_STATE_BUSY_TX)
2935 {
2936 hspi->TxCpltCallback(hspi);
2937 }
2938 #else
2939 /* Call appropriate user callback */
2940 if (State == HAL_SPI_STATE_BUSY_TX_RX)
2941 {
2942 HAL_SPI_TxRxCpltCallback(hspi);
2943 }
2944 else if (State == HAL_SPI_STATE_BUSY_RX)
2945 {
2946 HAL_SPI_RxCpltCallback(hspi);
2947 }
2948 else if (State == HAL_SPI_STATE_BUSY_TX)
2949 {
2950 HAL_SPI_TxCpltCallback(hspi);
2951 }
2952 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
2953 else
2954 {
2955 /* End of the appropriate call */
2956 }
2957
2958 return;
2959 }
2960
2961 /* SPI in Error Treatment --------------------------------------------------*/
2962 if ((trigger & (SPI_FLAG_MODF | SPI_FLAG_OVR | SPI_FLAG_FRE | SPI_FLAG_UDR)) != 0UL)
2963 {
2964 /* SPI Overrun error interrupt occurred ----------------------------------*/
2965 if ((trigger & SPI_FLAG_OVR) != 0UL)
2966 {
2967 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_OVR);
2968 __HAL_SPI_CLEAR_OVRFLAG(hspi);
2969 }
2970
2971 /* SPI Mode Fault error interrupt occurred -------------------------------*/
2972 if ((trigger & SPI_FLAG_MODF) != 0UL)
2973 {
2974 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_MODF);
2975 __HAL_SPI_CLEAR_MODFFLAG(hspi);
2976 }
2977
2978 /* SPI Frame error interrupt occurred ------------------------------------*/
2979 if ((trigger & SPI_FLAG_FRE) != 0UL)
2980 {
2981 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FRE);
2982 __HAL_SPI_CLEAR_FREFLAG(hspi);
2983 }
2984
2985 /* SPI Underrun error interrupt occurred ------------------------------------*/
2986 if ((trigger & SPI_FLAG_UDR) != 0UL)
2987 {
2988 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_UDR);
2989 __HAL_SPI_CLEAR_UDRFLAG(hspi);
2990 }
2991
2992 if (hspi->ErrorCode != HAL_SPI_ERROR_NONE)
2993 {
2994 /* Disable SPI peripheral */
2995 __HAL_SPI_DISABLE(hspi);
2996
2997 /* Disable all interrupts */
2998 __HAL_SPI_DISABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_RXP | SPI_IT_TXP | SPI_IT_MODF |
2999 SPI_IT_OVR | SPI_IT_FRE | SPI_IT_UDR));
3000
3001 /* Disable the SPI DMA requests if enabled */
3002 if (HAL_IS_BIT_SET(cfg1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN))
3003 {
3004 /* Disable the SPI DMA requests */
3005 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
3006
3007 /* Abort the SPI DMA Rx channel */
3008 if (hspi->hdmarx != NULL)
3009 {
3010 /* Set the SPI DMA Abort callback :
3011 will lead to call HAL_SPI_ErrorCallback() at end of DMA abort procedure */
3012 hspi->hdmarx->XferAbortCallback = SPI_DMAAbortOnError;
3013 if (HAL_OK != HAL_DMA_Abort_IT(hspi->hdmarx))
3014 {
3015 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
3016 }
3017 }
3018 /* Abort the SPI DMA Tx channel */
3019 if (hspi->hdmatx != NULL)
3020 {
3021 /* Set the SPI DMA Abort callback :
3022 will lead to call HAL_SPI_ErrorCallback() at end of DMA abort procedure */
3023 hspi->hdmatx->XferAbortCallback = SPI_DMAAbortOnError;
3024 if (HAL_OK != HAL_DMA_Abort_IT(hspi->hdmatx))
3025 {
3026 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_ABORT);
3027 }
3028 }
3029 }
3030 else
3031 {
3032 /* Restore hspi->State to Ready */
3033 hspi->State = HAL_SPI_STATE_READY;
3034
3035 /* Call user error callback */
3036 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3037 hspi->ErrorCallback(hspi);
3038 #else
3039 HAL_SPI_ErrorCallback(hspi);
3040 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3041 }
3042 }
3043 return;
3044 }
3045 }
3046
3047 /**
3048 * @brief Tx Transfer completed callback.
3049 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3050 * the configuration information for SPI module.
3051 * @retval None
3052 */
HAL_SPI_TxCpltCallback(SPI_HandleTypeDef * hspi)3053 __weak void HAL_SPI_TxCpltCallback(SPI_HandleTypeDef *hspi)
3054 {
3055 /* Prevent unused argument(s) compilation warning */
3056 UNUSED(hspi);
3057
3058 /* NOTE : This function should not be modified, when the callback is needed,
3059 the HAL_SPI_TxCpltCallback should be implemented in the user file
3060 */
3061 }
3062
3063 /**
3064 * @brief Rx Transfer completed callback.
3065 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3066 * the configuration information for SPI module.
3067 * @retval None
3068 */
HAL_SPI_RxCpltCallback(SPI_HandleTypeDef * hspi)3069 __weak void HAL_SPI_RxCpltCallback(SPI_HandleTypeDef *hspi)
3070 {
3071 /* Prevent unused argument(s) compilation warning */
3072 UNUSED(hspi);
3073
3074 /* NOTE : This function should not be modified, when the callback is needed,
3075 the HAL_SPI_RxCpltCallback should be implemented in the user file
3076 */
3077 }
3078
3079 /**
3080 * @brief Tx and Rx Transfer completed callback.
3081 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3082 * the configuration information for SPI module.
3083 * @retval None
3084 */
HAL_SPI_TxRxCpltCallback(SPI_HandleTypeDef * hspi)3085 __weak void HAL_SPI_TxRxCpltCallback(SPI_HandleTypeDef *hspi)
3086 {
3087 /* Prevent unused argument(s) compilation warning */
3088 UNUSED(hspi);
3089
3090 /* NOTE : This function should not be modified, when the callback is needed,
3091 the HAL_SPI_TxRxCpltCallback should be implemented in the user file
3092 */
3093 }
3094
3095 /**
3096 * @brief Tx Half Transfer completed callback.
3097 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3098 * the configuration information for SPI module.
3099 * @retval None
3100 */
HAL_SPI_TxHalfCpltCallback(SPI_HandleTypeDef * hspi)3101 __weak void HAL_SPI_TxHalfCpltCallback(SPI_HandleTypeDef *hspi)
3102 {
3103 /* Prevent unused argument(s) compilation warning */
3104 UNUSED(hspi);
3105
3106 /* NOTE : This function should not be modified, when the callback is needed,
3107 the HAL_SPI_TxHalfCpltCallback should be implemented in the user file
3108 */
3109 }
3110
3111 /**
3112 * @brief Rx Half Transfer completed callback.
3113 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3114 * the configuration information for SPI module.
3115 * @retval None
3116 */
HAL_SPI_RxHalfCpltCallback(SPI_HandleTypeDef * hspi)3117 __weak void HAL_SPI_RxHalfCpltCallback(SPI_HandleTypeDef *hspi)
3118 {
3119 /* Prevent unused argument(s) compilation warning */
3120 UNUSED(hspi);
3121
3122 /* NOTE : This function should not be modified, when the callback is needed,
3123 the HAL_SPI_RxHalfCpltCallback() should be implemented in the user file
3124 */
3125 }
3126
3127 /**
3128 * @brief Tx and Rx Half Transfer callback.
3129 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3130 * the configuration information for SPI module.
3131 * @retval None
3132 */
HAL_SPI_TxRxHalfCpltCallback(SPI_HandleTypeDef * hspi)3133 __weak void HAL_SPI_TxRxHalfCpltCallback(SPI_HandleTypeDef *hspi)
3134 {
3135 /* Prevent unused argument(s) compilation warning */
3136 UNUSED(hspi);
3137
3138 /* NOTE : This function should not be modified, when the callback is needed,
3139 the HAL_SPI_TxRxHalfCpltCallback() should be implemented in the user file
3140 */
3141 }
3142
3143 /**
3144 * @brief SPI error callback.
3145 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3146 * the configuration information for SPI module.
3147 * @retval None
3148 */
HAL_SPI_ErrorCallback(SPI_HandleTypeDef * hspi)3149 __weak void HAL_SPI_ErrorCallback(SPI_HandleTypeDef *hspi)
3150 {
3151 /* Prevent unused argument(s) compilation warning */
3152 UNUSED(hspi);
3153
3154 /* NOTE : This function should not be modified, when the callback is needed,
3155 the HAL_SPI_ErrorCallback should be implemented in the user file
3156 */
3157 /* NOTE : The ErrorCode parameter in the hspi handle is updated by the SPI processes
3158 and user can use HAL_SPI_GetError() API to check the latest error occurred
3159 */
3160 }
3161
3162 /**
3163 * @brief SPI Abort Complete callback.
3164 * @param hspi SPI handle.
3165 * @retval None
3166 */
HAL_SPI_AbortCpltCallback(SPI_HandleTypeDef * hspi)3167 __weak void HAL_SPI_AbortCpltCallback(SPI_HandleTypeDef *hspi)
3168 {
3169 /* Prevent unused argument(s) compilation warning */
3170 UNUSED(hspi);
3171
3172 /* NOTE : This function should not be modified, when the callback is needed,
3173 the HAL_SPI_AbortCpltCallback can be implemented in the user file.
3174 */
3175 }
3176
3177 /**
3178 * @brief SPI Suspend callback.
3179 * @param hspi SPI handle.
3180 * @retval None
3181 */
HAL_SPI_SuspendCallback(SPI_HandleTypeDef * hspi)3182 __weak void HAL_SPI_SuspendCallback(SPI_HandleTypeDef *hspi)
3183 {
3184 /* Prevent unused argument(s) compilation warning */
3185 UNUSED(hspi);
3186
3187 /* NOTE : This function should not be modified, when the callback is needed,
3188 the HAL_SPI_SuspendCallback can be implemented in the user file.
3189 */
3190 }
3191
3192 /**
3193 * @}
3194 */
3195
3196 /** @defgroup SPI_Exported_Functions_Group3 Peripheral State and Errors functions
3197 * @brief SPI control functions
3198 *
3199 @verbatim
3200 ===============================================================================
3201 ##### Peripheral State and Errors functions #####
3202 ===============================================================================
3203 [..]
3204 This subsection provides a set of functions allowing to control the SPI.
3205 (+) HAL_SPI_GetState() API can be helpful to check in run-time the state of the SPI peripheral
3206 (+) HAL_SPI_GetError() check in run-time Errors occurring during communication
3207 @endverbatim
3208 * @{
3209 */
3210
3211 /**
3212 * @brief Return the SPI handle state.
3213 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3214 * the configuration information for SPI module.
3215 * @retval SPI state
3216 */
HAL_SPI_GetState(const SPI_HandleTypeDef * hspi)3217 HAL_SPI_StateTypeDef HAL_SPI_GetState(const SPI_HandleTypeDef *hspi)
3218 {
3219 /* Return SPI handle state */
3220 return hspi->State;
3221 }
3222
3223 /**
3224 * @brief Return the SPI error code.
3225 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3226 * the configuration information for SPI module.
3227 * @retval SPI error code in bitmap format
3228 */
HAL_SPI_GetError(const SPI_HandleTypeDef * hspi)3229 uint32_t HAL_SPI_GetError(const SPI_HandleTypeDef *hspi)
3230 {
3231 /* Return SPI ErrorCode */
3232 return hspi->ErrorCode;
3233 }
3234
3235 /**
3236 * @}
3237 */
3238
3239 /**
3240 * @}
3241 */
3242
3243 /** @addtogroup SPI_Private_Functions
3244 * @brief Private functions
3245 * @{
3246 */
3247
3248 /**
3249 * @brief DMA SPI transmit process complete callback.
3250 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3251 * the configuration information for the specified DMA module.
3252 * @retval None
3253 */
SPI_DMATransmitCplt(DMA_HandleTypeDef * hdma)3254 static void SPI_DMATransmitCplt(DMA_HandleTypeDef *hdma)
3255 {
3256 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3257
3258 if (hspi->State != HAL_SPI_STATE_ABORT)
3259 {
3260 if (hspi->hdmatx->Init.Mode == DMA_CIRCULAR)
3261 {
3262 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3263 hspi->TxCpltCallback(hspi);
3264 #else
3265 HAL_SPI_TxCpltCallback(hspi);
3266 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3267 }
3268 else
3269 {
3270 /* Enable EOT interrupt */
3271 __HAL_SPI_ENABLE_IT(hspi, SPI_IT_EOT);
3272 }
3273 }
3274 }
3275
3276 /**
3277 * @brief DMA SPI receive process complete callback.
3278 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3279 * the configuration information for the specified DMA module.
3280 * @retval None
3281 */
SPI_DMAReceiveCplt(DMA_HandleTypeDef * hdma)3282 static void SPI_DMAReceiveCplt(DMA_HandleTypeDef *hdma)
3283 {
3284 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3285
3286 if (hspi->State != HAL_SPI_STATE_ABORT)
3287 {
3288 if (hspi->hdmarx->Init.Mode == DMA_CIRCULAR)
3289 {
3290 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3291 hspi->RxCpltCallback(hspi);
3292 #else
3293 HAL_SPI_RxCpltCallback(hspi);
3294 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3295 }
3296 else
3297 {
3298 /* Enable EOT interrupt */
3299 __HAL_SPI_ENABLE_IT(hspi, SPI_IT_EOT);
3300 }
3301 }
3302 }
3303
3304 /**
3305 * @brief DMA SPI transmit receive process complete callback.
3306 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3307 * the configuration information for the specified DMA module.
3308 * @retval None
3309 */
SPI_DMATransmitReceiveCplt(DMA_HandleTypeDef * hdma)3310 static void SPI_DMATransmitReceiveCplt(DMA_HandleTypeDef *hdma)
3311 {
3312 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3313
3314 if (hspi->State != HAL_SPI_STATE_ABORT)
3315 {
3316 if (hspi->hdmatx->Init.Mode == DMA_CIRCULAR)
3317 {
3318 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3319 hspi->TxRxCpltCallback(hspi);
3320 #else
3321 HAL_SPI_TxRxCpltCallback(hspi);
3322 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3323 }
3324 else
3325 {
3326 /* Enable EOT interrupt */
3327 __HAL_SPI_ENABLE_IT(hspi, SPI_IT_EOT);
3328 }
3329 }
3330 }
3331
3332 /**
3333 * @brief DMA SPI half transmit process complete callback.
3334 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3335 * the configuration information for the specified DMA module.
3336 * @retval None
3337 */
SPI_DMAHalfTransmitCplt(DMA_HandleTypeDef * hdma)3338 static void SPI_DMAHalfTransmitCplt(DMA_HandleTypeDef *hdma)
3339 {
3340 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3341
3342 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3343 hspi->TxHalfCpltCallback(hspi);
3344 #else
3345 HAL_SPI_TxHalfCpltCallback(hspi);
3346 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3347 }
3348
3349 /**
3350 * @brief DMA SPI half receive process complete callback
3351 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3352 * the configuration information for the specified DMA module.
3353 * @retval None
3354 */
SPI_DMAHalfReceiveCplt(DMA_HandleTypeDef * hdma)3355 static void SPI_DMAHalfReceiveCplt(DMA_HandleTypeDef *hdma)
3356 {
3357 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3358
3359 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3360 hspi->RxHalfCpltCallback(hspi);
3361 #else
3362 HAL_SPI_RxHalfCpltCallback(hspi);
3363 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3364 }
3365
3366 /**
3367 * @brief DMA SPI half transmit receive process complete callback.
3368 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3369 * the configuration information for the specified DMA module.
3370 * @retval None
3371 */
SPI_DMAHalfTransmitReceiveCplt(DMA_HandleTypeDef * hdma)3372 static void SPI_DMAHalfTransmitReceiveCplt(DMA_HandleTypeDef *hdma)
3373 {
3374 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3375
3376 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3377 hspi->TxRxHalfCpltCallback(hspi);
3378 #else
3379 HAL_SPI_TxRxHalfCpltCallback(hspi);
3380 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3381 }
3382
3383 /**
3384 * @brief DMA SPI communication error callback.
3385 * @param hdma: pointer to a DMA_HandleTypeDef structure that contains
3386 * the configuration information for the specified DMA module.
3387 * @retval None
3388 */
SPI_DMAError(DMA_HandleTypeDef * hdma)3389 static void SPI_DMAError(DMA_HandleTypeDef *hdma)
3390 {
3391 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3392
3393 /* if DMA error is FIFO error ignore it */
3394 if (HAL_DMA_GetError(hdma) != HAL_DMA_ERROR_FE)
3395 {
3396 /* Call SPI standard close procedure */
3397 SPI_CloseTransfer(hspi);
3398
3399 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_DMA);
3400 hspi->State = HAL_SPI_STATE_READY;
3401 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3402 hspi->ErrorCallback(hspi);
3403 #else
3404 HAL_SPI_ErrorCallback(hspi);
3405 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3406 }
3407 }
3408
3409 /**
3410 * @brief DMA SPI communication abort callback, when initiated by HAL services on Error
3411 * (To be called at end of DMA Abort procedure following error occurrence).
3412 * @param hdma DMA handle.
3413 * @retval None
3414 */
SPI_DMAAbortOnError(DMA_HandleTypeDef * hdma)3415 static void SPI_DMAAbortOnError(DMA_HandleTypeDef *hdma)
3416 {
3417 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3418 hspi->RxXferCount = (uint16_t) 0UL;
3419 hspi->TxXferCount = (uint16_t) 0UL;
3420
3421 /* Restore hspi->State to Ready */
3422 hspi->State = HAL_SPI_STATE_READY;
3423
3424 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3425 hspi->ErrorCallback(hspi);
3426 #else
3427 HAL_SPI_ErrorCallback(hspi);
3428 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3429 }
3430
3431 /**
3432 * @brief DMA SPI Tx communication abort callback, when initiated by user
3433 * (To be called at end of DMA Tx Abort procedure following user abort request).
3434 * @note When this callback is executed, User Abort complete call back is called only if no
3435 * Abort still ongoing for Rx DMA Handle.
3436 * @param hdma DMA handle.
3437 * @retval None
3438 */
SPI_DMATxAbortCallback(DMA_HandleTypeDef * hdma)3439 static void SPI_DMATxAbortCallback(DMA_HandleTypeDef *hdma)
3440 {
3441 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3442
3443 hspi->hdmatx->XferAbortCallback = NULL;
3444
3445 /* Check if an Abort process is still ongoing */
3446 if (hspi->hdmarx != NULL)
3447 {
3448 if (hspi->hdmarx->XferAbortCallback != NULL)
3449 {
3450 return;
3451 }
3452 }
3453
3454 /* Call the Abort procedure */
3455 SPI_AbortTransfer(hspi);
3456
3457 /* Restore hspi->State to Ready */
3458 hspi->State = HAL_SPI_STATE_READY;
3459
3460 /* Call user Abort complete callback */
3461 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3462 hspi->AbortCpltCallback(hspi);
3463 #else
3464 HAL_SPI_AbortCpltCallback(hspi);
3465 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3466 }
3467
3468 /**
3469 * @brief DMA SPI Rx communication abort callback, when initiated by user
3470 * (To be called at end of DMA Rx Abort procedure following user abort request).
3471 * @note When this callback is executed, User Abort complete call back is called only if no
3472 * Abort still ongoing for Tx DMA Handle.
3473 * @param hdma DMA handle.
3474 * @retval None
3475 */
SPI_DMARxAbortCallback(DMA_HandleTypeDef * hdma)3476 static void SPI_DMARxAbortCallback(DMA_HandleTypeDef *hdma)
3477 {
3478 SPI_HandleTypeDef *hspi = (SPI_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3479
3480 hspi->hdmarx->XferAbortCallback = NULL;
3481
3482 /* Check if an Abort process is still ongoing */
3483 if (hspi->hdmatx != NULL)
3484 {
3485 if (hspi->hdmatx->XferAbortCallback != NULL)
3486 {
3487 return;
3488 }
3489 }
3490
3491 /* Call the Abort procedure */
3492 SPI_AbortTransfer(hspi);
3493
3494 /* Restore hspi->State to Ready */
3495 hspi->State = HAL_SPI_STATE_READY;
3496
3497 /* Call user Abort complete callback */
3498 #if (USE_HAL_SPI_REGISTER_CALLBACKS == 1UL)
3499 hspi->AbortCpltCallback(hspi);
3500 #else
3501 HAL_SPI_AbortCpltCallback(hspi);
3502 #endif /* USE_HAL_SPI_REGISTER_CALLBACKS */
3503 }
3504
3505 /**
3506 * @brief Manage the receive 8-bit in Interrupt context.
3507 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3508 * the configuration information for SPI module.
3509 * @retval None
3510 */
SPI_RxISR_8BIT(SPI_HandleTypeDef * hspi)3511 static void SPI_RxISR_8BIT(SPI_HandleTypeDef *hspi)
3512 {
3513 /* Receive data in 8 Bit mode */
3514 *((uint8_t *)hspi->pRxBuffPtr) = (*(__IO uint8_t *)&hspi->Instance->RXDR);
3515 hspi->pRxBuffPtr += sizeof(uint8_t);
3516 hspi->RxXferCount--;
3517
3518 /* Disable IT if no more data excepted */
3519 if (hspi->RxXferCount == 0UL)
3520 {
3521 #if defined(USE_SPI_RELOAD_TRANSFER)
3522 /* Check if there is any request to reload */
3523 if (hspi->Reload.Requested == 1UL)
3524 {
3525 hspi->RxXferSize = hspi->Reload.RxXferSize;
3526 hspi->RxXferCount = hspi->Reload.RxXferSize;
3527 hspi->pRxBuffPtr = hspi->Reload.pRxBuffPtr;
3528 }
3529 else
3530 {
3531 /* Disable RXP interrupts */
3532 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3533 }
3534 #else
3535 /* Disable RXP interrupts */
3536 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3537 #endif /* USE_SPI_RELOAD_TRANSFER */
3538 }
3539 }
3540
3541
3542 /**
3543 * @brief Manage the 16-bit receive in Interrupt context.
3544 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3545 * the configuration information for SPI module.
3546 * @retval None
3547 */
SPI_RxISR_16BIT(SPI_HandleTypeDef * hspi)3548 static void SPI_RxISR_16BIT(SPI_HandleTypeDef *hspi)
3549 {
3550 /* Receive data in 16 Bit mode */
3551 #if defined (__GNUC__)
3552 __IO uint16_t *prxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->RXDR));
3553
3554 *((uint16_t *)hspi->pRxBuffPtr) = *prxdr_16bits;
3555 #else
3556 *((uint16_t *)hspi->pRxBuffPtr) = (*(__IO uint16_t *)&hspi->Instance->RXDR);
3557 #endif /* __GNUC__ */
3558 hspi->pRxBuffPtr += sizeof(uint16_t);
3559 hspi->RxXferCount--;
3560
3561 /* Disable IT if no more data excepted */
3562 if (hspi->RxXferCount == 0UL)
3563 {
3564 #if defined(USE_SPI_RELOAD_TRANSFER)
3565 /* Check if there is any request to reload */
3566 if (hspi->Reload.Requested == 1UL)
3567 {
3568 hspi->RxXferSize = hspi->Reload.RxXferSize;
3569 hspi->RxXferCount = hspi->Reload.RxXferSize;
3570 hspi->pRxBuffPtr = hspi->Reload.pRxBuffPtr;
3571 }
3572 else
3573 {
3574 /* Disable RXP interrupts */
3575 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3576 }
3577 #else
3578 /* Disable RXP interrupts */
3579 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3580 #endif /* USE_SPI_RELOAD_TRANSFER */
3581 }
3582 }
3583
3584
3585 /**
3586 * @brief Manage the 32-bit receive in Interrupt context.
3587 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3588 * the configuration information for SPI module.
3589 * @retval None
3590 */
SPI_RxISR_32BIT(SPI_HandleTypeDef * hspi)3591 static void SPI_RxISR_32BIT(SPI_HandleTypeDef *hspi)
3592 {
3593 /* Receive data in 32 Bit mode */
3594 *((uint32_t *)hspi->pRxBuffPtr) = (*(__IO uint32_t *)&hspi->Instance->RXDR);
3595 hspi->pRxBuffPtr += sizeof(uint32_t);
3596 hspi->RxXferCount--;
3597
3598 /* Disable IT if no more data excepted */
3599 if (hspi->RxXferCount == 0UL)
3600 {
3601 #if defined(USE_SPI_RELOAD_TRANSFER)
3602 /* Check if there is any request to reload */
3603 if (hspi->Reload.Requested == 1UL)
3604 {
3605 hspi->RxXferSize = hspi->Reload.RxXferSize;
3606 hspi->RxXferCount = hspi->Reload.RxXferSize;
3607 hspi->pRxBuffPtr = hspi->Reload.pRxBuffPtr;
3608 }
3609 else
3610 {
3611 /* Disable RXP interrupts */
3612 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3613 }
3614 #else
3615 /* Disable RXP interrupts */
3616 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_RXP);
3617 #endif /* USE_SPI_RELOAD_TRANSFER */
3618 }
3619 }
3620
3621
3622 /**
3623 * @brief Handle the data 8-bit transmit in Interrupt mode.
3624 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3625 * the configuration information for SPI module.
3626 * @retval None
3627 */
SPI_TxISR_8BIT(SPI_HandleTypeDef * hspi)3628 static void SPI_TxISR_8BIT(SPI_HandleTypeDef *hspi)
3629 {
3630 /* Transmit data in 8 Bit mode */
3631 *(__IO uint8_t *)&hspi->Instance->TXDR = *((const uint8_t *)hspi->pTxBuffPtr);
3632 hspi->pTxBuffPtr += sizeof(uint8_t);
3633 hspi->TxXferCount--;
3634
3635 /* Disable IT if no more data excepted */
3636 if (hspi->TxXferCount == 0UL)
3637 {
3638 #if defined(USE_SPI_RELOAD_TRANSFER)
3639 /* Check if there is any request to reload */
3640 if (hspi->Reload.Requested == 1UL)
3641 {
3642 hspi->TxXferSize = hspi->Reload.TxXferSize;
3643 hspi->TxXferCount = hspi->Reload.TxXferSize;
3644 hspi->pTxBuffPtr = hspi->Reload.pTxBuffPtr;
3645 }
3646 else
3647 {
3648 /* Disable TXP interrupts */
3649 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3650 }
3651 #else
3652 /* Disable TXP interrupts */
3653 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3654 #endif /* USE_SPI_RELOAD_TRANSFER */
3655 }
3656 }
3657
3658 /**
3659 * @brief Handle the data 16-bit transmit in Interrupt mode.
3660 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3661 * the configuration information for SPI module.
3662 * @retval None
3663 */
SPI_TxISR_16BIT(SPI_HandleTypeDef * hspi)3664 static void SPI_TxISR_16BIT(SPI_HandleTypeDef *hspi)
3665 {
3666 /* Transmit data in 16 Bit mode */
3667 #if defined (__GNUC__)
3668 __IO uint16_t *ptxdr_16bits = (__IO uint16_t *)(&(hspi->Instance->TXDR));
3669
3670 *ptxdr_16bits = *((const uint16_t *)hspi->pTxBuffPtr);
3671 #else
3672 *((__IO uint16_t *)&hspi->Instance->TXDR) = *((const uint16_t *)hspi->pTxBuffPtr);
3673 #endif /* __GNUC__ */
3674 hspi->pTxBuffPtr += sizeof(uint16_t);
3675 hspi->TxXferCount--;
3676
3677 /* Disable IT if no more data excepted */
3678 if (hspi->TxXferCount == 0UL)
3679 {
3680 #if defined(USE_SPI_RELOAD_TRANSFER)
3681 /* Check if there is any request to reload */
3682 if (hspi->Reload.Requested == 1UL)
3683 {
3684 hspi->TxXferSize = hspi->Reload.TxXferSize;
3685 hspi->TxXferCount = hspi->Reload.TxXferSize;
3686 hspi->pTxBuffPtr = hspi->Reload.pTxBuffPtr;
3687 }
3688 else
3689 {
3690 /* Disable TXP interrupts */
3691 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3692 }
3693 #else
3694 /* Disable TXP interrupts */
3695 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3696 #endif /* USE_SPI_RELOAD_TRANSFER */
3697 }
3698 }
3699
3700 /**
3701 * @brief Handle the data 32-bit transmit in Interrupt mode.
3702 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3703 * the configuration information for SPI module.
3704 * @retval None
3705 */
SPI_TxISR_32BIT(SPI_HandleTypeDef * hspi)3706 static void SPI_TxISR_32BIT(SPI_HandleTypeDef *hspi)
3707 {
3708 /* Transmit data in 32 Bit mode */
3709 *((__IO uint32_t *)&hspi->Instance->TXDR) = *((const uint32_t *)hspi->pTxBuffPtr);
3710 hspi->pTxBuffPtr += sizeof(uint32_t);
3711 hspi->TxXferCount--;
3712
3713 /* Disable IT if no more data excepted */
3714 if (hspi->TxXferCount == 0UL)
3715 {
3716 #if defined(USE_SPI_RELOAD_TRANSFER)
3717 /* Check if there is any request to reload */
3718 if (hspi->Reload.Requested == 1UL)
3719 {
3720 hspi->TxXferSize = hspi->Reload.TxXferSize;
3721 hspi->TxXferCount = hspi->Reload.TxXferSize;
3722 hspi->pTxBuffPtr = hspi->Reload.pTxBuffPtr;
3723 }
3724 else
3725 {
3726 /* Disable TXP interrupts */
3727 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3728 }
3729 #else
3730 /* Disable TXP interrupts */
3731 __HAL_SPI_DISABLE_IT(hspi, SPI_IT_TXP);
3732 #endif /* USE_SPI_RELOAD_TRANSFER */
3733 }
3734 }
3735
3736 /**
3737 * @brief Abort Transfer and clear flags.
3738 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3739 * the configuration information for SPI module.
3740 * @retval None
3741 */
SPI_AbortTransfer(SPI_HandleTypeDef * hspi)3742 static void SPI_AbortTransfer(SPI_HandleTypeDef *hspi)
3743 {
3744 /* Disable SPI peripheral */
3745 __HAL_SPI_DISABLE(hspi);
3746
3747 /* Disable ITs */
3748 __HAL_SPI_DISABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_TXP | SPI_IT_RXP | SPI_IT_DXP | SPI_IT_UDR | SPI_IT_OVR | \
3749 SPI_IT_FRE | SPI_IT_MODF));
3750
3751 /* Clear the Status flags in the SR register */
3752 __HAL_SPI_CLEAR_EOTFLAG(hspi);
3753 __HAL_SPI_CLEAR_TXTFFLAG(hspi);
3754
3755 /* Disable Tx DMA Request */
3756 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
3757
3758 /* Clear the Error flags in the SR register */
3759 __HAL_SPI_CLEAR_OVRFLAG(hspi);
3760 __HAL_SPI_CLEAR_UDRFLAG(hspi);
3761 __HAL_SPI_CLEAR_FREFLAG(hspi);
3762 __HAL_SPI_CLEAR_MODFFLAG(hspi);
3763 __HAL_SPI_CLEAR_SUSPFLAG(hspi);
3764
3765 #if (USE_SPI_CRC != 0U)
3766 __HAL_SPI_CLEAR_CRCERRFLAG(hspi);
3767 #endif /* USE_SPI_CRC */
3768
3769 hspi->TxXferCount = (uint16_t)0UL;
3770 hspi->RxXferCount = (uint16_t)0UL;
3771 }
3772
3773
3774 /**
3775 * @brief Close Transfer and clear flags.
3776 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3777 * the configuration information for SPI module.
3778 * @retval HAL_ERROR: if any error detected
3779 * HAL_OK: if nothing detected
3780 */
SPI_CloseTransfer(SPI_HandleTypeDef * hspi)3781 static void SPI_CloseTransfer(SPI_HandleTypeDef *hspi)
3782 {
3783 uint32_t itflag = hspi->Instance->SR;
3784
3785 __HAL_SPI_CLEAR_EOTFLAG(hspi);
3786 __HAL_SPI_CLEAR_TXTFFLAG(hspi);
3787
3788 /* Disable SPI peripheral */
3789 __HAL_SPI_DISABLE(hspi);
3790
3791 /* Disable ITs */
3792 __HAL_SPI_DISABLE_IT(hspi, (SPI_IT_EOT | SPI_IT_TXP | SPI_IT_RXP | SPI_IT_DXP | SPI_IT_UDR | SPI_IT_OVR | \
3793 SPI_IT_FRE | SPI_IT_MODF));
3794
3795 /* Disable Tx DMA Request */
3796 CLEAR_BIT(hspi->Instance->CFG1, SPI_CFG1_TXDMAEN | SPI_CFG1_RXDMAEN);
3797
3798 /* Report UnderRun error for non RX Only communication */
3799 if (hspi->State != HAL_SPI_STATE_BUSY_RX)
3800 {
3801 if ((itflag & SPI_FLAG_UDR) != 0UL)
3802 {
3803 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_UDR);
3804 __HAL_SPI_CLEAR_UDRFLAG(hspi);
3805 }
3806 }
3807
3808 /* Report OverRun error for non TX Only communication */
3809 if (hspi->State != HAL_SPI_STATE_BUSY_TX)
3810 {
3811 if ((itflag & SPI_FLAG_OVR) != 0UL)
3812 {
3813 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_OVR);
3814 __HAL_SPI_CLEAR_OVRFLAG(hspi);
3815 }
3816
3817 #if (USE_SPI_CRC != 0UL)
3818 /* Check if CRC error occurred */
3819 if (hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE)
3820 {
3821 if ((itflag & SPI_FLAG_CRCERR) != 0UL)
3822 {
3823 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_CRC);
3824 __HAL_SPI_CLEAR_CRCERRFLAG(hspi);
3825 }
3826 }
3827 #endif /* USE_SPI_CRC */
3828 }
3829
3830 /* SPI Mode Fault error interrupt occurred -------------------------------*/
3831 if ((itflag & SPI_FLAG_MODF) != 0UL)
3832 {
3833 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_MODF);
3834 __HAL_SPI_CLEAR_MODFFLAG(hspi);
3835 }
3836
3837 /* SPI Frame error interrupt occurred ------------------------------------*/
3838 if ((itflag & SPI_FLAG_FRE) != 0UL)
3839 {
3840 SET_BIT(hspi->ErrorCode, HAL_SPI_ERROR_FRE);
3841 __HAL_SPI_CLEAR_FREFLAG(hspi);
3842 }
3843
3844 hspi->TxXferCount = (uint16_t)0UL;
3845 hspi->RxXferCount = (uint16_t)0UL;
3846 }
3847
3848 /**
3849 * @brief Handle SPI Communication Timeout.
3850 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3851 * the configuration information for SPI module.
3852 * @param Flag: SPI flag to check
3853 * @param Status: flag state to check
3854 * @param Timeout: Timeout duration
3855 * @param Tickstart: Tick start value
3856 * @retval HAL status
3857 */
SPI_WaitOnFlagUntilTimeout(SPI_HandleTypeDef * hspi,uint32_t Flag,FlagStatus Status,uint32_t Tickstart,uint32_t Timeout)3858 static HAL_StatusTypeDef SPI_WaitOnFlagUntilTimeout(SPI_HandleTypeDef *hspi, uint32_t Flag, FlagStatus Status,
3859 uint32_t Tickstart, uint32_t Timeout)
3860 {
3861 /* Wait until flag is set */
3862 while ((__HAL_SPI_GET_FLAG(hspi, Flag) ? SET : RESET) == Status)
3863 {
3864 /* Check for the Timeout */
3865 if ((((HAL_GetTick() - Tickstart) >= Timeout) && (Timeout != HAL_MAX_DELAY)) || (Timeout == 0U))
3866 {
3867 return HAL_TIMEOUT;
3868 }
3869 }
3870 return HAL_OK;
3871 }
3872
3873 /**
3874 * @brief Compute configured packet size from fifo perspective.
3875 * @param hspi: pointer to a SPI_HandleTypeDef structure that contains
3876 * the configuration information for SPI module.
3877 * @retval Packet size occupied in the fifo
3878 */
SPI_GetPacketSize(SPI_HandleTypeDef * hspi)3879 static uint32_t SPI_GetPacketSize(SPI_HandleTypeDef *hspi)
3880 {
3881 uint32_t fifo_threashold = (hspi->Init.FifoThreshold >> SPI_CFG1_FTHLV_Pos) + 1UL;
3882 uint32_t data_size = (hspi->Init.DataSize >> SPI_CFG1_DSIZE_Pos) + 1UL;
3883
3884 /* Convert data size to Byte */
3885 data_size = (data_size + 7UL) / 8UL;
3886
3887 return data_size * fifo_threashold;
3888 }
3889
3890 /**
3891 * @}
3892 */
3893
3894 #endif /* HAL_SPI_MODULE_ENABLED */
3895
3896 /**
3897 * @}
3898 */
3899
3900 /**
3901 * @}
3902 */
3903