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