1 /**
2   ******************************************************************************
3   * @file    stm32wlxx_hal_smartcard.c
4   * @author  MCD Application Team
5   * @brief   SMARTCARD HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the SMARTCARD peripheral:
8   *           + Initialization and de-initialization functions
9   *           + IO operation functions
10   *           + Peripheral Control functions
11   *           + Peripheral State and Error functions
12   *
13   ******************************************************************************
14   * @attention
15   *
16   * Copyright (c) 2020 STMicroelectronics.
17   * All rights reserved.
18   *
19   * This software is licensed under terms that can be found in the LICENSE file
20   * in the root directory of this software component.
21   * If no LICENSE file comes with this software, it is provided AS-IS.
22   *
23   ******************************************************************************
24   @verbatim
25   ==============================================================================
26                         ##### How to use this driver #####
27   ==============================================================================
28   [..]
29     The SMARTCARD HAL driver can be used as follows:
30 
31     (#) Declare a SMARTCARD_HandleTypeDef handle structure (eg. SMARTCARD_HandleTypeDef hsmartcard).
32     (#) Associate a USART to the SMARTCARD handle hsmartcard.
33     (#) Initialize the SMARTCARD low level resources by implementing the HAL_SMARTCARD_MspInit() API:
34         (++) Enable the USARTx interface clock.
35         (++) USART pins configuration:
36              (+++) Enable the clock for the USART GPIOs.
37              (+++) Configure the USART pins (TX as alternate function pull-up, RX as alternate function Input).
38         (++) NVIC configuration if you need to use interrupt process (HAL_SMARTCARD_Transmit_IT()
39              and HAL_SMARTCARD_Receive_IT() APIs):
40              (+++) Configure the USARTx interrupt priority.
41              (+++) Enable the NVIC USART IRQ handle.
42         (++) DMA Configuration if you need to use DMA process (HAL_SMARTCARD_Transmit_DMA()
43              and HAL_SMARTCARD_Receive_DMA() APIs):
44              (+++) Declare a DMA handle structure for the Tx/Rx channel.
45              (+++) Enable the DMAx interface clock.
46              (+++) Configure the declared DMA handle structure with the required Tx/Rx parameters.
47              (+++) Configure the DMA Tx/Rx channel.
48              (+++) Associate the initialized DMA handle to the SMARTCARD DMA Tx/Rx handle.
49              (+++) Configure the priority and enable the NVIC for the transfer complete
50                    interrupt on the DMA Tx/Rx channel.
51 
52     (#) Program the Baud Rate, Parity, Mode(Receiver/Transmitter), clock enabling/disabling and accordingly,
53         the clock parameters (parity, phase, last bit), prescaler value, guard time and NACK on transmission
54         error enabling or disabling in the hsmartcard handle Init structure.
55 
56     (#) If required, program SMARTCARD advanced features (TX/RX pins swap, TimeOut, auto-retry counter,...)
57         in the hsmartcard handle AdvancedInit structure.
58 
59     (#) Initialize the SMARTCARD registers by calling the HAL_SMARTCARD_Init() API:
60         (++) This API configures also the low level Hardware GPIO, CLOCK, CORTEX...etc)
61              by calling the customized HAL_SMARTCARD_MspInit() API.
62         [..]
63         (@) The specific SMARTCARD interrupts (Transmission complete interrupt,
64              RXNE interrupt and Error Interrupts) will be managed using the macros
65              __HAL_SMARTCARD_ENABLE_IT() and __HAL_SMARTCARD_DISABLE_IT() inside the transmit and receive process.
66 
67     [..]
68     [..] Three operation modes are available within this driver :
69 
70      *** Polling mode IO operation ***
71      =================================
72      [..]
73        (+) Send an amount of data in blocking mode using HAL_SMARTCARD_Transmit()
74        (+) Receive an amount of data in blocking mode using HAL_SMARTCARD_Receive()
75 
76      *** Interrupt mode IO operation ***
77      ===================================
78      [..]
79        (+) Send an amount of data in non-blocking mode using HAL_SMARTCARD_Transmit_IT()
80        (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback() is executed and user can
81             add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback()
82        (+) Receive an amount of data in non-blocking mode using HAL_SMARTCARD_Receive_IT()
83        (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback() is executed and user can
84             add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback()
85        (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
86             add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback()
87 
88      *** DMA mode IO operation ***
89      ==============================
90      [..]
91        (+) Send an amount of data in non-blocking mode (DMA) using HAL_SMARTCARD_Transmit_DMA()
92        (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback() is executed and user can
93             add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback()
94        (+) Receive an amount of data in non-blocking mode (DMA) using HAL_SMARTCARD_Receive_DMA()
95        (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback() is executed and user can
96             add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback()
97        (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
98             add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback()
99 
100      *** SMARTCARD HAL driver macros list ***
101      ========================================
102      [..]
103        Below the list of most used macros in SMARTCARD HAL driver.
104 
105        (+) __HAL_SMARTCARD_GET_FLAG : Check whether or not the specified SMARTCARD flag is set
106        (+) __HAL_SMARTCARD_CLEAR_FLAG : Clear the specified SMARTCARD pending flag
107        (+) __HAL_SMARTCARD_ENABLE_IT: Enable the specified SMARTCARD interrupt
108        (+) __HAL_SMARTCARD_DISABLE_IT: Disable the specified SMARTCARD interrupt
109        (+) __HAL_SMARTCARD_GET_IT_SOURCE: Check whether or not the specified SMARTCARD interrupt is enabled
110 
111      [..]
112        (@) You can refer to the SMARTCARD HAL driver header file for more useful macros
113 
114     ##### Callback registration #####
115     ==================================
116 
117     [..]
118     The compilation define USE_HAL_SMARTCARD_REGISTER_CALLBACKS when set to 1
119     allows the user to configure dynamically the driver callbacks.
120 
121     [..]
122     Use Function HAL_SMARTCARD_RegisterCallback() to register a user callback.
123     Function HAL_SMARTCARD_RegisterCallback() allows to register following callbacks:
124     (+) TxCpltCallback            : Tx Complete Callback.
125     (+) RxCpltCallback            : Rx Complete Callback.
126     (+) ErrorCallback             : Error Callback.
127     (+) AbortCpltCallback         : Abort Complete Callback.
128     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
129     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
130     (+) RxFifoFullCallback        : Rx Fifo Full Callback.
131     (+) TxFifoEmptyCallback       : Tx Fifo Empty Callback.
132     (+) MspInitCallback           : SMARTCARD MspInit.
133     (+) MspDeInitCallback         : SMARTCARD MspDeInit.
134     This function takes as parameters the HAL peripheral handle, the Callback ID
135     and a pointer to the user callback function.
136 
137     [..]
138     Use function HAL_SMARTCARD_UnRegisterCallback() to reset a callback to the default
139     weak (surcharged) function.
140     HAL_SMARTCARD_UnRegisterCallback() takes as parameters the HAL peripheral handle,
141     and the Callback ID.
142     This function allows to reset following callbacks:
143     (+) TxCpltCallback            : Tx Complete Callback.
144     (+) RxCpltCallback            : Rx Complete Callback.
145     (+) ErrorCallback             : Error Callback.
146     (+) AbortCpltCallback         : Abort Complete Callback.
147     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
148     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
149     (+) RxFifoFullCallback        : Rx Fifo Full Callback.
150     (+) TxFifoEmptyCallback       : Tx Fifo Empty Callback.
151     (+) MspInitCallback           : SMARTCARD MspInit.
152     (+) MspDeInitCallback         : SMARTCARD MspDeInit.
153 
154     [..]
155     By default, after the HAL_SMARTCARD_Init() and when the state is HAL_SMARTCARD_STATE_RESET
156     all callbacks are set to the corresponding weak (surcharged) functions:
157     examples HAL_SMARTCARD_TxCpltCallback(), HAL_SMARTCARD_RxCpltCallback().
158     Exception done for MspInit and MspDeInit functions that are respectively
159     reset to the legacy weak (surcharged) functions in the HAL_SMARTCARD_Init()
160     and HAL_SMARTCARD_DeInit() only when these callbacks are null (not registered beforehand).
161     If not, MspInit or MspDeInit are not null, the HAL_SMARTCARD_Init() and HAL_SMARTCARD_DeInit()
162     keep and use the user MspInit/MspDeInit callbacks (registered beforehand).
163 
164     [..]
165     Callbacks can be registered/unregistered in HAL_SMARTCARD_STATE_READY state only.
166     Exception done MspInit/MspDeInit that can be registered/unregistered
167     in HAL_SMARTCARD_STATE_READY or HAL_SMARTCARD_STATE_RESET state, thus registered (user)
168     MspInit/DeInit callbacks can be used during the Init/DeInit.
169     In that case first register the MspInit/MspDeInit user callbacks
170     using HAL_SMARTCARD_RegisterCallback() before calling HAL_SMARTCARD_DeInit()
171     or HAL_SMARTCARD_Init() function.
172 
173     [..]
174     When The compilation define USE_HAL_SMARTCARD_REGISTER_CALLBACKS is set to 0 or
175     not defined, the callback registration feature is not available
176     and weak (surcharged) callbacks are used.
177 
178 
179   @endverbatim
180   ******************************************************************************
181   */
182 
183 /* Includes ------------------------------------------------------------------*/
184 #include "stm32wlxx_hal.h"
185 
186 /** @addtogroup STM32WLxx_HAL_Driver
187   * @{
188   */
189 
190 /** @defgroup SMARTCARD SMARTCARD
191   * @brief HAL SMARTCARD module driver
192   * @{
193   */
194 
195 #ifdef HAL_SMARTCARD_MODULE_ENABLED
196 
197 /* Private typedef -----------------------------------------------------------*/
198 /* Private define ------------------------------------------------------------*/
199 /** @defgroup SMARTCARD_Private_Constants SMARTCARD Private Constants
200   * @{
201   */
202 #define SMARTCARD_TEACK_REACK_TIMEOUT  1000U       /*!< SMARTCARD TX or RX enable acknowledge time-out value */
203 
204 #define USART_CR1_FIELDS  ((uint32_t)(USART_CR1_M | USART_CR1_PCE | USART_CR1_PS | USART_CR1_TE | \
205                                       USART_CR1_RE | USART_CR1_OVER8| \
206                                       USART_CR1_FIFOEN))  /*!< USART CR1 fields of parameters set by SMARTCARD_SetConfig API */
207 
208 #define USART_CR2_CLK_FIELDS  ((uint32_t)(USART_CR2_CLKEN | USART_CR2_CPOL | \
209                                           USART_CR2_CPHA | USART_CR2_LBCL)) /*!< SMARTCARD clock-related USART CR2 fields of parameters */
210 
211 #define USART_CR2_FIELDS  ((uint32_t)(USART_CR2_RTOEN | USART_CR2_CLK_FIELDS | \
212                                       USART_CR2_STOP)) /*!< USART CR2 fields of parameters set by SMARTCARD_SetConfig API */
213 
214 #define USART_CR3_FIELDS  ((uint32_t)(USART_CR3_ONEBIT | USART_CR3_NACK | USART_CR3_SCARCNT | \
215                                       USART_CR3_TXFTCFG | USART_CR3_RXFTCFG )) /*!< USART CR3 fields of parameters set by SMARTCARD_SetConfig API */
216 
217 #define USART_BRR_MIN  0x10U        /*!< USART BRR minimum authorized value */
218 
219 #define USART_BRR_MAX  0x0000FFFFU  /*!< USART BRR maximum authorized value */
220 /**
221   * @}
222   */
223 
224 /* Private macros ------------------------------------------------------------*/
225 /* Private variables ---------------------------------------------------------*/
226 /* Private function prototypes -----------------------------------------------*/
227 /** @addtogroup SMARTCARD_Private_Functions
228   * @{
229   */
230 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
231 void SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef *hsmartcard);
232 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
233 static HAL_StatusTypeDef SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef *hsmartcard);
234 static void SMARTCARD_AdvFeatureConfig(SMARTCARD_HandleTypeDef *hsmartcard);
235 static HAL_StatusTypeDef SMARTCARD_CheckIdleState(SMARTCARD_HandleTypeDef *hsmartcard);
236 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsmartcard, uint32_t Flag,
237                                                           FlagStatus Status, uint32_t Tickstart, uint32_t Timeout);
238 static void SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef *hsmartcard);
239 static void SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef *hsmartcard);
240 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma);
241 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma);
242 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma);
243 static void SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef *hdma);
244 static void SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef *hdma);
245 static void SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef *hdma);
246 static void SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
247 static void SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
248 static void SMARTCARD_TxISR(SMARTCARD_HandleTypeDef *hsmartcard);
249 static void SMARTCARD_TxISR_FIFOEN(SMARTCARD_HandleTypeDef *hsmartcard);
250 static void SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsmartcard);
251 static void SMARTCARD_RxISR(SMARTCARD_HandleTypeDef *hsmartcard);
252 static void SMARTCARD_RxISR_FIFOEN(SMARTCARD_HandleTypeDef *hsmartcard);
253 /**
254   * @}
255   */
256 
257 /* Exported functions --------------------------------------------------------*/
258 
259 /** @defgroup SMARTCARD_Exported_Functions SMARTCARD Exported Functions
260   * @{
261   */
262 
263 /** @defgroup SMARTCARD_Exported_Functions_Group1 Initialization and de-initialization functions
264   * @brief    Initialization and Configuration functions
265   *
266 @verbatim
267   ==============================================================================
268               ##### Initialization and Configuration functions #####
269   ==============================================================================
270   [..]
271   This subsection provides a set of functions allowing to initialize the USARTx
272   associated to the SmartCard.
273   (+) These parameters can be configured:
274       (++) Baud Rate
275       (++) Parity: parity should be enabled, frame Length is fixed to 8 bits plus parity
276       (++) Receiver/transmitter modes
277       (++) Synchronous mode (and if enabled, phase, polarity and last bit parameters)
278       (++) Prescaler value
279       (++) Guard bit time
280       (++) NACK enabling or disabling on transmission error
281 
282   (+) The following advanced features can be configured as well:
283       (++) TX and/or RX pin level inversion
284       (++) data logical level inversion
285       (++) RX and TX pins swap
286       (++) RX overrun detection disabling
287       (++) DMA disabling on RX error
288       (++) MSB first on communication line
289       (++) Time out enabling (and if activated, timeout value)
290       (++) Block length
291       (++) Auto-retry counter
292   [..]
293   The HAL_SMARTCARD_Init() API follows the USART synchronous configuration procedures
294   (details for the procedures are available in reference manual).
295 
296 @endverbatim
297 
298   The USART frame format is given in the following table:
299 
300     Table 1. USART frame format.
301     +---------------------------------------------------------------+
302     | M1M0 bits |  PCE bit  |            USART frame                |
303     |-----------------------|---------------------------------------|
304     |     01    |    1      |    | SB | 8 bit data | PB | STB |     |
305     +---------------------------------------------------------------+
306 
307 
308   * @{
309   */
310 
311 /**
312   * @brief  Initialize the SMARTCARD mode according to the specified
313   *         parameters in the SMARTCARD_HandleTypeDef and initialize the associated handle.
314   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
315   *                    the configuration information for the specified SMARTCARD module.
316   * @retval HAL status
317   */
HAL_SMARTCARD_Init(SMARTCARD_HandleTypeDef * hsmartcard)318 HAL_StatusTypeDef HAL_SMARTCARD_Init(SMARTCARD_HandleTypeDef *hsmartcard)
319 {
320   /* Check the SMARTCARD handle allocation */
321   if (hsmartcard == NULL)
322   {
323     return HAL_ERROR;
324   }
325 
326   /* Check the USART associated to the SMARTCARD handle */
327   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
328 
329   if (hsmartcard->gState == HAL_SMARTCARD_STATE_RESET)
330   {
331     /* Allocate lock resource and initialize it */
332     hsmartcard->Lock = HAL_UNLOCKED;
333 
334 #if USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1
335     SMARTCARD_InitCallbacksToDefault(hsmartcard);
336 
337     if (hsmartcard->MspInitCallback == NULL)
338     {
339       hsmartcard->MspInitCallback = HAL_SMARTCARD_MspInit;
340     }
341 
342     /* Init the low level hardware */
343     hsmartcard->MspInitCallback(hsmartcard);
344 #else
345     /* Init the low level hardware : GPIO, CLOCK */
346     HAL_SMARTCARD_MspInit(hsmartcard);
347 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
348   }
349 
350   hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY;
351 
352   /* Disable the Peripheral to set smartcard mode */
353   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
354 
355   /* In SmartCard mode, the following bits must be kept cleared:
356   - LINEN in the USART_CR2 register,
357   - HDSEL and IREN  bits in the USART_CR3 register.*/
358   CLEAR_BIT(hsmartcard->Instance->CR2, USART_CR2_LINEN);
359   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_HDSEL | USART_CR3_IREN));
360 
361   /* set the USART in SMARTCARD mode */
362   SET_BIT(hsmartcard->Instance->CR3, USART_CR3_SCEN);
363 
364   /* Set the SMARTCARD Communication parameters */
365   if (SMARTCARD_SetConfig(hsmartcard) == HAL_ERROR)
366   {
367     return HAL_ERROR;
368   }
369 
370   /* Set the SMARTCARD transmission completion indication */
371   SMARTCARD_TRANSMISSION_COMPLETION_SETTING(hsmartcard);
372 
373   if (hsmartcard->AdvancedInit.AdvFeatureInit != SMARTCARD_ADVFEATURE_NO_INIT)
374   {
375     SMARTCARD_AdvFeatureConfig(hsmartcard);
376   }
377 
378   /* Enable the Peripheral */
379   SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
380 
381   /* TEACK and/or REACK to check before moving hsmartcard->gState and hsmartcard->RxState to Ready */
382   return (SMARTCARD_CheckIdleState(hsmartcard));
383 }
384 
385 /**
386   * @brief  DeInitialize the SMARTCARD peripheral.
387   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
388   *                    the configuration information for the specified SMARTCARD module.
389   * @retval HAL status
390   */
HAL_SMARTCARD_DeInit(SMARTCARD_HandleTypeDef * hsmartcard)391 HAL_StatusTypeDef HAL_SMARTCARD_DeInit(SMARTCARD_HandleTypeDef *hsmartcard)
392 {
393   /* Check the SMARTCARD handle allocation */
394   if (hsmartcard == NULL)
395   {
396     return HAL_ERROR;
397   }
398 
399   /* Check the USART/UART associated to the SMARTCARD handle */
400   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
401 
402   hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY;
403 
404   /* Disable the Peripheral */
405   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
406 
407   WRITE_REG(hsmartcard->Instance->CR1, 0x0U);
408   WRITE_REG(hsmartcard->Instance->CR2, 0x0U);
409   WRITE_REG(hsmartcard->Instance->CR3, 0x0U);
410   WRITE_REG(hsmartcard->Instance->RTOR, 0x0U);
411   WRITE_REG(hsmartcard->Instance->GTPR, 0x0U);
412 
413   /* DeInit the low level hardware */
414 #if USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1
415   if (hsmartcard->MspDeInitCallback == NULL)
416   {
417     hsmartcard->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;
418   }
419   /* DeInit the low level hardware */
420   hsmartcard->MspDeInitCallback(hsmartcard);
421 #else
422   HAL_SMARTCARD_MspDeInit(hsmartcard);
423 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
424 
425   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
426   hsmartcard->gState    = HAL_SMARTCARD_STATE_RESET;
427   hsmartcard->RxState   = HAL_SMARTCARD_STATE_RESET;
428 
429   /* Process Unlock */
430   __HAL_UNLOCK(hsmartcard);
431 
432   return HAL_OK;
433 }
434 
435 /**
436   * @brief  Initialize the SMARTCARD MSP.
437   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
438   *                    the configuration information for the specified SMARTCARD module.
439   * @retval None
440   */
HAL_SMARTCARD_MspInit(SMARTCARD_HandleTypeDef * hsmartcard)441 __weak void HAL_SMARTCARD_MspInit(SMARTCARD_HandleTypeDef *hsmartcard)
442 {
443   /* Prevent unused argument(s) compilation warning */
444   UNUSED(hsmartcard);
445 
446   /* NOTE : This function should not be modified, when the callback is needed,
447             the HAL_SMARTCARD_MspInit can be implemented in the user file
448    */
449 }
450 
451 /**
452   * @brief  DeInitialize the SMARTCARD MSP.
453   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
454   *                    the configuration information for the specified SMARTCARD module.
455   * @retval None
456   */
HAL_SMARTCARD_MspDeInit(SMARTCARD_HandleTypeDef * hsmartcard)457 __weak void HAL_SMARTCARD_MspDeInit(SMARTCARD_HandleTypeDef *hsmartcard)
458 {
459   /* Prevent unused argument(s) compilation warning */
460   UNUSED(hsmartcard);
461 
462   /* NOTE : This function should not be modified, when the callback is needed,
463             the HAL_SMARTCARD_MspDeInit can be implemented in the user file
464    */
465 }
466 
467 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
468 /**
469   * @brief  Register a User SMARTCARD Callback
470   *         To be used instead of the weak predefined callback
471   * @note   The HAL_SMARTCARD_RegisterCallback() may be called before HAL_SMARTCARD_Init()
472   *         in HAL_SMARTCARD_STATE_RESET to register callbacks for HAL_SMARTCARD_MSPINIT_CB_ID
473   *         and HAL_SMARTCARD_MSPDEINIT_CB_ID
474   * @param  hsmartcard smartcard handle
475   * @param  CallbackID ID of the callback to be registered
476   *         This parameter can be one of the following values:
477   *           @arg @ref HAL_SMARTCARD_TX_COMPLETE_CB_ID Tx Complete Callback ID
478   *           @arg @ref HAL_SMARTCARD_RX_COMPLETE_CB_ID Rx Complete Callback ID
479   *           @arg @ref HAL_SMARTCARD_ERROR_CB_ID Error Callback ID
480   *           @arg @ref HAL_SMARTCARD_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
481   *           @arg @ref HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
482   *           @arg @ref HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
483   *           @arg @ref HAL_SMARTCARD_RX_FIFO_FULL_CB_ID Rx Fifo Full Callback ID
484   *           @arg @ref HAL_SMARTCARD_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty Callback ID
485   *           @arg @ref HAL_SMARTCARD_MSPINIT_CB_ID MspInit Callback ID
486   *           @arg @ref HAL_SMARTCARD_MSPDEINIT_CB_ID MspDeInit Callback ID
487   * @param  pCallback pointer to the Callback function
488   * @retval HAL status
489   */
HAL_SMARTCARD_RegisterCallback(SMARTCARD_HandleTypeDef * hsmartcard,HAL_SMARTCARD_CallbackIDTypeDef CallbackID,pSMARTCARD_CallbackTypeDef pCallback)490 HAL_StatusTypeDef HAL_SMARTCARD_RegisterCallback(SMARTCARD_HandleTypeDef *hsmartcard,
491                                                  HAL_SMARTCARD_CallbackIDTypeDef CallbackID,
492                                                  pSMARTCARD_CallbackTypeDef pCallback)
493 {
494   HAL_StatusTypeDef status = HAL_OK;
495 
496   if (pCallback == NULL)
497   {
498     /* Update the error code */
499     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
500 
501     return HAL_ERROR;
502   }
503 
504   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
505   {
506     switch (CallbackID)
507     {
508 
509       case HAL_SMARTCARD_TX_COMPLETE_CB_ID :
510         hsmartcard->TxCpltCallback = pCallback;
511         break;
512 
513       case HAL_SMARTCARD_RX_COMPLETE_CB_ID :
514         hsmartcard->RxCpltCallback = pCallback;
515         break;
516 
517       case HAL_SMARTCARD_ERROR_CB_ID :
518         hsmartcard->ErrorCallback = pCallback;
519         break;
520 
521       case HAL_SMARTCARD_ABORT_COMPLETE_CB_ID :
522         hsmartcard->AbortCpltCallback = pCallback;
523         break;
524 
525       case HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID :
526         hsmartcard->AbortTransmitCpltCallback = pCallback;
527         break;
528 
529       case HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID :
530         hsmartcard->AbortReceiveCpltCallback = pCallback;
531         break;
532 
533       case HAL_SMARTCARD_RX_FIFO_FULL_CB_ID :
534         hsmartcard->RxFifoFullCallback = pCallback;
535         break;
536 
537       case HAL_SMARTCARD_TX_FIFO_EMPTY_CB_ID :
538         hsmartcard->TxFifoEmptyCallback = pCallback;
539         break;
540 
541       case HAL_SMARTCARD_MSPINIT_CB_ID :
542         hsmartcard->MspInitCallback = pCallback;
543         break;
544 
545       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
546         hsmartcard->MspDeInitCallback = pCallback;
547         break;
548 
549       default :
550         /* Update the error code */
551         hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
552 
553         /* Return error status */
554         status =  HAL_ERROR;
555         break;
556     }
557   }
558   else if (hsmartcard->gState == HAL_SMARTCARD_STATE_RESET)
559   {
560     switch (CallbackID)
561     {
562       case HAL_SMARTCARD_MSPINIT_CB_ID :
563         hsmartcard->MspInitCallback = pCallback;
564         break;
565 
566       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
567         hsmartcard->MspDeInitCallback = pCallback;
568         break;
569 
570       default :
571         /* Update the error code */
572         hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
573 
574         /* Return error status */
575         status =  HAL_ERROR;
576         break;
577     }
578   }
579   else
580   {
581     /* Update the error code */
582     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
583 
584     /* Return error status */
585     status =  HAL_ERROR;
586   }
587 
588   return status;
589 }
590 
591 /**
592   * @brief  Unregister an SMARTCARD callback
593   *         SMARTCARD callback is redirected to the weak predefined callback
594   * @note   The HAL_SMARTCARD_UnRegisterCallback() may be called before HAL_SMARTCARD_Init()
595   *         in HAL_SMARTCARD_STATE_RESET to un-register callbacks for HAL_SMARTCARD_MSPINIT_CB_ID
596   *         and HAL_SMARTCARD_MSPDEINIT_CB_ID
597   * @param  hsmartcard smartcard handle
598   * @param  CallbackID ID of the callback to be unregistered
599   *         This parameter can be one of the following values:
600   *           @arg @ref HAL_SMARTCARD_TX_COMPLETE_CB_ID Tx Complete Callback ID
601   *           @arg @ref HAL_SMARTCARD_RX_COMPLETE_CB_ID Rx Complete Callback ID
602   *           @arg @ref HAL_SMARTCARD_ERROR_CB_ID Error Callback ID
603   *           @arg @ref HAL_SMARTCARD_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
604   *           @arg @ref HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
605   *           @arg @ref HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
606   *           @arg @ref HAL_SMARTCARD_RX_FIFO_FULL_CB_ID Rx Fifo Full Callback ID
607   *           @arg @ref HAL_SMARTCARD_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty Callback ID
608   *           @arg @ref HAL_SMARTCARD_MSPINIT_CB_ID MspInit Callback ID
609   *           @arg @ref HAL_SMARTCARD_MSPDEINIT_CB_ID MspDeInit Callback ID
610   * @retval HAL status
611   */
HAL_SMARTCARD_UnRegisterCallback(SMARTCARD_HandleTypeDef * hsmartcard,HAL_SMARTCARD_CallbackIDTypeDef CallbackID)612 HAL_StatusTypeDef HAL_SMARTCARD_UnRegisterCallback(SMARTCARD_HandleTypeDef *hsmartcard,
613                                                    HAL_SMARTCARD_CallbackIDTypeDef CallbackID)
614 {
615   HAL_StatusTypeDef status = HAL_OK;
616 
617   if (HAL_SMARTCARD_STATE_READY == hsmartcard->gState)
618   {
619     switch (CallbackID)
620     {
621       case HAL_SMARTCARD_TX_COMPLETE_CB_ID :
622         hsmartcard->TxCpltCallback = HAL_SMARTCARD_TxCpltCallback;                 /* Legacy weak TxCpltCallback */
623         break;
624 
625       case HAL_SMARTCARD_RX_COMPLETE_CB_ID :
626         hsmartcard->RxCpltCallback = HAL_SMARTCARD_RxCpltCallback;                 /* Legacy weak RxCpltCallback */
627         break;
628 
629       case HAL_SMARTCARD_ERROR_CB_ID :
630         hsmartcard->ErrorCallback = HAL_SMARTCARD_ErrorCallback;                   /* Legacy weak ErrorCallback  */
631         break;
632 
633       case HAL_SMARTCARD_ABORT_COMPLETE_CB_ID :
634         hsmartcard->AbortCpltCallback = HAL_SMARTCARD_AbortCpltCallback;           /* Legacy weak AbortCpltCallback */
635         break;
636 
637       case HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID :
638         hsmartcard->AbortTransmitCpltCallback = HAL_SMARTCARD_AbortTransmitCpltCallback; /* Legacy weak
639                                                                                             AbortTransmitCpltCallback*/
640         break;
641 
642       case HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID :
643         hsmartcard->AbortReceiveCpltCallback = HAL_SMARTCARD_AbortReceiveCpltCallback;  /* Legacy weak
644                                                                                            AbortReceiveCpltCallback */
645         break;
646 
647       case HAL_SMARTCARD_RX_FIFO_FULL_CB_ID :
648         hsmartcard->RxFifoFullCallback = HAL_SMARTCARDEx_RxFifoFullCallback;      /* Legacy weak RxFifoFullCallback */
649         break;
650 
651       case HAL_SMARTCARD_TX_FIFO_EMPTY_CB_ID :
652         hsmartcard->TxFifoEmptyCallback = HAL_SMARTCARDEx_TxFifoEmptyCallback;    /* Legacy weak TxFifoEmptyCallback */
653         break;
654 
655       case HAL_SMARTCARD_MSPINIT_CB_ID :
656         hsmartcard->MspInitCallback = HAL_SMARTCARD_MspInit;                       /* Legacy weak MspInitCallback  */
657         break;
658 
659       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
660         hsmartcard->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;                   /* Legacy weak MspDeInitCallback */
661         break;
662 
663       default :
664         /* Update the error code */
665         hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
666 
667         /* Return error status */
668         status =  HAL_ERROR;
669         break;
670     }
671   }
672   else if (HAL_SMARTCARD_STATE_RESET == hsmartcard->gState)
673   {
674     switch (CallbackID)
675     {
676       case HAL_SMARTCARD_MSPINIT_CB_ID :
677         hsmartcard->MspInitCallback = HAL_SMARTCARD_MspInit;
678         break;
679 
680       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
681         hsmartcard->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;
682         break;
683 
684       default :
685         /* Update the error code */
686         hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
687 
688         /* Return error status */
689         status =  HAL_ERROR;
690         break;
691     }
692   }
693   else
694   {
695     /* Update the error code */
696     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
697 
698     /* Return error status */
699     status =  HAL_ERROR;
700   }
701 
702   return status;
703 }
704 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
705 
706 /**
707   * @}
708   */
709 
710 /** @defgroup SMARTCARD_Exported_Functions_Group2 IO operation functions
711   * @brief    SMARTCARD Transmit and Receive functions
712   *
713 @verbatim
714   ==============================================================================
715                          ##### IO operation functions #####
716   ==============================================================================
717   [..]
718     This subsection provides a set of functions allowing to manage the SMARTCARD data transfers.
719 
720   [..]
721     Smartcard is a single wire half duplex communication protocol.
722     The Smartcard interface is designed to support asynchronous protocol Smartcards as
723     defined in the ISO 7816-3 standard. The USART should be configured as:
724     (+) 8 bits plus parity: where M=1 and PCE=1 in the USART_CR1 register
725     (+) 1.5 stop bits when transmitting and receiving: where STOP=11 in the USART_CR2 register.
726 
727   [..]
728     (#) There are two modes of transfer:
729         (##) Blocking mode: The communication is performed in polling mode.
730              The HAL status of all data processing is returned by the same function
731              after finishing transfer.
732         (##) Non-Blocking mode: The communication is performed using Interrupts
733              or DMA, the relevant API's return the HAL status.
734              The end of the data processing will be indicated through the
735              dedicated SMARTCARD IRQ when using Interrupt mode or the DMA IRQ when
736              using DMA mode.
737         (##) The HAL_SMARTCARD_TxCpltCallback(), HAL_SMARTCARD_RxCpltCallback() user callbacks
738              will be executed respectively at the end of the Transmit or Receive process
739              The HAL_SMARTCARD_ErrorCallback() user callback will be executed when a communication
740              error is detected.
741 
742     (#) Blocking mode APIs are :
743         (##) HAL_SMARTCARD_Transmit()
744         (##) HAL_SMARTCARD_Receive()
745 
746     (#) Non Blocking mode APIs with Interrupt are :
747         (##) HAL_SMARTCARD_Transmit_IT()
748         (##) HAL_SMARTCARD_Receive_IT()
749         (##) HAL_SMARTCARD_IRQHandler()
750 
751     (#) Non Blocking mode functions with DMA are :
752         (##) HAL_SMARTCARD_Transmit_DMA()
753         (##) HAL_SMARTCARD_Receive_DMA()
754 
755     (#) A set of Transfer Complete Callbacks are provided in non Blocking mode:
756         (##) HAL_SMARTCARD_TxCpltCallback()
757         (##) HAL_SMARTCARD_RxCpltCallback()
758         (##) HAL_SMARTCARD_ErrorCallback()
759 
760   [..]
761     (#) Non-Blocking mode transfers could be aborted using Abort API's :
762         (##) HAL_SMARTCARD_Abort()
763         (##) HAL_SMARTCARD_AbortTransmit()
764         (##) HAL_SMARTCARD_AbortReceive()
765         (##) HAL_SMARTCARD_Abort_IT()
766         (##) HAL_SMARTCARD_AbortTransmit_IT()
767         (##) HAL_SMARTCARD_AbortReceive_IT()
768 
769     (#) For Abort services based on interrupts (HAL_SMARTCARD_Abortxxx_IT),
770         a set of Abort Complete Callbacks are provided:
771         (##) HAL_SMARTCARD_AbortCpltCallback()
772         (##) HAL_SMARTCARD_AbortTransmitCpltCallback()
773         (##) HAL_SMARTCARD_AbortReceiveCpltCallback()
774 
775     (#) In Non-Blocking mode transfers, possible errors are split into 2 categories.
776         Errors are handled as follows :
777        (##) Error is considered as Recoverable and non blocking : Transfer could go till end, but error severity is
778            to be evaluated by user : this concerns Frame Error,
779            Parity Error or Noise Error in Interrupt mode reception .
780            Received character is then retrieved and stored in Rx buffer,
781            Error code is set to allow user to identify error type,
782            and HAL_SMARTCARD_ErrorCallback() user callback is executed. Transfer is kept ongoing on SMARTCARD side.
783            If user wants to abort it, Abort services should be called by user.
784        (##) Error is considered as Blocking : Transfer could not be completed properly and is aborted.
785            This concerns Frame Error in Interrupt mode transmission, Overrun Error in Interrupt
786            mode reception and all errors in DMA mode.
787            Error code is set to allow user to identify error type,
788            and HAL_SMARTCARD_ErrorCallback() user callback is executed.
789 
790 @endverbatim
791   * @{
792   */
793 
794 /**
795   * @brief  Send an amount of data in blocking mode.
796   * @note   When FIFO mode is enabled, writing a data in the TDR register adds one
797   *         data to the TXFIFO. Write operations to the TDR register are performed
798   *         when TXFNF flag is set. From hardware perspective, TXFNF flag and
799   *         TXE are mapped on the same bit-field.
800   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
801   *                    the configuration information for the specified SMARTCARD module.
802   * @param  pData pointer to data buffer.
803   * @param  Size amount of data to be sent.
804   * @param  Timeout  Timeout duration.
805   * @retval HAL status
806   */
HAL_SMARTCARD_Transmit(SMARTCARD_HandleTypeDef * hsmartcard,const uint8_t * pData,uint16_t Size,uint32_t Timeout)807 HAL_StatusTypeDef HAL_SMARTCARD_Transmit(SMARTCARD_HandleTypeDef *hsmartcard, const uint8_t *pData, uint16_t Size,
808                                          uint32_t Timeout)
809 {
810   uint32_t tickstart;
811   const uint8_t  *ptmpdata = pData;
812 
813   /* Check that a Tx process is not already ongoing */
814   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
815   {
816     if ((ptmpdata == NULL) || (Size == 0U))
817     {
818       return  HAL_ERROR;
819     }
820 
821     /* Process Locked */
822     __HAL_LOCK(hsmartcard);
823 
824     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
825 
826     /* Init tickstart for timeout management */
827     tickstart = HAL_GetTick();
828 
829     /* Disable the Peripheral first to update mode for TX master */
830     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
831 
832     /* In case of TX only mode, if NACK is enabled, the USART must be able to monitor
833        the bidirectional line to detect a NACK signal in case of parity error.
834        Therefore, the receiver block must be enabled as well (RE bit must be set). */
835     if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX)
836         && (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
837     {
838       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
839     }
840     /* Enable Tx */
841     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
842 
843     /* Enable the Peripheral */
844     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
845 
846     /* Perform a TX/RX FIFO Flush */
847     __HAL_SMARTCARD_FLUSH_DRREGISTER(hsmartcard);
848 
849     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
850     hsmartcard->TxXferSize = Size;
851     hsmartcard->TxXferCount = Size;
852 
853     while (hsmartcard->TxXferCount > 0U)
854     {
855       hsmartcard->TxXferCount--;
856       if (SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_FLAG_TXE, RESET, tickstart, Timeout) != HAL_OK)
857       {
858         return HAL_TIMEOUT;
859       }
860       hsmartcard->Instance->TDR = (uint8_t)(*ptmpdata & 0xFFU);
861       ptmpdata++;
862     }
863     if (SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_TRANSMISSION_COMPLETION_FLAG(hsmartcard), RESET,
864                                          tickstart, Timeout) != HAL_OK)
865     {
866       return HAL_TIMEOUT;
867     }
868 
869     /* Disable the Peripheral first to update mode */
870     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
871     if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX)
872         && (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
873     {
874       /* In case of TX only mode, if NACK is enabled, receiver block has been enabled
875          for Transmit phase. Disable this receiver block. */
876       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
877     }
878     if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX_RX)
879         || (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
880     {
881       /* Perform a TX FIFO Flush at end of Tx phase, as all sent bytes are appearing in Rx Data register */
882       __HAL_SMARTCARD_FLUSH_DRREGISTER(hsmartcard);
883     }
884     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
885 
886     /* At end of Tx process, restore hsmartcard->gState to Ready */
887     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
888 
889     /* Process Unlocked */
890     __HAL_UNLOCK(hsmartcard);
891 
892     return HAL_OK;
893   }
894   else
895   {
896     return HAL_BUSY;
897   }
898 }
899 
900 /**
901   * @brief  Receive an amount of data in blocking mode.
902   * @note   When FIFO mode is enabled, the RXFNE flag is set as long as the RXFIFO
903   *         is not empty. Read operations from the RDR register are performed when
904   *         RXFNE flag is set. From hardware perspective, RXFNE flag and
905   *         RXNE are mapped on the same bit-field.
906   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
907   *                    the configuration information for the specified SMARTCARD module.
908   * @param  pData pointer to data buffer.
909   * @param  Size amount of data to be received.
910   * @param  Timeout Timeout duration.
911   * @retval HAL status
912   */
HAL_SMARTCARD_Receive(SMARTCARD_HandleTypeDef * hsmartcard,uint8_t * pData,uint16_t Size,uint32_t Timeout)913 HAL_StatusTypeDef HAL_SMARTCARD_Receive(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size,
914                                         uint32_t Timeout)
915 {
916   uint32_t tickstart;
917   uint8_t  *ptmpdata = pData;
918 
919   /* Check that a Rx process is not already ongoing */
920   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
921   {
922     if ((ptmpdata == NULL) || (Size == 0U))
923     {
924       return  HAL_ERROR;
925     }
926 
927     /* Process Locked */
928     __HAL_LOCK(hsmartcard);
929 
930     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
931     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
932 
933     /* Init tickstart for timeout management */
934     tickstart = HAL_GetTick();
935 
936     hsmartcard->RxXferSize = Size;
937     hsmartcard->RxXferCount = Size;
938 
939     /* Check the remain data to be received */
940     while (hsmartcard->RxXferCount > 0U)
941     {
942       hsmartcard->RxXferCount--;
943 
944       if (SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_FLAG_RXNE, RESET, tickstart, Timeout) != HAL_OK)
945       {
946         return HAL_TIMEOUT;
947       }
948       *ptmpdata = (uint8_t)(hsmartcard->Instance->RDR & (uint8_t)0x00FF);
949       ptmpdata++;
950     }
951 
952     /* At end of Rx process, restore hsmartcard->RxState to Ready */
953     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
954 
955     /* Process Unlocked */
956     __HAL_UNLOCK(hsmartcard);
957 
958     return HAL_OK;
959   }
960   else
961   {
962     return HAL_BUSY;
963   }
964 }
965 
966 /**
967   * @brief  Send an amount of data in interrupt mode.
968   * @note   When FIFO mode is disabled, USART interrupt is generated whenever
969   *         USART_TDR register is empty, i.e one interrupt per data to transmit.
970   * @note   When FIFO mode is enabled, USART interrupt is generated whenever
971   *         TXFIFO threshold reached. In that case the interrupt rate depends on
972   *         TXFIFO threshold configuration.
973   * @note   This function sets the hsmartcard->TxIsr function pointer according to
974   *         the FIFO mode (data transmission processing depends on FIFO mode).
975   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
976   *                    the configuration information for the specified SMARTCARD module.
977   * @param  pData pointer to data buffer.
978   * @param  Size amount of data to be sent.
979   * @retval HAL status
980   */
HAL_SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef * hsmartcard,const uint8_t * pData,uint16_t Size)981 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsmartcard, const uint8_t *pData, uint16_t Size)
982 {
983   /* Check that a Tx process is not already ongoing */
984   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
985   {
986     if ((pData == NULL) || (Size == 0U))
987     {
988       return HAL_ERROR;
989     }
990 
991     /* Process Locked */
992     __HAL_LOCK(hsmartcard);
993 
994     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
995     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
996 
997     hsmartcard->pTxBuffPtr  = pData;
998     hsmartcard->TxXferSize  = Size;
999     hsmartcard->TxXferCount = Size;
1000     hsmartcard->TxISR       = NULL;
1001 
1002     /* Disable the Peripheral first to update mode for TX master */
1003     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
1004 
1005     /* In case of TX only mode, if NACK is enabled, the USART must be able to monitor
1006        the bidirectional line to detect a NACK signal in case of parity error.
1007        Therefore, the receiver block must be enabled as well (RE bit must be set). */
1008     if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX)
1009         && (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
1010     {
1011       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
1012     }
1013     /* Enable Tx */
1014     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
1015 
1016     /* Enable the Peripheral */
1017     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
1018 
1019     /* Perform a TX/RX FIFO Flush */
1020     __HAL_SMARTCARD_FLUSH_DRREGISTER(hsmartcard);
1021 
1022     /* Configure Tx interrupt processing */
1023     if (hsmartcard->FifoMode == SMARTCARD_FIFOMODE_ENABLE)
1024     {
1025       /* Set the Tx ISR function pointer */
1026       hsmartcard->TxISR = SMARTCARD_TxISR_FIFOEN;
1027 
1028       /* Process Unlocked */
1029       __HAL_UNLOCK(hsmartcard);
1030 
1031       /* Enable the SMARTCARD Error Interrupt: (Frame error) */
1032       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1033 
1034       /* Enable the TX FIFO threshold interrupt */
1035       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_TXFTIE);
1036     }
1037     else
1038     {
1039       /* Set the Tx ISR function pointer */
1040       hsmartcard->TxISR = SMARTCARD_TxISR;
1041 
1042       /* Process Unlocked */
1043       __HAL_UNLOCK(hsmartcard);
1044 
1045       /* Enable the SMARTCARD Error Interrupt: (Frame error) */
1046       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1047 
1048       /* Enable the SMARTCARD Transmit Data Register Empty Interrupt */
1049       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
1050     }
1051 
1052     return HAL_OK;
1053   }
1054   else
1055   {
1056     return HAL_BUSY;
1057   }
1058 }
1059 
1060 /**
1061   * @brief  Receive an amount of data in interrupt mode.
1062   * @note   When FIFO mode is disabled, USART interrupt is generated whenever
1063   *         USART_RDR register can be read, i.e one interrupt per data to receive.
1064   * @note   When FIFO mode is enabled, USART interrupt is generated whenever
1065   *         RXFIFO threshold reached. In that case the interrupt rate depends on
1066   *         RXFIFO threshold configuration.
1067   * @note   This function sets the hsmartcard->RxIsr function pointer according to
1068   *         the FIFO mode (data reception processing depends on FIFO mode).
1069   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1070   *                    the configuration information for the specified SMARTCARD module.
1071   * @param  pData pointer to data buffer.
1072   * @param  Size amount of data to be received.
1073   * @retval HAL status
1074   */
HAL_SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef * hsmartcard,uint8_t * pData,uint16_t Size)1075 HAL_StatusTypeDef HAL_SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
1076 {
1077   /* Check that a Rx process is not already ongoing */
1078   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
1079   {
1080     if ((pData == NULL) || (Size == 0U))
1081     {
1082       return HAL_ERROR;
1083     }
1084 
1085     /* Process Locked */
1086     __HAL_LOCK(hsmartcard);
1087 
1088     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1089     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
1090 
1091     hsmartcard->pRxBuffPtr = pData;
1092     hsmartcard->RxXferSize = Size;
1093     hsmartcard->RxXferCount = Size;
1094 
1095     /* Configure Rx interrupt processing */
1096     if ((hsmartcard->FifoMode == SMARTCARD_FIFOMODE_ENABLE) && (Size >= hsmartcard->NbRxDataToProcess))
1097     {
1098       /* Set the Rx ISR function pointer */
1099       hsmartcard->RxISR = SMARTCARD_RxISR_FIFOEN;
1100 
1101       /* Process Unlocked */
1102       __HAL_UNLOCK(hsmartcard);
1103 
1104       /* Enable the SMARTCART Parity Error interrupt and RX FIFO Threshold interrupt */
1105       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE);
1106       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_RXFTIE);
1107     }
1108     else
1109     {
1110       /* Set the Rx ISR function pointer */
1111       hsmartcard->RxISR = SMARTCARD_RxISR;
1112 
1113       /* Process Unlocked */
1114       __HAL_UNLOCK(hsmartcard);
1115 
1116       /* Enable the SMARTCARD Parity Error and Data Register not empty Interrupts */
1117       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE | USART_CR1_RXNEIE_RXFNEIE);
1118     }
1119 
1120     /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
1121     SET_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1122 
1123     return HAL_OK;
1124   }
1125   else
1126   {
1127     return HAL_BUSY;
1128   }
1129 }
1130 
1131 /**
1132   * @brief  Send an amount of data in DMA mode.
1133   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1134   *                    the configuration information for the specified SMARTCARD module.
1135   * @param  pData pointer to data buffer.
1136   * @param  Size amount of data to be sent.
1137   * @retval HAL status
1138   */
HAL_SMARTCARD_Transmit_DMA(SMARTCARD_HandleTypeDef * hsmartcard,const uint8_t * pData,uint16_t Size)1139 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_DMA(SMARTCARD_HandleTypeDef *hsmartcard, const uint8_t *pData, uint16_t Size)
1140 {
1141   /* Check that a Tx process is not already ongoing */
1142   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
1143   {
1144     if ((pData == NULL) || (Size == 0U))
1145     {
1146       return HAL_ERROR;
1147     }
1148 
1149     /* Process Locked */
1150     __HAL_LOCK(hsmartcard);
1151 
1152     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
1153 
1154     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1155     hsmartcard->pTxBuffPtr = pData;
1156     hsmartcard->TxXferSize = Size;
1157     hsmartcard->TxXferCount = Size;
1158 
1159     /* Disable the Peripheral first to update mode for TX master */
1160     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
1161 
1162     /* In case of TX only mode, if NACK is enabled, the USART must be able to monitor
1163        the bidirectional line to detect a NACK signal in case of parity error.
1164        Therefore, the receiver block must be enabled as well (RE bit must be set). */
1165     if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX)
1166         && (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
1167     {
1168       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
1169     }
1170     /* Enable Tx */
1171     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
1172 
1173     /* Enable the Peripheral */
1174     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
1175 
1176     /* Perform a TX/RX FIFO Flush */
1177     __HAL_SMARTCARD_FLUSH_DRREGISTER(hsmartcard);
1178 
1179     /* Set the SMARTCARD DMA transfer complete callback */
1180     hsmartcard->hdmatx->XferCpltCallback = SMARTCARD_DMATransmitCplt;
1181 
1182     /* Set the SMARTCARD error callback */
1183     hsmartcard->hdmatx->XferErrorCallback = SMARTCARD_DMAError;
1184 
1185     /* Set the DMA abort callback */
1186     hsmartcard->hdmatx->XferAbortCallback = NULL;
1187 
1188     /* Enable the SMARTCARD transmit DMA channel */
1189     if (HAL_DMA_Start_IT(hsmartcard->hdmatx, (uint32_t)hsmartcard->pTxBuffPtr, (uint32_t)&hsmartcard->Instance->TDR,
1190                          Size) == HAL_OK)
1191     {
1192       /* Clear the TC flag in the ICR register */
1193       CLEAR_BIT(hsmartcard->Instance->ICR, USART_ICR_TCCF);
1194 
1195       /* Process Unlocked */
1196       __HAL_UNLOCK(hsmartcard);
1197 
1198       /* Enable the UART Error Interrupt: (Frame error) */
1199       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1200 
1201       /* Enable the DMA transfer for transmit request by setting the DMAT bit
1202          in the SMARTCARD associated USART CR3 register */
1203       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
1204 
1205       return HAL_OK;
1206     }
1207     else
1208     {
1209       /* Set error code to DMA */
1210       hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1211 
1212       /* Process Unlocked */
1213       __HAL_UNLOCK(hsmartcard);
1214 
1215       /* Restore hsmartcard->State to ready */
1216       hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
1217 
1218       return HAL_ERROR;
1219     }
1220   }
1221   else
1222   {
1223     return HAL_BUSY;
1224   }
1225 }
1226 
1227 /**
1228   * @brief  Receive an amount of data in DMA mode.
1229   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1230   *                    the configuration information for the specified SMARTCARD module.
1231   * @param  pData pointer to data buffer.
1232   * @param  Size amount of data to be received.
1233   * @note   The SMARTCARD-associated USART parity is enabled (PCE = 1),
1234   *         the received data contain the parity bit (MSB position).
1235   * @retval HAL status
1236   */
HAL_SMARTCARD_Receive_DMA(SMARTCARD_HandleTypeDef * hsmartcard,uint8_t * pData,uint16_t Size)1237 HAL_StatusTypeDef HAL_SMARTCARD_Receive_DMA(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
1238 {
1239   /* Check that a Rx process is not already ongoing */
1240   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
1241   {
1242     if ((pData == NULL) || (Size == 0U))
1243     {
1244       return HAL_ERROR;
1245     }
1246 
1247     /* Process Locked */
1248     __HAL_LOCK(hsmartcard);
1249 
1250     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1251     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
1252 
1253     hsmartcard->pRxBuffPtr = pData;
1254     hsmartcard->RxXferSize = Size;
1255 
1256     /* Set the SMARTCARD DMA transfer complete callback */
1257     hsmartcard->hdmarx->XferCpltCallback = SMARTCARD_DMAReceiveCplt;
1258 
1259     /* Set the SMARTCARD DMA error callback */
1260     hsmartcard->hdmarx->XferErrorCallback = SMARTCARD_DMAError;
1261 
1262     /* Set the DMA abort callback */
1263     hsmartcard->hdmarx->XferAbortCallback = NULL;
1264 
1265     /* Enable the DMA channel */
1266     if (HAL_DMA_Start_IT(hsmartcard->hdmarx, (uint32_t)&hsmartcard->Instance->RDR, (uint32_t)hsmartcard->pRxBuffPtr,
1267                          Size) == HAL_OK)
1268     {
1269       /* Process Unlocked */
1270       __HAL_UNLOCK(hsmartcard);
1271 
1272       /* Enable the SMARTCARD Parity Error Interrupt */
1273       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE);
1274 
1275       /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
1276       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1277 
1278       /* Enable the DMA transfer for the receiver request by setting the DMAR bit
1279          in the SMARTCARD associated USART CR3 register */
1280       SET_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1281 
1282       return HAL_OK;
1283     }
1284     else
1285     {
1286       /* Set error code to DMA */
1287       hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1288 
1289       /* Process Unlocked */
1290       __HAL_UNLOCK(hsmartcard);
1291 
1292       /* Restore hsmartcard->State to ready */
1293       hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1294 
1295       return HAL_ERROR;
1296     }
1297   }
1298   else
1299   {
1300     return HAL_BUSY;
1301   }
1302 }
1303 
1304 /**
1305   * @brief  Abort ongoing transfers (blocking mode).
1306   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1307   *                    the configuration information for the specified SMARTCARD module.
1308   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1309   *         This procedure performs following operations :
1310   *           - Disable SMARTCARD Interrupts (Tx and Rx)
1311   *           - Disable the DMA transfer in the peripheral register (if enabled)
1312   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1313   *           - Set handle State to READY
1314   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1315   * @retval HAL status
1316   */
HAL_SMARTCARD_Abort(SMARTCARD_HandleTypeDef * hsmartcard)1317 HAL_StatusTypeDef HAL_SMARTCARD_Abort(SMARTCARD_HandleTypeDef *hsmartcard)
1318 {
1319   /* Disable RTOIE, EOBIE, TXEIE, TCIE, RXNE, PE, RXFT, TXFT and
1320      ERR (Frame error, noise error, overrun error) interrupts */
1321   CLEAR_BIT(hsmartcard->Instance->CR1,
1322             (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE | USART_CR1_RTOIE |
1323              USART_CR1_EOBIE));
1324   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE | USART_CR3_TXFTIE));
1325 
1326   /* Disable the SMARTCARD DMA Tx request if enabled */
1327   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
1328   {
1329     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
1330 
1331     /* Abort the SMARTCARD DMA Tx channel : use blocking DMA Abort API (no callback) */
1332     if (hsmartcard->hdmatx != NULL)
1333     {
1334       /* Set the SMARTCARD DMA Abort callback to Null.
1335          No call back execution at end of DMA abort procedure */
1336       hsmartcard->hdmatx->XferAbortCallback = NULL;
1337 
1338       if (HAL_DMA_Abort(hsmartcard->hdmatx) != HAL_OK)
1339       {
1340         if (HAL_DMA_GetError(hsmartcard->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
1341         {
1342           /* Set error code to DMA */
1343           hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1344 
1345           return HAL_TIMEOUT;
1346         }
1347       }
1348     }
1349   }
1350 
1351   /* Disable the SMARTCARD DMA Rx request if enabled */
1352   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1353   {
1354     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1355 
1356     /* Abort the SMARTCARD DMA Rx channel : use blocking DMA Abort API (no callback) */
1357     if (hsmartcard->hdmarx != NULL)
1358     {
1359       /* Set the SMARTCARD DMA Abort callback to Null.
1360          No call back execution at end of DMA abort procedure */
1361       hsmartcard->hdmarx->XferAbortCallback = NULL;
1362 
1363       if (HAL_DMA_Abort(hsmartcard->hdmarx) != HAL_OK)
1364       {
1365         if (HAL_DMA_GetError(hsmartcard->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
1366         {
1367           /* Set error code to DMA */
1368           hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1369 
1370           return HAL_TIMEOUT;
1371         }
1372       }
1373     }
1374   }
1375 
1376   /* Reset Tx and Rx transfer counters */
1377   hsmartcard->TxXferCount = 0U;
1378   hsmartcard->RxXferCount = 0U;
1379 
1380   /* Clear the Error flags in the ICR register */
1381   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
1382                              SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF | SMARTCARD_CLEAR_FEF |
1383                              SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
1384 
1385   /* Restore hsmartcard->gState and hsmartcard->RxState to Ready */
1386   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
1387   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1388 
1389   /* Reset Handle ErrorCode to No Error */
1390   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1391 
1392   return HAL_OK;
1393 }
1394 
1395 /**
1396   * @brief  Abort ongoing Transmit transfer (blocking mode).
1397   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1398   *                    the configuration information for the specified SMARTCARD module.
1399   * @note   This procedure could be used for aborting any ongoing Tx transfer started in Interrupt or DMA mode.
1400   *         This procedure performs following operations :
1401   *           - Disable SMARTCARD Interrupts (Tx)
1402   *           - Disable the DMA transfer in the peripheral register (if enabled)
1403   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1404   *           - Set handle State to READY
1405   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1406   * @retval HAL status
1407   */
HAL_SMARTCARD_AbortTransmit(SMARTCARD_HandleTypeDef * hsmartcard)1408 HAL_StatusTypeDef HAL_SMARTCARD_AbortTransmit(SMARTCARD_HandleTypeDef *hsmartcard)
1409 {
1410   /* Disable TCIE, TXEIE and TXFTIE interrupts */
1411   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE));
1412   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_TXFTIE);
1413 
1414   /* Check if a receive process is ongoing or not. If not disable ERR IT */
1415   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
1416   {
1417     /* Disable the SMARTCARD Error Interrupt: (Frame error) */
1418     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1419   }
1420 
1421   /* Disable the SMARTCARD DMA Tx request if enabled */
1422   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
1423   {
1424     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
1425 
1426     /* Abort the SMARTCARD DMA Tx channel : use blocking DMA Abort API (no callback) */
1427     if (hsmartcard->hdmatx != NULL)
1428     {
1429       /* Set the SMARTCARD DMA Abort callback to Null.
1430          No call back execution at end of DMA abort procedure */
1431       hsmartcard->hdmatx->XferAbortCallback = NULL;
1432 
1433       if (HAL_DMA_Abort(hsmartcard->hdmatx) != HAL_OK)
1434       {
1435         if (HAL_DMA_GetError(hsmartcard->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
1436         {
1437           /* Set error code to DMA */
1438           hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1439 
1440           return HAL_TIMEOUT;
1441         }
1442       }
1443     }
1444   }
1445 
1446   /* Reset Tx transfer counter */
1447   hsmartcard->TxXferCount = 0U;
1448 
1449   /* Clear the Error flags in the ICR register */
1450   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard, SMARTCARD_CLEAR_FEF);
1451 
1452   /* Restore hsmartcard->gState to Ready */
1453   hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
1454 
1455   return HAL_OK;
1456 }
1457 
1458 /**
1459   * @brief  Abort ongoing Receive transfer (blocking mode).
1460   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1461   *                    the configuration information for the specified SMARTCARD module.
1462   * @note   This procedure could be used for aborting any ongoing Rx transfer started in Interrupt or DMA mode.
1463   *         This procedure performs following operations :
1464   *           - Disable SMARTCARD Interrupts (Rx)
1465   *           - Disable the DMA transfer in the peripheral register (if enabled)
1466   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1467   *           - Set handle State to READY
1468   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1469   * @retval HAL status
1470   */
HAL_SMARTCARD_AbortReceive(SMARTCARD_HandleTypeDef * hsmartcard)1471 HAL_StatusTypeDef HAL_SMARTCARD_AbortReceive(SMARTCARD_HandleTypeDef *hsmartcard)
1472 {
1473   /* Disable RTOIE, EOBIE, RXNE, PE, RXFT, TXFT and  ERR (Frame error, noise error, overrun error) interrupts */
1474   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_RTOIE |
1475                                         USART_CR1_EOBIE));
1476   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
1477 
1478   /* Check if a Transmit process is ongoing or not. If not disable ERR IT */
1479   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
1480   {
1481     /* Disable the SMARTCARD Error Interrupt: (Frame error) */
1482     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1483   }
1484 
1485   /* Disable the SMARTCARD DMA Rx request if enabled */
1486   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1487   {
1488     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1489 
1490     /* Abort the SMARTCARD DMA Rx channel : use blocking DMA Abort API (no callback) */
1491     if (hsmartcard->hdmarx != NULL)
1492     {
1493       /* Set the SMARTCARD DMA Abort callback to Null.
1494          No call back execution at end of DMA abort procedure */
1495       hsmartcard->hdmarx->XferAbortCallback = NULL;
1496 
1497       if (HAL_DMA_Abort(hsmartcard->hdmarx) != HAL_OK)
1498       {
1499         if (HAL_DMA_GetError(hsmartcard->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
1500         {
1501           /* Set error code to DMA */
1502           hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1503 
1504           return HAL_TIMEOUT;
1505         }
1506       }
1507     }
1508   }
1509 
1510   /* Reset Rx transfer counter */
1511   hsmartcard->RxXferCount = 0U;
1512 
1513   /* Clear the Error flags in the ICR register */
1514   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
1515                              SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF | SMARTCARD_CLEAR_FEF |
1516                              SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
1517 
1518   /* Restore hsmartcard->RxState to Ready */
1519   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1520 
1521   return HAL_OK;
1522 }
1523 
1524 /**
1525   * @brief  Abort ongoing transfers (Interrupt mode).
1526   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1527   *                    the configuration information for the specified SMARTCARD module.
1528   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1529   *         This procedure performs following operations :
1530   *           - Disable SMARTCARD Interrupts (Tx and Rx)
1531   *           - Disable the DMA transfer in the peripheral register (if enabled)
1532   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1533   *           - Set handle State to READY
1534   *           - At abort completion, call user abort complete callback
1535   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1536   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1537   * @retval HAL status
1538   */
HAL_SMARTCARD_Abort_IT(SMARTCARD_HandleTypeDef * hsmartcard)1539 HAL_StatusTypeDef HAL_SMARTCARD_Abort_IT(SMARTCARD_HandleTypeDef *hsmartcard)
1540 {
1541   uint32_t abortcplt = 1U;
1542 
1543   /* Disable RTOIE, EOBIE, TXEIE, TCIE, RXNE, PE, RXFT, TXFT and
1544      ERR (Frame error, noise error, overrun error) interrupts */
1545   CLEAR_BIT(hsmartcard->Instance->CR1,
1546             (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE | USART_CR1_RTOIE |
1547              USART_CR1_EOBIE));
1548   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE | USART_CR3_TXFTIE));
1549 
1550   /* If DMA Tx and/or DMA Rx Handles are associated to SMARTCARD Handle,
1551      DMA Abort complete callbacks should be initialised before any call
1552      to DMA Abort functions */
1553   /* DMA Tx Handle is valid */
1554   if (hsmartcard->hdmatx != NULL)
1555   {
1556     /* Set DMA Abort Complete callback if SMARTCARD DMA Tx request if enabled.
1557        Otherwise, set it to NULL */
1558     if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
1559     {
1560       hsmartcard->hdmatx->XferAbortCallback = SMARTCARD_DMATxAbortCallback;
1561     }
1562     else
1563     {
1564       hsmartcard->hdmatx->XferAbortCallback = NULL;
1565     }
1566   }
1567   /* DMA Rx Handle is valid */
1568   if (hsmartcard->hdmarx != NULL)
1569   {
1570     /* Set DMA Abort Complete callback if SMARTCARD DMA Rx request if enabled.
1571        Otherwise, set it to NULL */
1572     if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1573     {
1574       hsmartcard->hdmarx->XferAbortCallback = SMARTCARD_DMARxAbortCallback;
1575     }
1576     else
1577     {
1578       hsmartcard->hdmarx->XferAbortCallback = NULL;
1579     }
1580   }
1581 
1582   /* Disable the SMARTCARD DMA Tx request if enabled */
1583   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
1584   {
1585     /* Disable DMA Tx at UART level */
1586     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
1587 
1588     /* Abort the SMARTCARD DMA Tx channel : use non blocking DMA Abort API (callback) */
1589     if (hsmartcard->hdmatx != NULL)
1590     {
1591       /* SMARTCARD Tx DMA Abort callback has already been initialised :
1592          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1593 
1594       /* Abort DMA TX */
1595       if (HAL_DMA_Abort_IT(hsmartcard->hdmatx) != HAL_OK)
1596       {
1597         hsmartcard->hdmatx->XferAbortCallback = NULL;
1598       }
1599       else
1600       {
1601         abortcplt = 0U;
1602       }
1603     }
1604   }
1605 
1606   /* Disable the SMARTCARD DMA Rx request if enabled */
1607   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1608   {
1609     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1610 
1611     /* Abort the SMARTCARD DMA Rx channel : use non blocking DMA Abort API (callback) */
1612     if (hsmartcard->hdmarx != NULL)
1613     {
1614       /* SMARTCARD Rx DMA Abort callback has already been initialised :
1615          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1616 
1617       /* Abort DMA RX */
1618       if (HAL_DMA_Abort_IT(hsmartcard->hdmarx) != HAL_OK)
1619       {
1620         hsmartcard->hdmarx->XferAbortCallback = NULL;
1621         abortcplt = 1U;
1622       }
1623       else
1624       {
1625         abortcplt = 0U;
1626       }
1627     }
1628   }
1629 
1630   /* if no DMA abort complete callback execution is required => call user Abort Complete callback */
1631   if (abortcplt == 1U)
1632   {
1633     /* Reset Tx and Rx transfer counters */
1634     hsmartcard->TxXferCount = 0U;
1635     hsmartcard->RxXferCount = 0U;
1636 
1637     /* Clear ISR function pointers */
1638     hsmartcard->RxISR = NULL;
1639     hsmartcard->TxISR = NULL;
1640 
1641     /* Reset errorCode */
1642     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1643 
1644     /* Clear the Error flags in the ICR register */
1645     __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
1646                                SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF |
1647                                SMARTCARD_CLEAR_FEF | SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
1648 
1649     /* Restore hsmartcard->gState and hsmartcard->RxState to Ready */
1650     hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
1651     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1652 
1653     /* As no DMA to be aborted, call directly user Abort complete callback */
1654 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1655     /* Call registered Abort complete callback */
1656     hsmartcard->AbortCpltCallback(hsmartcard);
1657 #else
1658     /* Call legacy weak Abort complete callback */
1659     HAL_SMARTCARD_AbortCpltCallback(hsmartcard);
1660 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1661   }
1662 
1663   return HAL_OK;
1664 }
1665 
1666 /**
1667   * @brief  Abort ongoing Transmit transfer (Interrupt mode).
1668   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1669   *                    the configuration information for the specified SMARTCARD module.
1670   * @note   This procedure could be used for aborting any ongoing Tx transfer started in Interrupt or DMA mode.
1671   *         This procedure performs following operations :
1672   *           - Disable SMARTCARD Interrupts (Tx)
1673   *           - Disable the DMA transfer in the peripheral register (if enabled)
1674   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1675   *           - Set handle State to READY
1676   *           - At abort completion, call user abort complete callback
1677   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1678   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1679   * @retval HAL status
1680   */
HAL_SMARTCARD_AbortTransmit_IT(SMARTCARD_HandleTypeDef * hsmartcard)1681 HAL_StatusTypeDef HAL_SMARTCARD_AbortTransmit_IT(SMARTCARD_HandleTypeDef *hsmartcard)
1682 {
1683   /* Disable TCIE, TXEIE and TXFTIE interrupts */
1684   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE));
1685   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_TXFTIE);
1686 
1687   /* Check if a receive process is ongoing or not. If not disable ERR IT */
1688   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
1689   {
1690     /* Disable the SMARTCARD Error Interrupt: (Frame error) */
1691     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1692   }
1693 
1694   /* Disable the SMARTCARD DMA Tx request if enabled */
1695   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
1696   {
1697     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
1698 
1699     /* Abort the SMARTCARD DMA Tx channel : use non blocking DMA Abort API (callback) */
1700     if (hsmartcard->hdmatx != NULL)
1701     {
1702       /* Set the SMARTCARD DMA Abort callback :
1703          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1704       hsmartcard->hdmatx->XferAbortCallback = SMARTCARD_DMATxOnlyAbortCallback;
1705 
1706       /* Abort DMA TX */
1707       if (HAL_DMA_Abort_IT(hsmartcard->hdmatx) != HAL_OK)
1708       {
1709         /* Call Directly hsmartcard->hdmatx->XferAbortCallback function in case of error */
1710         hsmartcard->hdmatx->XferAbortCallback(hsmartcard->hdmatx);
1711       }
1712     }
1713     else
1714     {
1715       /* Reset Tx transfer counter */
1716       hsmartcard->TxXferCount = 0U;
1717 
1718       /* Clear TxISR function pointers */
1719       hsmartcard->TxISR = NULL;
1720 
1721       /* Restore hsmartcard->gState to Ready */
1722       hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
1723 
1724       /* As no DMA to be aborted, call directly user Abort complete callback */
1725 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1726       /* Call registered Abort Transmit Complete Callback */
1727       hsmartcard->AbortTransmitCpltCallback(hsmartcard);
1728 #else
1729       /* Call legacy weak Abort Transmit Complete Callback */
1730       HAL_SMARTCARD_AbortTransmitCpltCallback(hsmartcard);
1731 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1732     }
1733   }
1734   else
1735   {
1736     /* Reset Tx transfer counter */
1737     hsmartcard->TxXferCount = 0U;
1738 
1739     /* Clear TxISR function pointers */
1740     hsmartcard->TxISR = NULL;
1741 
1742     /* Clear the Error flags in the ICR register */
1743     __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard, SMARTCARD_CLEAR_FEF);
1744 
1745     /* Restore hsmartcard->gState to Ready */
1746     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
1747 
1748     /* As no DMA to be aborted, call directly user Abort complete callback */
1749 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1750     /* Call registered Abort Transmit Complete Callback */
1751     hsmartcard->AbortTransmitCpltCallback(hsmartcard);
1752 #else
1753     /* Call legacy weak Abort Transmit Complete Callback */
1754     HAL_SMARTCARD_AbortTransmitCpltCallback(hsmartcard);
1755 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1756   }
1757 
1758   return HAL_OK;
1759 }
1760 
1761 /**
1762   * @brief  Abort ongoing Receive transfer (Interrupt mode).
1763   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1764   *                    the configuration information for the specified SMARTCARD module.
1765   * @note   This procedure could be used for aborting any ongoing Rx transfer started in Interrupt or DMA mode.
1766   *         This procedure performs following operations :
1767   *           - Disable SMARTCARD Interrupts (Rx)
1768   *           - Disable the DMA transfer in the peripheral register (if enabled)
1769   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1770   *           - Set handle State to READY
1771   *           - At abort completion, call user abort complete callback
1772   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1773   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1774   * @retval HAL status
1775   */
HAL_SMARTCARD_AbortReceive_IT(SMARTCARD_HandleTypeDef * hsmartcard)1776 HAL_StatusTypeDef HAL_SMARTCARD_AbortReceive_IT(SMARTCARD_HandleTypeDef *hsmartcard)
1777 {
1778   /* Disable RTOIE, EOBIE, RXNE, PE, RXFT and  ERR (Frame error, noise error, overrun error) interrupts */
1779   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_RTOIE |
1780                                         USART_CR1_EOBIE));
1781   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
1782 
1783   /* Check if a Transmit process is ongoing or not. If not disable ERR IT */
1784   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
1785   {
1786     /* Disable the SMARTCARD Error Interrupt: (Frame error) */
1787     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
1788   }
1789 
1790   /* Disable the SMARTCARD DMA Rx request if enabled */
1791   if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1792   {
1793     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1794 
1795     /* Abort the SMARTCARD DMA Rx channel : use non blocking DMA Abort API (callback) */
1796     if (hsmartcard->hdmarx != NULL)
1797     {
1798       /* Set the SMARTCARD DMA Abort callback :
1799          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1800       hsmartcard->hdmarx->XferAbortCallback = SMARTCARD_DMARxOnlyAbortCallback;
1801 
1802       /* Abort DMA RX */
1803       if (HAL_DMA_Abort_IT(hsmartcard->hdmarx) != HAL_OK)
1804       {
1805         /* Call Directly hsmartcard->hdmarx->XferAbortCallback function in case of error */
1806         hsmartcard->hdmarx->XferAbortCallback(hsmartcard->hdmarx);
1807       }
1808     }
1809     else
1810     {
1811       /* Reset Rx transfer counter */
1812       hsmartcard->RxXferCount = 0U;
1813 
1814       /* Clear RxISR function pointer */
1815       hsmartcard->RxISR = NULL;
1816 
1817       /* Clear the Error flags in the ICR register */
1818       __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
1819                                  SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF |
1820                                  SMARTCARD_CLEAR_FEF | SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
1821 
1822       /* Restore hsmartcard->RxState to Ready */
1823       hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1824 
1825       /* As no DMA to be aborted, call directly user Abort complete callback */
1826 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1827       /* Call registered Abort Receive Complete Callback */
1828       hsmartcard->AbortReceiveCpltCallback(hsmartcard);
1829 #else
1830       /* Call legacy weak Abort Receive Complete Callback */
1831       HAL_SMARTCARD_AbortReceiveCpltCallback(hsmartcard);
1832 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1833     }
1834   }
1835   else
1836   {
1837     /* Reset Rx transfer counter */
1838     hsmartcard->RxXferCount = 0U;
1839 
1840     /* Clear RxISR function pointer */
1841     hsmartcard->RxISR = NULL;
1842 
1843     /* Clear the Error flags in the ICR register */
1844     __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
1845                                SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF |
1846                                SMARTCARD_CLEAR_FEF | SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
1847 
1848     /* Restore hsmartcard->RxState to Ready */
1849     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
1850 
1851     /* As no DMA to be aborted, call directly user Abort complete callback */
1852 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1853     /* Call registered Abort Receive Complete Callback */
1854     hsmartcard->AbortReceiveCpltCallback(hsmartcard);
1855 #else
1856     /* Call legacy weak Abort Receive Complete Callback */
1857     HAL_SMARTCARD_AbortReceiveCpltCallback(hsmartcard);
1858 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1859   }
1860 
1861   return HAL_OK;
1862 }
1863 
1864 /**
1865   * @brief  Handle SMARTCARD interrupt requests.
1866   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
1867   *                    the configuration information for the specified SMARTCARD module.
1868   * @retval None
1869   */
HAL_SMARTCARD_IRQHandler(SMARTCARD_HandleTypeDef * hsmartcard)1870 void HAL_SMARTCARD_IRQHandler(SMARTCARD_HandleTypeDef *hsmartcard)
1871 {
1872   uint32_t isrflags   = READ_REG(hsmartcard->Instance->ISR);
1873   uint32_t cr1its     = READ_REG(hsmartcard->Instance->CR1);
1874   uint32_t cr3its     = READ_REG(hsmartcard->Instance->CR3);
1875   uint32_t errorflags;
1876   uint32_t errorcode;
1877 
1878   /* If no error occurs */
1879   errorflags = (isrflags & (uint32_t)(USART_ISR_PE | USART_ISR_FE | USART_ISR_ORE | USART_ISR_NE | USART_ISR_RTOF));
1880   if (errorflags == 0U)
1881   {
1882     /* SMARTCARD in mode Receiver ---------------------------------------------------*/
1883     if (((isrflags & USART_ISR_RXNE_RXFNE) != 0U)
1884         && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U)
1885             || ((cr3its & USART_CR3_RXFTIE) != 0U)))
1886     {
1887       if (hsmartcard->RxISR != NULL)
1888       {
1889         hsmartcard->RxISR(hsmartcard);
1890       }
1891       return;
1892     }
1893   }
1894 
1895   /* If some errors occur */
1896   if ((errorflags != 0U)
1897       && ((((cr3its & (USART_CR3_RXFTIE | USART_CR3_EIE)) != 0U)
1898            || ((cr1its & (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE)) != 0U))))
1899   {
1900     /* SMARTCARD parity error interrupt occurred -------------------------------------*/
1901     if (((isrflags & USART_ISR_PE) != 0U) && ((cr1its & USART_CR1_PEIE) != 0U))
1902     {
1903       __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_PEF);
1904 
1905       hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_PE;
1906     }
1907 
1908     /* SMARTCARD frame error interrupt occurred --------------------------------------*/
1909     if (((isrflags & USART_ISR_FE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
1910     {
1911       __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_FEF);
1912 
1913       hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_FE;
1914     }
1915 
1916     /* SMARTCARD noise error interrupt occurred --------------------------------------*/
1917     if (((isrflags & USART_ISR_NE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
1918     {
1919       __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_NEF);
1920 
1921       hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_NE;
1922     }
1923 
1924     /* SMARTCARD Over-Run interrupt occurred -----------------------------------------*/
1925     if (((isrflags & USART_ISR_ORE) != 0U)
1926         && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U)
1927             || ((cr3its & USART_CR3_RXFTIE) != 0U)
1928             || ((cr3its & USART_CR3_EIE) != 0U)))
1929     {
1930       __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_OREF);
1931 
1932       hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_ORE;
1933     }
1934 
1935     /* SMARTCARD receiver timeout interrupt occurred -----------------------------------------*/
1936     if (((isrflags & USART_ISR_RTOF) != 0U) && ((cr1its & USART_CR1_RTOIE) != 0U))
1937     {
1938       __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_RTOF);
1939 
1940       hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_RTO;
1941     }
1942 
1943     /* Call SMARTCARD Error Call back function if need be --------------------------*/
1944     if (hsmartcard->ErrorCode != HAL_SMARTCARD_ERROR_NONE)
1945     {
1946       /* SMARTCARD in mode Receiver ---------------------------------------------------*/
1947       if (((isrflags & USART_ISR_RXNE_RXFNE) != 0U)
1948           && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U)
1949               || ((cr3its & USART_CR3_RXFTIE) != 0U)))
1950       {
1951         if (hsmartcard->RxISR != NULL)
1952         {
1953           hsmartcard->RxISR(hsmartcard);
1954         }
1955       }
1956 
1957       /* If Error is to be considered as blocking :
1958           - Receiver Timeout error in Reception
1959           - Overrun error in Reception
1960           - any error occurs in DMA mode reception
1961       */
1962       errorcode = hsmartcard->ErrorCode;
1963       if ((HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1964           || ((errorcode & (HAL_SMARTCARD_ERROR_RTO | HAL_SMARTCARD_ERROR_ORE)) != 0U))
1965       {
1966         /* Blocking error : transfer is aborted
1967            Set the SMARTCARD state ready to be able to start again the process,
1968            Disable Rx Interrupts, and disable Rx DMA request, if ongoing */
1969         SMARTCARD_EndRxTransfer(hsmartcard);
1970 
1971         /* Disable the SMARTCARD DMA Rx request if enabled */
1972         if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
1973         {
1974           CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
1975 
1976           /* Abort the SMARTCARD DMA Rx channel */
1977           if (hsmartcard->hdmarx != NULL)
1978           {
1979             /* Set the SMARTCARD DMA Abort callback :
1980                will lead to call HAL_SMARTCARD_ErrorCallback() at end of DMA abort procedure */
1981             hsmartcard->hdmarx->XferAbortCallback = SMARTCARD_DMAAbortOnError;
1982 
1983             /* Abort DMA RX */
1984             if (HAL_DMA_Abort_IT(hsmartcard->hdmarx) != HAL_OK)
1985             {
1986               /* Call Directly hsmartcard->hdmarx->XferAbortCallback function in case of error */
1987               hsmartcard->hdmarx->XferAbortCallback(hsmartcard->hdmarx);
1988             }
1989           }
1990           else
1991           {
1992 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1993             /* Call registered user error callback */
1994             hsmartcard->ErrorCallback(hsmartcard);
1995 #else
1996             /* Call legacy weak user error callback */
1997             HAL_SMARTCARD_ErrorCallback(hsmartcard);
1998 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1999           }
2000         }
2001         else
2002         {
2003 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2004           /* Call registered user error callback */
2005           hsmartcard->ErrorCallback(hsmartcard);
2006 #else
2007           /* Call legacy weak user error callback */
2008           HAL_SMARTCARD_ErrorCallback(hsmartcard);
2009 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2010         }
2011       }
2012       /* other error type to be considered as blocking :
2013           - Frame error in Transmission
2014       */
2015       else if ((hsmartcard->gState == HAL_SMARTCARD_STATE_BUSY_TX)
2016                && ((errorcode & HAL_SMARTCARD_ERROR_FE) != 0U))
2017       {
2018         /* Blocking error : transfer is aborted
2019            Set the SMARTCARD state ready to be able to start again the process,
2020            Disable Tx Interrupts, and disable Tx DMA request, if ongoing */
2021         SMARTCARD_EndTxTransfer(hsmartcard);
2022 
2023         /* Disable the SMARTCARD DMA Tx request if enabled */
2024         if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
2025         {
2026           CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
2027 
2028           /* Abort the SMARTCARD DMA Tx channel */
2029           if (hsmartcard->hdmatx != NULL)
2030           {
2031             /* Set the SMARTCARD DMA Abort callback :
2032                will lead to call HAL_SMARTCARD_ErrorCallback() at end of DMA abort procedure */
2033             hsmartcard->hdmatx->XferAbortCallback = SMARTCARD_DMAAbortOnError;
2034 
2035             /* Abort DMA TX */
2036             if (HAL_DMA_Abort_IT(hsmartcard->hdmatx) != HAL_OK)
2037             {
2038               /* Call Directly hsmartcard->hdmatx->XferAbortCallback function in case of error */
2039               hsmartcard->hdmatx->XferAbortCallback(hsmartcard->hdmatx);
2040             }
2041           }
2042           else
2043           {
2044 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2045             /* Call registered user error callback */
2046             hsmartcard->ErrorCallback(hsmartcard);
2047 #else
2048             /* Call legacy weak user error callback */
2049             HAL_SMARTCARD_ErrorCallback(hsmartcard);
2050 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2051           }
2052         }
2053         else
2054         {
2055 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2056           /* Call registered user error callback */
2057           hsmartcard->ErrorCallback(hsmartcard);
2058 #else
2059           /* Call legacy weak user error callback */
2060           HAL_SMARTCARD_ErrorCallback(hsmartcard);
2061 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2062         }
2063       }
2064       else
2065       {
2066         /* Non Blocking error : transfer could go on.
2067            Error is notified to user through user error callback */
2068 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2069         /* Call registered user error callback */
2070         hsmartcard->ErrorCallback(hsmartcard);
2071 #else
2072         /* Call legacy weak user error callback */
2073         HAL_SMARTCARD_ErrorCallback(hsmartcard);
2074 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2075         hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2076       }
2077     }
2078     return;
2079 
2080   } /* End if some error occurs */
2081 
2082   /* SMARTCARD in mode Receiver, end of block interruption ------------------------*/
2083   if (((isrflags & USART_ISR_EOBF) != 0U) && ((cr1its & USART_CR1_EOBIE) != 0U))
2084   {
2085     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2086     __HAL_UNLOCK(hsmartcard);
2087 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2088     /* Call registered Rx complete callback */
2089     hsmartcard->RxCpltCallback(hsmartcard);
2090 #else
2091     /* Call legacy weak Rx complete callback */
2092     HAL_SMARTCARD_RxCpltCallback(hsmartcard);
2093 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2094     /* Clear EOBF interrupt after HAL_SMARTCARD_RxCpltCallback() call for the End of Block information
2095        to be available during HAL_SMARTCARD_RxCpltCallback() processing */
2096     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_EOBF);
2097     return;
2098   }
2099 
2100   /* SMARTCARD in mode Transmitter ------------------------------------------------*/
2101   if (((isrflags & USART_ISR_TXE_TXFNF) != 0U)
2102       && (((cr1its & USART_CR1_TXEIE_TXFNFIE) != 0U)
2103           || ((cr3its & USART_CR3_TXFTIE) != 0U)))
2104   {
2105     if (hsmartcard->TxISR != NULL)
2106     {
2107       hsmartcard->TxISR(hsmartcard);
2108     }
2109     return;
2110   }
2111 
2112   /* SMARTCARD in mode Transmitter (transmission end) ------------------------*/
2113   if (__HAL_SMARTCARD_GET_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication) != RESET)
2114   {
2115     if (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication) != RESET)
2116     {
2117       SMARTCARD_EndTransmit_IT(hsmartcard);
2118       return;
2119     }
2120   }
2121 
2122   /* SMARTCARD TX Fifo Empty occurred ----------------------------------------------*/
2123   if (((isrflags & USART_ISR_TXFE) != 0U) && ((cr1its & USART_CR1_TXFEIE) != 0U))
2124   {
2125 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2126     /* Call registered Tx Fifo Empty Callback */
2127     hsmartcard->TxFifoEmptyCallback(hsmartcard);
2128 #else
2129     /* Call legacy weak Tx Fifo Empty Callback */
2130     HAL_SMARTCARDEx_TxFifoEmptyCallback(hsmartcard);
2131 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2132     return;
2133   }
2134 
2135   /* SMARTCARD RX Fifo Full occurred ----------------------------------------------*/
2136   if (((isrflags & USART_ISR_RXFF) != 0U) && ((cr1its & USART_CR1_RXFFIE) != 0U))
2137   {
2138 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2139     /* Call registered Rx Fifo Full Callback */
2140     hsmartcard->RxFifoFullCallback(hsmartcard);
2141 #else
2142     /* Call legacy weak Rx Fifo Full Callback */
2143     HAL_SMARTCARDEx_RxFifoFullCallback(hsmartcard);
2144 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2145     return;
2146   }
2147 }
2148 
2149 /**
2150   * @brief  Tx Transfer completed callback.
2151   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2152   *                    the configuration information for the specified SMARTCARD module.
2153   * @retval None
2154   */
HAL_SMARTCARD_TxCpltCallback(SMARTCARD_HandleTypeDef * hsmartcard)2155 __weak void HAL_SMARTCARD_TxCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2156 {
2157   /* Prevent unused argument(s) compilation warning */
2158   UNUSED(hsmartcard);
2159 
2160   /* NOTE : This function should not be modified, when the callback is needed,
2161             the HAL_SMARTCARD_TxCpltCallback can be implemented in the user file.
2162    */
2163 }
2164 
2165 /**
2166   * @brief  Rx Transfer completed callback.
2167   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2168   *                    the configuration information for the specified SMARTCARD module.
2169   * @retval None
2170   */
HAL_SMARTCARD_RxCpltCallback(SMARTCARD_HandleTypeDef * hsmartcard)2171 __weak void HAL_SMARTCARD_RxCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2172 {
2173   /* Prevent unused argument(s) compilation warning */
2174   UNUSED(hsmartcard);
2175 
2176   /* NOTE : This function should not be modified, when the callback is needed,
2177             the HAL_SMARTCARD_RxCpltCallback can be implemented in the user file.
2178    */
2179 }
2180 
2181 /**
2182   * @brief  SMARTCARD error callback.
2183   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2184   *                    the configuration information for the specified SMARTCARD module.
2185   * @retval None
2186   */
HAL_SMARTCARD_ErrorCallback(SMARTCARD_HandleTypeDef * hsmartcard)2187 __weak void HAL_SMARTCARD_ErrorCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2188 {
2189   /* Prevent unused argument(s) compilation warning */
2190   UNUSED(hsmartcard);
2191 
2192   /* NOTE : This function should not be modified, when the callback is needed,
2193             the HAL_SMARTCARD_ErrorCallback can be implemented in the user file.
2194    */
2195 }
2196 
2197 /**
2198   * @brief  SMARTCARD Abort Complete callback.
2199   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2200   *                    the configuration information for the specified SMARTCARD module.
2201   * @retval None
2202   */
HAL_SMARTCARD_AbortCpltCallback(SMARTCARD_HandleTypeDef * hsmartcard)2203 __weak void HAL_SMARTCARD_AbortCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2204 {
2205   /* Prevent unused argument(s) compilation warning */
2206   UNUSED(hsmartcard);
2207 
2208   /* NOTE : This function should not be modified, when the callback is needed,
2209             the HAL_SMARTCARD_AbortCpltCallback can be implemented in the user file.
2210    */
2211 }
2212 
2213 /**
2214   * @brief  SMARTCARD Abort Complete callback.
2215   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2216   *                    the configuration information for the specified SMARTCARD module.
2217   * @retval None
2218   */
HAL_SMARTCARD_AbortTransmitCpltCallback(SMARTCARD_HandleTypeDef * hsmartcard)2219 __weak void HAL_SMARTCARD_AbortTransmitCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2220 {
2221   /* Prevent unused argument(s) compilation warning */
2222   UNUSED(hsmartcard);
2223 
2224   /* NOTE : This function should not be modified, when the callback is needed,
2225             the HAL_SMARTCARD_AbortTransmitCpltCallback can be implemented in the user file.
2226    */
2227 }
2228 
2229 /**
2230   * @brief  SMARTCARD Abort Receive Complete callback.
2231   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2232   *                    the configuration information for the specified SMARTCARD module.
2233   * @retval None
2234   */
HAL_SMARTCARD_AbortReceiveCpltCallback(SMARTCARD_HandleTypeDef * hsmartcard)2235 __weak void HAL_SMARTCARD_AbortReceiveCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
2236 {
2237   /* Prevent unused argument(s) compilation warning */
2238   UNUSED(hsmartcard);
2239 
2240   /* NOTE : This function should not be modified, when the callback is needed,
2241             the HAL_SMARTCARD_AbortReceiveCpltCallback can be implemented in the user file.
2242    */
2243 }
2244 
2245 /**
2246   * @}
2247   */
2248 
2249 /** @defgroup SMARTCARD_Exported_Functions_Group4 Peripheral State and Errors functions
2250   * @brief    SMARTCARD State and Errors functions
2251   *
2252 @verbatim
2253   ==============================================================================
2254                   ##### Peripheral State and Errors functions #####
2255   ==============================================================================
2256   [..]
2257     This subsection provides a set of functions allowing to return the State of SmartCard
2258     handle and also return Peripheral Errors occurred during communication process
2259      (+) HAL_SMARTCARD_GetState() API can be helpful to check in run-time the state
2260          of the SMARTCARD peripheral.
2261      (+) HAL_SMARTCARD_GetError() checks in run-time errors that could occur during
2262          communication.
2263 
2264 @endverbatim
2265   * @{
2266   */
2267 
2268 /**
2269   * @brief  Return the SMARTCARD handle state.
2270   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2271   *                    the configuration information for the specified SMARTCARD module.
2272   * @retval SMARTCARD handle state
2273   */
HAL_SMARTCARD_GetState(const SMARTCARD_HandleTypeDef * hsmartcard)2274 HAL_SMARTCARD_StateTypeDef HAL_SMARTCARD_GetState(const SMARTCARD_HandleTypeDef *hsmartcard)
2275 {
2276   /* Return SMARTCARD handle state */
2277   uint32_t temp1;
2278   uint32_t temp2;
2279   temp1 = (uint32_t)hsmartcard->gState;
2280   temp2 = (uint32_t)hsmartcard->RxState;
2281 
2282   return (HAL_SMARTCARD_StateTypeDef)(temp1 | temp2);
2283 }
2284 
2285 /**
2286   * @brief  Return the SMARTCARD handle error code.
2287   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2288   *                    the configuration information for the specified SMARTCARD module.
2289   * @retval SMARTCARD handle Error Code
2290   */
HAL_SMARTCARD_GetError(const SMARTCARD_HandleTypeDef * hsmartcard)2291 uint32_t HAL_SMARTCARD_GetError(const SMARTCARD_HandleTypeDef *hsmartcard)
2292 {
2293   return hsmartcard->ErrorCode;
2294 }
2295 
2296 /**
2297   * @}
2298   */
2299 
2300 /**
2301   * @}
2302   */
2303 
2304 /** @defgroup SMARTCARD_Private_Functions SMARTCARD Private Functions
2305   * @{
2306   */
2307 
2308 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2309 /**
2310   * @brief  Initialize the callbacks to their default values.
2311   * @param  hsmartcard SMARTCARD handle.
2312   * @retval none
2313   */
SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef * hsmartcard)2314 void SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef *hsmartcard)
2315 {
2316   /* Init the SMARTCARD Callback settings */
2317   hsmartcard->TxCpltCallback            = HAL_SMARTCARD_TxCpltCallback;            /* Legacy weak TxCpltCallback    */
2318   hsmartcard->RxCpltCallback            = HAL_SMARTCARD_RxCpltCallback;            /* Legacy weak RxCpltCallback    */
2319   hsmartcard->ErrorCallback             = HAL_SMARTCARD_ErrorCallback;             /* Legacy weak ErrorCallback     */
2320   hsmartcard->AbortCpltCallback         = HAL_SMARTCARD_AbortCpltCallback;         /* Legacy weak AbortCpltCallback */
2321   hsmartcard->AbortTransmitCpltCallback = HAL_SMARTCARD_AbortTransmitCpltCallback; /* Legacy weak
2322                                                                                       AbortTransmitCpltCallback     */
2323   hsmartcard->AbortReceiveCpltCallback  = HAL_SMARTCARD_AbortReceiveCpltCallback;  /* Legacy weak
2324                                                                                       AbortReceiveCpltCallback      */
2325   hsmartcard->RxFifoFullCallback        = HAL_SMARTCARDEx_RxFifoFullCallback;      /* Legacy weak
2326                                                                                       RxFifoFullCallback            */
2327   hsmartcard->TxFifoEmptyCallback       = HAL_SMARTCARDEx_TxFifoEmptyCallback;     /* Legacy weak
2328                                                                                       TxFifoEmptyCallback           */
2329 
2330 }
2331 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
2332 
2333 /**
2334   * @brief  Configure the SMARTCARD associated USART peripheral.
2335   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2336   *                    the configuration information for the specified SMARTCARD module.
2337   * @retval HAL status
2338   */
SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef * hsmartcard)2339 static HAL_StatusTypeDef SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef *hsmartcard)
2340 {
2341   uint32_t tmpreg;
2342   SMARTCARD_ClockSourceTypeDef clocksource;
2343   HAL_StatusTypeDef ret = HAL_OK;
2344   static const uint16_t SMARTCARDPrescTable[12] = {1U, 2U, 4U, 6U, 8U, 10U, 12U, 16U, 32U, 64U, 128U, 256U};
2345   uint32_t pclk;
2346 
2347   /* Check the parameters */
2348   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
2349   assert_param(IS_SMARTCARD_BAUDRATE(hsmartcard->Init.BaudRate));
2350   assert_param(IS_SMARTCARD_WORD_LENGTH(hsmartcard->Init.WordLength));
2351   assert_param(IS_SMARTCARD_STOPBITS(hsmartcard->Init.StopBits));
2352   assert_param(IS_SMARTCARD_PARITY(hsmartcard->Init.Parity));
2353   assert_param(IS_SMARTCARD_MODE(hsmartcard->Init.Mode));
2354   assert_param(IS_SMARTCARD_POLARITY(hsmartcard->Init.CLKPolarity));
2355   assert_param(IS_SMARTCARD_PHASE(hsmartcard->Init.CLKPhase));
2356   assert_param(IS_SMARTCARD_LASTBIT(hsmartcard->Init.CLKLastBit));
2357   assert_param(IS_SMARTCARD_ONE_BIT_SAMPLE(hsmartcard->Init.OneBitSampling));
2358   assert_param(IS_SMARTCARD_NACK(hsmartcard->Init.NACKEnable));
2359   assert_param(IS_SMARTCARD_TIMEOUT(hsmartcard->Init.TimeOutEnable));
2360   assert_param(IS_SMARTCARD_AUTORETRY_COUNT(hsmartcard->Init.AutoRetryCount));
2361   assert_param(IS_SMARTCARD_CLOCKPRESCALER(hsmartcard->Init.ClockPrescaler));
2362 
2363   /*-------------------------- USART CR1 Configuration -----------------------*/
2364   /* In SmartCard mode, M and PCE are forced to 1 (8 bits + parity).
2365    * Oversampling is forced to 16 (OVER8 = 0).
2366    * Configure the Parity and Mode:
2367    *  set PS bit according to hsmartcard->Init.Parity value
2368    *  set TE and RE bits according to hsmartcard->Init.Mode value */
2369   tmpreg = (((uint32_t)hsmartcard->Init.Parity) | ((uint32_t)hsmartcard->Init.Mode) |
2370             ((uint32_t)hsmartcard->Init.WordLength));
2371   MODIFY_REG(hsmartcard->Instance->CR1, USART_CR1_FIELDS, tmpreg);
2372 
2373   /*-------------------------- USART CR2 Configuration -----------------------*/
2374   tmpreg = hsmartcard->Init.StopBits;
2375   /* Synchronous mode is activated by default */
2376   tmpreg |= (uint32_t) USART_CR2_CLKEN | hsmartcard->Init.CLKPolarity;
2377   tmpreg |= (uint32_t) hsmartcard->Init.CLKPhase | hsmartcard->Init.CLKLastBit;
2378   tmpreg |= (uint32_t) hsmartcard->Init.TimeOutEnable;
2379   MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_FIELDS, tmpreg);
2380 
2381   /*-------------------------- USART CR3 Configuration -----------------------*/
2382   /* Configure
2383    * - one-bit sampling method versus three samples' majority rule
2384    *   according to hsmartcard->Init.OneBitSampling
2385    * - NACK transmission in case of parity error according
2386    *   to hsmartcard->Init.NACKEnable
2387    * - autoretry counter according to hsmartcard->Init.AutoRetryCount */
2388 
2389   tmpreg = (uint32_t) hsmartcard->Init.OneBitSampling | hsmartcard->Init.NACKEnable;
2390   tmpreg |= ((uint32_t)hsmartcard->Init.AutoRetryCount << USART_CR3_SCARCNT_Pos);
2391   MODIFY_REG(hsmartcard->Instance->CR3, USART_CR3_FIELDS, tmpreg);
2392 
2393   /*--------------------- SMARTCARD clock PRESC Configuration ----------------*/
2394   /* Configure
2395   * - SMARTCARD Clock Prescaler: set PRESCALER according to hsmartcard->Init.ClockPrescaler value */
2396   MODIFY_REG(hsmartcard->Instance->PRESC, USART_PRESC_PRESCALER, hsmartcard->Init.ClockPrescaler);
2397 
2398   /*-------------------------- USART GTPR Configuration ----------------------*/
2399   tmpreg = (hsmartcard->Init.Prescaler | ((uint32_t)hsmartcard->Init.GuardTime << USART_GTPR_GT_Pos));
2400   MODIFY_REG(hsmartcard->Instance->GTPR, (uint16_t)(USART_GTPR_GT | USART_GTPR_PSC), (uint16_t)tmpreg);
2401 
2402   /*-------------------------- USART RTOR Configuration ----------------------*/
2403   tmpreg = ((uint32_t)hsmartcard->Init.BlockLength << USART_RTOR_BLEN_Pos);
2404   if (hsmartcard->Init.TimeOutEnable == SMARTCARD_TIMEOUT_ENABLE)
2405   {
2406     assert_param(IS_SMARTCARD_TIMEOUT_VALUE(hsmartcard->Init.TimeOutValue));
2407     tmpreg |= (uint32_t) hsmartcard->Init.TimeOutValue;
2408   }
2409   MODIFY_REG(hsmartcard->Instance->RTOR, (USART_RTOR_RTO | USART_RTOR_BLEN), tmpreg);
2410 
2411   /*-------------------------- USART BRR Configuration -----------------------*/
2412   SMARTCARD_GETCLOCKSOURCE(hsmartcard, clocksource);
2413   tmpreg =   0U;
2414   switch (clocksource)
2415   {
2416     case SMARTCARD_CLOCKSOURCE_PCLK1:
2417       pclk = HAL_RCC_GetPCLK1Freq();
2418       tmpreg = (uint32_t)(((pclk / SMARTCARDPrescTable[hsmartcard->Init.ClockPrescaler]) +
2419                            (hsmartcard->Init.BaudRate / 2U)) / hsmartcard->Init.BaudRate);
2420       break;
2421     case SMARTCARD_CLOCKSOURCE_PCLK2:
2422       pclk = HAL_RCC_GetPCLK2Freq();
2423       tmpreg = (uint32_t)(((pclk / SMARTCARDPrescTable[hsmartcard->Init.ClockPrescaler]) +
2424                            (hsmartcard->Init.BaudRate / 2U)) / hsmartcard->Init.BaudRate);
2425       break;
2426     case SMARTCARD_CLOCKSOURCE_HSI:
2427       tmpreg = (uint32_t)(((HSI_VALUE / SMARTCARDPrescTable[hsmartcard->Init.ClockPrescaler]) +
2428                            (hsmartcard->Init.BaudRate / 2U)) / hsmartcard->Init.BaudRate);
2429       break;
2430     case SMARTCARD_CLOCKSOURCE_SYSCLK:
2431       pclk = HAL_RCC_GetSysClockFreq();
2432       tmpreg = (uint32_t)(((pclk / SMARTCARDPrescTable[hsmartcard->Init.ClockPrescaler]) +
2433                            (hsmartcard->Init.BaudRate / 2U)) / hsmartcard->Init.BaudRate);
2434       break;
2435     case SMARTCARD_CLOCKSOURCE_LSE:
2436       tmpreg = (uint32_t)(((uint16_t)(LSE_VALUE / SMARTCARDPrescTable[hsmartcard->Init.ClockPrescaler]) +
2437                            (hsmartcard->Init.BaudRate / 2U)) / hsmartcard->Init.BaudRate);
2438       break;
2439     default:
2440       ret = HAL_ERROR;
2441       break;
2442   }
2443 
2444   /* USARTDIV must be greater than or equal to 0d16 */
2445   if ((tmpreg >= USART_BRR_MIN) && (tmpreg <= USART_BRR_MAX))
2446   {
2447     hsmartcard->Instance->BRR = (uint16_t)tmpreg;
2448   }
2449   else
2450   {
2451     ret = HAL_ERROR;
2452   }
2453 
2454   /* Initialize the number of data to process during RX/TX ISR execution */
2455   hsmartcard->NbTxDataToProcess = 1U;
2456   hsmartcard->NbRxDataToProcess = 1U;
2457 
2458   /* Clear ISR function pointers */
2459   hsmartcard->RxISR   = NULL;
2460   hsmartcard->TxISR   = NULL;
2461 
2462   return ret;
2463 }
2464 
2465 
2466 /**
2467   * @brief Configure the SMARTCARD associated USART peripheral advanced features.
2468   * @param hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2469   *                   the configuration information for the specified SMARTCARD module.
2470   * @retval None
2471   */
SMARTCARD_AdvFeatureConfig(SMARTCARD_HandleTypeDef * hsmartcard)2472 static void SMARTCARD_AdvFeatureConfig(SMARTCARD_HandleTypeDef *hsmartcard)
2473 {
2474   /* Check whether the set of advanced features to configure is properly set */
2475   assert_param(IS_SMARTCARD_ADVFEATURE_INIT(hsmartcard->AdvancedInit.AdvFeatureInit));
2476 
2477   /* if required, configure TX pin active level inversion */
2478   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_TXINVERT_INIT))
2479   {
2480     assert_param(IS_SMARTCARD_ADVFEATURE_TXINV(hsmartcard->AdvancedInit.TxPinLevelInvert));
2481     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_TXINV, hsmartcard->AdvancedInit.TxPinLevelInvert);
2482   }
2483 
2484   /* if required, configure RX pin active level inversion */
2485   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_RXINVERT_INIT))
2486   {
2487     assert_param(IS_SMARTCARD_ADVFEATURE_RXINV(hsmartcard->AdvancedInit.RxPinLevelInvert));
2488     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_RXINV, hsmartcard->AdvancedInit.RxPinLevelInvert);
2489   }
2490 
2491   /* if required, configure data inversion */
2492   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_DATAINVERT_INIT))
2493   {
2494     assert_param(IS_SMARTCARD_ADVFEATURE_DATAINV(hsmartcard->AdvancedInit.DataInvert));
2495     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_DATAINV, hsmartcard->AdvancedInit.DataInvert);
2496   }
2497 
2498   /* if required, configure RX/TX pins swap */
2499   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_SWAP_INIT))
2500   {
2501     assert_param(IS_SMARTCARD_ADVFEATURE_SWAP(hsmartcard->AdvancedInit.Swap));
2502     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_SWAP, hsmartcard->AdvancedInit.Swap);
2503   }
2504 
2505   /* if required, configure RX overrun detection disabling */
2506   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_RXOVERRUNDISABLE_INIT))
2507   {
2508     assert_param(IS_SMARTCARD_OVERRUN(hsmartcard->AdvancedInit.OverrunDisable));
2509     MODIFY_REG(hsmartcard->Instance->CR3, USART_CR3_OVRDIS, hsmartcard->AdvancedInit.OverrunDisable);
2510   }
2511 
2512   /* if required, configure DMA disabling on reception error */
2513   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_DMADISABLEONERROR_INIT))
2514   {
2515     assert_param(IS_SMARTCARD_ADVFEATURE_DMAONRXERROR(hsmartcard->AdvancedInit.DMADisableonRxError));
2516     MODIFY_REG(hsmartcard->Instance->CR3, USART_CR3_DDRE, hsmartcard->AdvancedInit.DMADisableonRxError);
2517   }
2518 
2519   /* if required, configure MSB first on communication line */
2520   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_MSBFIRST_INIT))
2521   {
2522     assert_param(IS_SMARTCARD_ADVFEATURE_MSBFIRST(hsmartcard->AdvancedInit.MSBFirst));
2523     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_MSBFIRST, hsmartcard->AdvancedInit.MSBFirst);
2524   }
2525 
2526 }
2527 
2528 /**
2529   * @brief Check the SMARTCARD Idle State.
2530   * @param hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2531   *                   the configuration information for the specified SMARTCARD module.
2532   * @retval HAL status
2533   */
SMARTCARD_CheckIdleState(SMARTCARD_HandleTypeDef * hsmartcard)2534 static HAL_StatusTypeDef SMARTCARD_CheckIdleState(SMARTCARD_HandleTypeDef *hsmartcard)
2535 {
2536   uint32_t tickstart;
2537 
2538   /* Initialize the SMARTCARD ErrorCode */
2539   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2540 
2541   /* Init tickstart for timeout management */
2542   tickstart = HAL_GetTick();
2543 
2544   /* Check if the Transmitter is enabled */
2545   if ((hsmartcard->Instance->CR1 & USART_CR1_TE) == USART_CR1_TE)
2546   {
2547     /* Wait until TEACK flag is set */
2548     if (SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, USART_ISR_TEACK, RESET, tickstart,
2549                                          SMARTCARD_TEACK_REACK_TIMEOUT) != HAL_OK)
2550     {
2551       /* Timeout occurred */
2552       return HAL_TIMEOUT;
2553     }
2554   }
2555   /* Check if the Receiver is enabled */
2556   if ((hsmartcard->Instance->CR1 & USART_CR1_RE) == USART_CR1_RE)
2557   {
2558     /* Wait until REACK flag is set */
2559     if (SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, USART_ISR_REACK, RESET, tickstart,
2560                                          SMARTCARD_TEACK_REACK_TIMEOUT) != HAL_OK)
2561     {
2562       /* Timeout occurred */
2563       return HAL_TIMEOUT;
2564     }
2565   }
2566 
2567   /* Initialize the SMARTCARD states */
2568   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
2569   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2570 
2571   /* Process Unlocked */
2572   __HAL_UNLOCK(hsmartcard);
2573 
2574   return HAL_OK;
2575 }
2576 
2577 /**
2578   * @brief  Handle SMARTCARD Communication Timeout. It waits
2579   *         until a flag is no longer in the specified status.
2580   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2581   *                   the configuration information for the specified SMARTCARD module.
2582   * @param  Flag Specifies the SMARTCARD flag to check.
2583   * @param  Status The actual Flag status (SET or RESET).
2584   * @param  Tickstart Tick start value
2585   * @param  Timeout Timeout duration.
2586   * @retval HAL status
2587   */
SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef * hsmartcard,uint32_t Flag,FlagStatus Status,uint32_t Tickstart,uint32_t Timeout)2588 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsmartcard, uint32_t Flag,
2589                                                           FlagStatus Status, uint32_t Tickstart, uint32_t Timeout)
2590 {
2591   /* Wait until flag is set */
2592   while ((__HAL_SMARTCARD_GET_FLAG(hsmartcard, Flag) ? SET : RESET) == Status)
2593   {
2594     /* Check for the Timeout */
2595     if (Timeout != HAL_MAX_DELAY)
2596     {
2597       if (((HAL_GetTick() - Tickstart) > Timeout) || (Timeout == 0U))
2598       {
2599         /* Disable TXE, RXNE, PE and ERR (Frame error, noise error, overrun error)
2600            interrupts for the interrupt process */
2601         CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_TXEIE_TXFNFIE));
2602         CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
2603 
2604         hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
2605         hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2606 
2607         /* Process Unlocked */
2608         __HAL_UNLOCK(hsmartcard);
2609         return HAL_TIMEOUT;
2610       }
2611     }
2612   }
2613   return HAL_OK;
2614 }
2615 
2616 
2617 /**
2618   * @brief  End ongoing Tx transfer on SMARTCARD peripheral (following error detection or Transmit completion).
2619   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2620   *                    the configuration information for the specified SMARTCARD module.
2621   * @retval None
2622   */
SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef * hsmartcard)2623 static void SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef *hsmartcard)
2624 {
2625   /* Disable TXEIE, TCIE and ERR (Frame error, noise error, overrun error) interrupts */
2626   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE));
2627   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
2628 
2629   /* At end of Tx process, restore hsmartcard->gState to Ready */
2630   hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
2631 }
2632 
2633 
2634 /**
2635   * @brief  End ongoing Rx transfer on UART peripheral (following error detection or Reception completion).
2636   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2637   *                    the configuration information for the specified SMARTCARD module.
2638   * @retval None
2639   */
SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef * hsmartcard)2640 static void SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef *hsmartcard)
2641 {
2642   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
2643   CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
2644   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
2645 
2646   /* At end of Rx process, restore hsmartcard->RxState to Ready */
2647   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2648 }
2649 
2650 
2651 /**
2652   * @brief  DMA SMARTCARD transmit process complete callback.
2653   * @param  hdma Pointer to a DMA_HandleTypeDef structure that contains
2654   *              the configuration information for the specified DMA module.
2655   * @retval None
2656   */
SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef * hdma)2657 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma)
2658 {
2659   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2660   hsmartcard->TxXferCount = 0U;
2661 
2662   /* Disable the DMA transfer for transmit request by resetting the DMAT bit
2663   in the SMARTCARD associated USART CR3 register */
2664   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
2665 
2666   /* Enable the SMARTCARD Transmit Complete Interrupt */
2667   __HAL_SMARTCARD_ENABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
2668 }
2669 
2670 /**
2671   * @brief  DMA SMARTCARD receive process complete callback.
2672   * @param  hdma Pointer to a DMA_HandleTypeDef structure that contains
2673   *              the configuration information for the specified DMA module.
2674   * @retval None
2675   */
SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef * hdma)2676 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma)
2677 {
2678   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2679   hsmartcard->RxXferCount = 0U;
2680 
2681   /* Disable PE and ERR (Frame error, noise error, overrun error) interrupts */
2682   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE);
2683   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
2684 
2685   /* Disable the DMA transfer for the receiver request by resetting the DMAR bit
2686      in the SMARTCARD associated USART CR3 register */
2687   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
2688 
2689   /* At end of Rx process, restore hsmartcard->RxState to Ready */
2690   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2691 
2692 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2693   /* Call registered Rx complete callback */
2694   hsmartcard->RxCpltCallback(hsmartcard);
2695 #else
2696   /* Call legacy weak Rx complete callback */
2697   HAL_SMARTCARD_RxCpltCallback(hsmartcard);
2698 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2699 }
2700 
2701 /**
2702   * @brief  DMA SMARTCARD communication error callback.
2703   * @param  hdma Pointer to a DMA_HandleTypeDef structure that contains
2704   *              the configuration information for the specified DMA module.
2705   * @retval None
2706   */
SMARTCARD_DMAError(DMA_HandleTypeDef * hdma)2707 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma)
2708 {
2709   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2710 
2711   /* Stop SMARTCARD DMA Tx request if ongoing */
2712   if (hsmartcard->gState == HAL_SMARTCARD_STATE_BUSY_TX)
2713   {
2714     if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAT))
2715     {
2716       hsmartcard->TxXferCount = 0U;
2717       SMARTCARD_EndTxTransfer(hsmartcard);
2718     }
2719   }
2720 
2721   /* Stop SMARTCARD DMA Rx request if ongoing */
2722   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_BUSY_RX)
2723   {
2724     if (HAL_IS_BIT_SET(hsmartcard->Instance->CR3, USART_CR3_DMAR))
2725     {
2726       hsmartcard->RxXferCount = 0U;
2727       SMARTCARD_EndRxTransfer(hsmartcard);
2728     }
2729   }
2730 
2731   hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_DMA;
2732 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2733   /* Call registered user error callback */
2734   hsmartcard->ErrorCallback(hsmartcard);
2735 #else
2736   /* Call legacy weak user error callback */
2737   HAL_SMARTCARD_ErrorCallback(hsmartcard);
2738 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2739 }
2740 
2741 /**
2742   * @brief  DMA SMARTCARD communication abort callback, when initiated by HAL services on Error
2743   *         (To be called at end of DMA Abort procedure following error occurrence).
2744   * @param  hdma DMA handle.
2745   * @retval None
2746   */
SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef * hdma)2747 static void SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef *hdma)
2748 {
2749   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2750   hsmartcard->RxXferCount = 0U;
2751   hsmartcard->TxXferCount = 0U;
2752 
2753 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2754   /* Call registered user error callback */
2755   hsmartcard->ErrorCallback(hsmartcard);
2756 #else
2757   /* Call legacy weak user error callback */
2758   HAL_SMARTCARD_ErrorCallback(hsmartcard);
2759 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2760 }
2761 
2762 /**
2763   * @brief  DMA SMARTCARD Tx communication abort callback, when initiated by user
2764   *         (To be called at end of DMA Tx Abort procedure following user abort request).
2765   * @note   When this callback is executed, User Abort complete call back is called only if no
2766   *         Abort still ongoing for Rx DMA Handle.
2767   * @param  hdma DMA handle.
2768   * @retval None
2769   */
SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef * hdma)2770 static void SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef *hdma)
2771 {
2772   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2773 
2774   hsmartcard->hdmatx->XferAbortCallback = NULL;
2775 
2776   /* Check if an Abort process is still ongoing */
2777   if (hsmartcard->hdmarx != NULL)
2778   {
2779     if (hsmartcard->hdmarx->XferAbortCallback != NULL)
2780     {
2781       return;
2782     }
2783   }
2784 
2785   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
2786   hsmartcard->TxXferCount = 0U;
2787   hsmartcard->RxXferCount = 0U;
2788 
2789   /* Reset errorCode */
2790   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2791 
2792   /* Clear the Error flags in the ICR register */
2793   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
2794                              SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF | SMARTCARD_CLEAR_FEF |
2795                              SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
2796 
2797   /* Restore hsmartcard->gState and hsmartcard->RxState to Ready */
2798   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
2799   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2800 
2801 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2802   /* Call registered Abort complete callback */
2803   hsmartcard->AbortCpltCallback(hsmartcard);
2804 #else
2805   /* Call legacy weak Abort complete callback */
2806   HAL_SMARTCARD_AbortCpltCallback(hsmartcard);
2807 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2808 }
2809 
2810 
2811 /**
2812   * @brief  DMA SMARTCARD Rx communication abort callback, when initiated by user
2813   *         (To be called at end of DMA Rx Abort procedure following user abort request).
2814   * @note   When this callback is executed, User Abort complete call back is called only if no
2815   *         Abort still ongoing for Tx DMA Handle.
2816   * @param  hdma DMA handle.
2817   * @retval None
2818   */
SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef * hdma)2819 static void SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef *hdma)
2820 {
2821   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2822 
2823   hsmartcard->hdmarx->XferAbortCallback = NULL;
2824 
2825   /* Check if an Abort process is still ongoing */
2826   if (hsmartcard->hdmatx != NULL)
2827   {
2828     if (hsmartcard->hdmatx->XferAbortCallback != NULL)
2829     {
2830       return;
2831     }
2832   }
2833 
2834   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
2835   hsmartcard->TxXferCount = 0U;
2836   hsmartcard->RxXferCount = 0U;
2837 
2838   /* Reset errorCode */
2839   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2840 
2841   /* Clear the Error flags in the ICR register */
2842   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
2843                              SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF | SMARTCARD_CLEAR_FEF |
2844                              SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
2845 
2846   /* Restore hsmartcard->gState and hsmartcard->RxState to Ready */
2847   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
2848   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2849 
2850 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2851   /* Call registered Abort complete callback */
2852   hsmartcard->AbortCpltCallback(hsmartcard);
2853 #else
2854   /* Call legacy weak Abort complete callback */
2855   HAL_SMARTCARD_AbortCpltCallback(hsmartcard);
2856 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2857 }
2858 
2859 
2860 /**
2861   * @brief  DMA SMARTCARD Tx communication abort callback, when initiated by user by a call to
2862   *         HAL_SMARTCARD_AbortTransmit_IT API (Abort only Tx transfer)
2863   *         (This callback is executed at end of DMA Tx Abort procedure following user abort request,
2864   *         and leads to user Tx Abort Complete callback execution).
2865   * @param  hdma DMA handle.
2866   * @retval None
2867   */
SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef * hdma)2868 static void SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
2869 {
2870   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2871 
2872   hsmartcard->TxXferCount = 0U;
2873 
2874   /* Clear the Error flags in the ICR register */
2875   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard, SMARTCARD_CLEAR_FEF);
2876 
2877   /* Restore hsmartcard->gState to Ready */
2878   hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
2879 
2880 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2881   /* Call registered Abort Transmit Complete Callback */
2882   hsmartcard->AbortTransmitCpltCallback(hsmartcard);
2883 #else
2884   /* Call legacy weak Abort Transmit Complete Callback */
2885   HAL_SMARTCARD_AbortTransmitCpltCallback(hsmartcard);
2886 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2887 }
2888 
2889 /**
2890   * @brief  DMA SMARTCARD Rx communication abort callback, when initiated by user by a call to
2891   *         HAL_SMARTCARD_AbortReceive_IT API (Abort only Rx transfer)
2892   *         (This callback is executed at end of DMA Rx Abort procedure following user abort request,
2893   *         and leads to user Rx Abort Complete callback execution).
2894   * @param  hdma DMA handle.
2895   * @retval None
2896   */
SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef * hdma)2897 static void SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
2898 {
2899   SMARTCARD_HandleTypeDef *hsmartcard = (SMARTCARD_HandleTypeDef *)(hdma->Parent);
2900 
2901   hsmartcard->RxXferCount = 0U;
2902 
2903   /* Clear the Error flags in the ICR register */
2904   __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard,
2905                              SMARTCARD_CLEAR_OREF | SMARTCARD_CLEAR_NEF | SMARTCARD_CLEAR_PEF | SMARTCARD_CLEAR_FEF |
2906                              SMARTCARD_CLEAR_RTOF | SMARTCARD_CLEAR_EOBF);
2907 
2908   /* Restore hsmartcard->RxState to Ready */
2909   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
2910 
2911 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2912   /* Call registered Abort Receive Complete Callback */
2913   hsmartcard->AbortReceiveCpltCallback(hsmartcard);
2914 #else
2915   /* Call legacy weak Abort Receive Complete Callback */
2916   HAL_SMARTCARD_AbortReceiveCpltCallback(hsmartcard);
2917 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2918 }
2919 
2920 /**
2921   * @brief  Send an amount of data in non-blocking mode.
2922   * @note   Function called under interruption only, once
2923   *         interruptions have been enabled by HAL_SMARTCARD_Transmit_IT()
2924   *         and when the FIFO mode is disabled.
2925   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2926   *                    the configuration information for the specified SMARTCARD module.
2927   * @retval None
2928   */
SMARTCARD_TxISR(SMARTCARD_HandleTypeDef * hsmartcard)2929 static void SMARTCARD_TxISR(SMARTCARD_HandleTypeDef *hsmartcard)
2930 {
2931   /* Check that a Tx process is ongoing */
2932   if (hsmartcard->gState == HAL_SMARTCARD_STATE_BUSY_TX)
2933   {
2934     if (hsmartcard->TxXferCount == 0U)
2935     {
2936       /* Disable the SMARTCARD Transmit Data Register Empty Interrupt */
2937       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
2938 
2939       /* Enable the SMARTCARD Transmit Complete Interrupt */
2940       __HAL_SMARTCARD_ENABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
2941     }
2942     else
2943     {
2944       hsmartcard->Instance->TDR = (uint8_t)(*hsmartcard->pTxBuffPtr & 0xFFU);
2945       hsmartcard->pTxBuffPtr++;
2946       hsmartcard->TxXferCount--;
2947     }
2948   }
2949 }
2950 
2951 /**
2952   * @brief  Send an amount of data in non-blocking mode.
2953   * @note   Function called under interruption only, once
2954   *         interruptions have been enabled by HAL_SMARTCARD_Transmit_IT()
2955   *         and when the FIFO mode is enabled.
2956   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2957   *                    the configuration information for the specified SMARTCARD module.
2958   * @retval None
2959   */
SMARTCARD_TxISR_FIFOEN(SMARTCARD_HandleTypeDef * hsmartcard)2960 static void SMARTCARD_TxISR_FIFOEN(SMARTCARD_HandleTypeDef *hsmartcard)
2961 {
2962   uint16_t   nb_tx_data;
2963 
2964   /* Check that a Tx process is ongoing */
2965   if (hsmartcard->gState == HAL_SMARTCARD_STATE_BUSY_TX)
2966   {
2967     for (nb_tx_data = hsmartcard->NbTxDataToProcess ; nb_tx_data > 0U ; nb_tx_data--)
2968     {
2969       if (hsmartcard->TxXferCount == 0U)
2970       {
2971         /* Disable the SMARTCARD Transmit Data Register Empty Interrupt */
2972         CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
2973 
2974         /* Enable the SMARTCARD Transmit Complete Interrupt */
2975         __HAL_SMARTCARD_ENABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
2976       }
2977       else if (READ_BIT(hsmartcard->Instance->ISR, USART_ISR_TXE_TXFNF) != 0U)
2978       {
2979         hsmartcard->Instance->TDR = (uint8_t)(*hsmartcard->pTxBuffPtr & 0xFFU);
2980         hsmartcard->pTxBuffPtr++;
2981         hsmartcard->TxXferCount--;
2982       }
2983       else
2984       {
2985         /* Nothing to do */
2986       }
2987     }
2988   }
2989 }
2990 
2991 /**
2992   * @brief  Wrap up transmission in non-blocking mode.
2993   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
2994   *                    the configuration information for the specified SMARTCARD module.
2995   * @retval None
2996   */
SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef * hsmartcard)2997 static void SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsmartcard)
2998 {
2999   /* Disable the SMARTCARD Transmit Complete Interrupt */
3000   __HAL_SMARTCARD_DISABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
3001 
3002   /* Check if a receive process is ongoing or not. If not disable ERR IT */
3003   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
3004   {
3005     /* Disable the SMARTCARD Error Interrupt: (Frame error) */
3006     CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
3007   }
3008 
3009   /* Disable the Peripheral first to update mode */
3010   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
3011   if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX)
3012       && (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
3013   {
3014     /* In case of TX only mode, if NACK is enabled, receiver block has been enabled
3015        for Transmit phase. Disable this receiver block. */
3016     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
3017   }
3018   if ((hsmartcard->Init.Mode == SMARTCARD_MODE_TX_RX)
3019       || (hsmartcard->Init.NACKEnable == SMARTCARD_NACK_ENABLE))
3020   {
3021     /* Perform a TX FIFO Flush at end of Tx phase, as all sent bytes are appearing in Rx Data register */
3022     __HAL_SMARTCARD_FLUSH_DRREGISTER(hsmartcard);
3023   }
3024   SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
3025 
3026   /* Tx process is ended, restore hsmartcard->gState to Ready */
3027   hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
3028 
3029   /* Clear TxISR function pointer */
3030   hsmartcard->TxISR = NULL;
3031 
3032 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
3033   /* Call registered Tx complete callback */
3034   hsmartcard->TxCpltCallback(hsmartcard);
3035 #else
3036   /* Call legacy weak Tx complete callback */
3037   HAL_SMARTCARD_TxCpltCallback(hsmartcard);
3038 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
3039 }
3040 
3041 /**
3042   * @brief  Receive an amount of data in non-blocking mode.
3043   * @note   Function called under interruption only, once
3044   *         interruptions have been enabled by HAL_SMARTCARD_Receive_IT()
3045   *         and when the FIFO mode is disabled.
3046   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
3047   *                    the configuration information for the specified SMARTCARD module.
3048   * @retval None
3049   */
SMARTCARD_RxISR(SMARTCARD_HandleTypeDef * hsmartcard)3050 static void SMARTCARD_RxISR(SMARTCARD_HandleTypeDef *hsmartcard)
3051 {
3052   /* Check that a Rx process is ongoing */
3053   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_BUSY_RX)
3054   {
3055     *hsmartcard->pRxBuffPtr = (uint8_t)(hsmartcard->Instance->RDR & (uint8_t)0xFF);
3056     hsmartcard->pRxBuffPtr++;
3057 
3058     hsmartcard->RxXferCount--;
3059     if (hsmartcard->RxXferCount == 0U)
3060     {
3061       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
3062 
3063       /* Check if a transmit process is ongoing or not. If not disable ERR IT */
3064       if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
3065       {
3066         /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
3067         CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
3068       }
3069 
3070       /* Disable the SMARTCARD Parity Error Interrupt */
3071       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE);
3072 
3073       hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
3074 
3075       /* Clear RxISR function pointer */
3076       hsmartcard->RxISR = NULL;
3077 
3078 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
3079       /* Call registered Rx complete callback */
3080       hsmartcard->RxCpltCallback(hsmartcard);
3081 #else
3082       /* Call legacy weak Rx complete callback */
3083       HAL_SMARTCARD_RxCpltCallback(hsmartcard);
3084 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
3085     }
3086   }
3087   else
3088   {
3089     /* Clear RXNE interrupt flag */
3090     __HAL_SMARTCARD_SEND_REQ(hsmartcard, SMARTCARD_RXDATA_FLUSH_REQUEST);
3091   }
3092 }
3093 
3094 /**
3095   * @brief  Receive an amount of data in non-blocking mode.
3096   * @note   Function called under interruption only, once
3097   *         interruptions have been enabled by HAL_SMARTCARD_Receive_IT()
3098   *         and when the FIFO mode is enabled.
3099   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
3100   *                    the configuration information for the specified SMARTCARD module.
3101   * @retval None
3102   */
SMARTCARD_RxISR_FIFOEN(SMARTCARD_HandleTypeDef * hsmartcard)3103 static void SMARTCARD_RxISR_FIFOEN(SMARTCARD_HandleTypeDef *hsmartcard)
3104 {
3105   uint16_t   nb_rx_data;
3106   uint16_t rxdatacount;
3107 
3108   /* Check that a Rx process is ongoing */
3109   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_BUSY_RX)
3110   {
3111     for (nb_rx_data = hsmartcard->NbRxDataToProcess ; nb_rx_data > 0U ; nb_rx_data--)
3112     {
3113       *hsmartcard->pRxBuffPtr = (uint8_t)(hsmartcard->Instance->RDR & (uint8_t)0xFF);
3114       hsmartcard->pRxBuffPtr++;
3115 
3116       hsmartcard->RxXferCount--;
3117       if (hsmartcard->RxXferCount == 0U)
3118       {
3119         CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
3120 
3121         /* Check if a transmit process is ongoing or not. If not disable ERR IT */
3122         if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
3123         {
3124           /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
3125           CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
3126         }
3127 
3128         /* Disable the SMARTCARD Parity Error Interrupt */
3129         CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_PEIE);
3130 
3131         hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
3132 
3133         /* Clear RxISR function pointer */
3134         hsmartcard->RxISR = NULL;
3135 
3136 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
3137         /* Call registered Rx complete callback */
3138         hsmartcard->RxCpltCallback(hsmartcard);
3139 #else
3140         /* Call legacy weak Rx complete callback */
3141         HAL_SMARTCARD_RxCpltCallback(hsmartcard);
3142 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
3143       }
3144     }
3145 
3146     /* When remaining number of bytes to receive is less than the RX FIFO
3147     threshold, next incoming frames are processed as if FIFO mode was
3148     disabled (i.e. one interrupt per received frame).
3149     */
3150     rxdatacount = hsmartcard->RxXferCount;
3151     if (((rxdatacount != 0U)) && (rxdatacount < hsmartcard->NbRxDataToProcess))
3152     {
3153       /* Disable the UART RXFT interrupt*/
3154       CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_RXFTIE);
3155 
3156       /* Update the RxISR function pointer */
3157       hsmartcard->RxISR = SMARTCARD_RxISR;
3158 
3159       /* Enable the UART Data Register Not Empty interrupt */
3160       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
3161     }
3162   }
3163   else
3164   {
3165     /* Clear RXNE interrupt flag */
3166     __HAL_SMARTCARD_SEND_REQ(hsmartcard, SMARTCARD_RXDATA_FLUSH_REQUEST);
3167   }
3168 }
3169 
3170 /**
3171   * @}
3172   */
3173 
3174 #endif /* HAL_SMARTCARD_MODULE_ENABLED */
3175 /**
3176   * @}
3177   */
3178 
3179 /**
3180   * @}
3181   */
3182 
3183