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