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