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