xref: /btstack/port/stm32-f4discovery-usb/Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_smartcard.c (revision a8f7f3fcbcd51f8d2e92aca076b6a9f812db358c)
1 /**
2   ******************************************************************************
3   * @file    stm32f4xx_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   @verbatim
14   ==============================================================================
15                      ##### How to use this driver #####
16   ==============================================================================
17     [..]
18       The SMARTCARD HAL driver can be used as follows:
19 
20     (#) Declare a SMARTCARD_HandleTypeDef handle structure.
21     (#) Initialize the SMARTCARD low level resources by implementing the HAL_SMARTCARD_MspInit() API:
22         (##) Enable the interface clock of the USARTx associated to the SMARTCARD.
23         (##) SMARTCARD pins configuration:
24             (+++) Enable the clock for the SMARTCARD GPIOs.
25             (+++) Configure SMARTCARD pins as alternate function pull-up.
26         (##) NVIC configuration if you need to use interrupt process (HAL_SMARTCARD_Transmit_IT()
27              and HAL_SMARTCARD_Receive_IT() APIs):
28             (+++) Configure the USARTx interrupt priority.
29             (+++) Enable the NVIC USART IRQ handle.
30         (##) DMA Configuration if you need to use DMA process (HAL_SMARTCARD_Transmit_DMA()
31              and HAL_SMARTCARD_Receive_DMA() APIs):
32             (+++) Declare a DMA handle structure for the Tx/Rx stream.
33             (+++) Enable the DMAx interface clock.
34             (+++) Configure the declared DMA handle structure with the required Tx/Rx parameters.
35             (+++) Configure the DMA Tx/Rx stream.
36             (+++) Associate the initialized DMA handle to the SMARTCARD DMA Tx/Rx handle.
37             (+++) Configure the priority and enable the NVIC for the transfer complete interrupt on the DMA Tx/Rx stream.
38             (+++) Configure the USARTx interrupt priority and enable the NVIC USART IRQ handle
39                   (used for last byte sending completion detection in DMA non circular mode)
40 
41     (#) Program the Baud Rate, Word Length , Stop Bit, Parity, Hardware
42         flow control and Mode(Receiver/Transmitter) in the SMARTCARD Init structure.
43 
44     (#) Initialize the SMARTCARD registers by calling the HAL_SMARTCARD_Init() API:
45         (++) These APIs configure also the low level Hardware GPIO, CLOCK, CORTEX...etc)
46              by calling the customized HAL_SMARTCARD_MspInit() API.
47     [..]
48     (@) The specific SMARTCARD interrupts (Transmission complete interrupt,
49         RXNE interrupt and Error Interrupts) will be managed using the macros
50         __HAL_SMARTCARD_ENABLE_IT() and __HAL_SMARTCARD_DISABLE_IT() inside the transmit and receive process.
51 
52     [..]
53     Three operation modes are available within this driver :
54 
55     *** Polling mode IO operation ***
56     =================================
57     [..]
58       (+) Send an amount of data in blocking mode using HAL_SMARTCARD_Transmit()
59       (+) Receive an amount of data in blocking mode using HAL_SMARTCARD_Receive()
60 
61     *** Interrupt mode IO operation ***
62     ===================================
63     [..]
64       (+) Send an amount of data in non blocking mode using HAL_SMARTCARD_Transmit_IT()
65       (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback is executed and user can
66           add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback
67       (+) Receive an amount of data in non blocking mode using HAL_SMARTCARD_Receive_IT()
68       (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback is executed and user can
69           add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback
70       (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
71           add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback
72 
73     *** DMA mode IO operation ***
74     ==============================
75     [..]
76       (+) Send an amount of data in non blocking mode (DMA) using HAL_SMARTCARD_Transmit_DMA()
77       (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback is executed and user can
78           add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback
79       (+) Receive an amount of data in non blocking mode (DMA) using HAL_SMARTCARD_Receive_DMA()
80       (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback is executed and user can
81           add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback
82       (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
83           add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback
84 
85     *** SMARTCARD HAL driver macros list ***
86     ========================================
87     [..]
88       Below the list of most used macros in SMARTCARD HAL driver.
89 
90       (+) __HAL_SMARTCARD_ENABLE: Enable the SMARTCARD peripheral
91       (+) __HAL_SMARTCARD_DISABLE: Disable the SMARTCARD peripheral
92       (+) __HAL_SMARTCARD_GET_FLAG : Check whether the specified SMARTCARD flag is set or not
93       (+) __HAL_SMARTCARD_CLEAR_FLAG : Clear the specified SMARTCARD pending flag
94       (+) __HAL_SMARTCARD_ENABLE_IT: Enable the specified SMARTCARD interrupt
95       (+) __HAL_SMARTCARD_DISABLE_IT: Disable the specified SMARTCARD interrupt
96 
97     [..]
98       (@) You can refer to the SMARTCARD HAL driver header file for more useful macros
99 
100     ##### Callback registration #####
101     ==================================
102 
103     [..]
104     The compilation define USE_HAL_SMARTCARD_REGISTER_CALLBACKS when set to 1
105     allows the user to configure dynamically the driver callbacks.
106 
107     [..]
108     Use Function @ref HAL_SMARTCARD_RegisterCallback() to register a user callback.
109     Function @ref HAL_SMARTCARD_RegisterCallback() allows to register following callbacks:
110     (+) TxCpltCallback            : Tx Complete Callback.
111     (+) RxCpltCallback            : Rx Complete Callback.
112     (+) ErrorCallback             : Error Callback.
113     (+) AbortCpltCallback         : Abort Complete Callback.
114     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
115     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
116     (+) MspInitCallback           : SMARTCARD MspInit.
117     (+) MspDeInitCallback         : SMARTCARD MspDeInit.
118     This function takes as parameters the HAL peripheral handle, the Callback ID
119     and a pointer to the user callback function.
120 
121     [..]
122     Use function @ref HAL_SMARTCARD_UnRegisterCallback() to reset a callback to the default
123     weak (surcharged) function.
124     @ref HAL_SMARTCARD_UnRegisterCallback() takes as parameters the HAL peripheral handle,
125     and the Callback ID.
126     This function allows to reset following callbacks:
127     (+) TxCpltCallback            : Tx Complete Callback.
128     (+) RxCpltCallback            : Rx Complete Callback.
129     (+) ErrorCallback             : Error Callback.
130     (+) AbortCpltCallback         : Abort Complete Callback.
131     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
132     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
133     (+) MspInitCallback           : SMARTCARD MspInit.
134     (+) MspDeInitCallback         : SMARTCARD MspDeInit.
135 
136     [..]
137     By default, after the @ref HAL_SMARTCARD_Init() and when the state is HAL_SMARTCARD_STATE_RESET
138     all callbacks are set to the corresponding weak (surcharged) functions:
139     examples @ref HAL_SMARTCARD_TxCpltCallback(), @ref HAL_SMARTCARD_RxCpltCallback().
140     Exception done for MspInit and MspDeInit functions that are respectively
141     reset to the legacy weak (surcharged) functions in the @ref HAL_SMARTCARD_Init()
142     and @ref HAL_SMARTCARD_DeInit() only when these callbacks are null (not registered beforehand).
143     If not, MspInit or MspDeInit are not null, the @ref HAL_SMARTCARD_Init() and @ref HAL_SMARTCARD_DeInit()
144     keep and use the user MspInit/MspDeInit callbacks (registered beforehand).
145 
146     [..]
147     Callbacks can be registered/unregistered in HAL_SMARTCARD_STATE_READY state only.
148     Exception done MspInit/MspDeInit that can be registered/unregistered
149     in HAL_SMARTCARD_STATE_READY or HAL_SMARTCARD_STATE_RESET state, thus registered (user)
150     MspInit/DeInit callbacks can be used during the Init/DeInit.
151     In that case first register the MspInit/MspDeInit user callbacks
152     using @ref HAL_SMARTCARD_RegisterCallback() before calling @ref HAL_SMARTCARD_DeInit()
153     or @ref HAL_SMARTCARD_Init() function.
154 
155     [..]
156     When The compilation define USE_HAL_SMARTCARD_REGISTER_CALLBACKS is set to 0 or
157     not defined, the callback registration feature is not available
158     and weak (surcharged) callbacks are used.
159 
160   @endverbatim
161   ******************************************************************************
162   * @attention
163   *
164   * <h2><center>&copy; Copyright (c) 2016 STMicroelectronics.
165   * All rights reserved.</center></h2>
166   *
167   * This software component is licensed by ST under BSD 3-Clause license,
168   * the "License"; You may not use this file except in compliance with the
169   * License. You may obtain a copy of the License at:
170   *                        opensource.org/licenses/BSD-3-Clause
171   *
172   ******************************************************************************
173   */
174 
175 /* Includes ------------------------------------------------------------------*/
176 #include "stm32f4xx_hal.h"
177 
178 /** @addtogroup STM32F4xx_HAL_Driver
179   * @{
180   */
181 
182 /** @defgroup SMARTCARD SMARTCARD
183   * @brief HAL SMARTCARD module driver
184   * @{
185   */
186 #ifdef HAL_SMARTCARD_MODULE_ENABLED
187 /* Private typedef -----------------------------------------------------------*/
188 /* Private define ------------------------------------------------------------*/
189 /** @addtogroup SMARTCARD_Private_Constants
190   * @{
191   */
192 /**
193   * @}
194   */
195 
196 /* Private macro -------------------------------------------------------------*/
197 /* Private variables ---------------------------------------------------------*/
198 /* Private function prototypes -----------------------------------------------*/
199 /** @addtogroup SMARTCARD_Private_Functions
200   * @{
201   */
202 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
203 void SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef *hsc);
204 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
205 static void SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef *hsc);
206 static void SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef *hsc);
207 static void SMARTCARD_SetConfig (SMARTCARD_HandleTypeDef *hsc);
208 static HAL_StatusTypeDef SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsc);
209 static HAL_StatusTypeDef SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsc);
210 static HAL_StatusTypeDef SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsc);
211 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma);
212 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma);
213 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma);
214 static void SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef *hdma);
215 static void SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef *hdma);
216 static void SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef *hdma);
217 static void SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
218 static void SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
219 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsc, uint32_t Flag, FlagStatus Status, uint32_t Tickstart, uint32_t Timeout);
220 /**
221   * @}
222   */
223 
224 /* Exported functions --------------------------------------------------------*/
225 /** @defgroup SMARTCARD_Exported_Functions SMARTCARD Exported Functions
226   * @{
227   */
228 
229 /** @defgroup SMARTCARD_Exported_Functions_Group1 SmartCard Initialization and de-initialization functions
230   *  @brief    Initialization and Configuration functions
231   *
232 @verbatim
233   ==============================================================================
234               ##### Initialization and Configuration functions #####
235   ==============================================================================
236   [..]
237   This subsection provides a set of functions allowing to initialize the USART
238   in Smartcard mode.
239   [..]
240   The Smartcard interface is designed to support asynchronous protocol Smartcards as
241   defined in the ISO 7816-3 standard.
242   [..]
243   The USART can provide a clock to the smartcard through the SCLK output.
244   In smartcard mode, SCLK is not associated to the communication but is simply derived
245   from the internal peripheral input clock through a 5-bit prescaler.
246   [..]
247   (+) For the Smartcard mode only these parameters can be configured:
248       (++) Baud Rate
249       (++) Word Length => Should be 9 bits (8 bits + parity)
250       (++) Stop Bit
251       (++) Parity: => Should be enabled
252       (++) USART polarity
253       (++) USART phase
254       (++) USART LastBit
255       (++) Receiver/transmitter modes
256       (++) Prescaler
257       (++) GuardTime
258       (++) NACKState: The Smartcard NACK state
259 
260      (+) Recommended SmartCard interface configuration to get the Answer to Reset from the Card:
261         (++) Word Length = 9 Bits
262         (++) 1.5 Stop Bit
263         (++) Even parity
264         (++) BaudRate = 12096 baud
265         (++) Tx and Rx enabled
266   [..]
267   Please refer to the ISO 7816-3 specification for more details.
268 
269   [..]
270    (@) It is also possible to choose 0.5 stop bit for receiving but it is recommended
271        to use 1.5 stop bits for both transmitting and receiving to avoid switching
272        between the two configurations.
273   [..]
274     The HAL_SMARTCARD_Init() function follows the USART  SmartCard configuration
275     procedures (details for the procedures are available in reference manual
276     (RM0430 for STM32F4X3xx MCUs and RM0402 for STM32F412xx MCUs
277      RM0383 for STM32F411xC/E MCUs and RM0401 for STM32F410xx MCUs
278      RM0090 for STM32F4X5xx/STM32F4X7xx/STM32F429xx/STM32F439xx MCUs
279      RM0390 for STM32F446xx MCUs and RM0386 for STM32F469xx/STM32F479xx MCUs)).
280 
281 @endverbatim
282 
283   The SMARTCARD frame format is given in the following table:
284        +-------------------------------------------------------------+
285        |   M bit |  PCE bit  |        SMARTCARD frame                |
286        |---------------------|---------------------------------------|
287        |    1    |    1      |    | SB | 8 bit data | PB | STB |     |
288        +-------------------------------------------------------------+
289   * @{
290   */
291 
292 /**
293   * @brief  Initializes the SmartCard mode according to the specified
294   *         parameters in the SMARTCARD_InitTypeDef and create the associated handle.
295   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
296   *                the configuration information for SMARTCARD module.
297   * @retval HAL status
298   */
HAL_SMARTCARD_Init(SMARTCARD_HandleTypeDef * hsc)299 HAL_StatusTypeDef HAL_SMARTCARD_Init(SMARTCARD_HandleTypeDef *hsc)
300 {
301   /* Check the SMARTCARD handle allocation */
302   if(hsc == NULL)
303   {
304     return HAL_ERROR;
305   }
306 
307   /* Check the parameters */
308   assert_param(IS_SMARTCARD_INSTANCE(hsc->Instance));
309   assert_param(IS_SMARTCARD_NACK_STATE(hsc->Init.NACKState));
310 
311   if(hsc->gState == HAL_SMARTCARD_STATE_RESET)
312   {
313     /* Allocate lock resource and initialize it */
314     hsc->Lock = HAL_UNLOCKED;
315 
316 #if USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1
317     SMARTCARD_InitCallbacksToDefault(hsc);
318 
319     if (hsc->MspInitCallback == NULL)
320     {
321       hsc->MspInitCallback = HAL_SMARTCARD_MspInit;
322     }
323 
324     /* Init the low level hardware */
325     hsc->MspInitCallback(hsc);
326 #else
327     /* Init the low level hardware : GPIO, CLOCK */
328     HAL_SMARTCARD_MspInit(hsc);
329 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
330   }
331 
332   hsc->gState = HAL_SMARTCARD_STATE_BUSY;
333 
334   /* Set the Prescaler */
335   MODIFY_REG(hsc->Instance->GTPR, USART_GTPR_PSC, hsc->Init.Prescaler);
336 
337   /* Set the Guard Time */
338   MODIFY_REG(hsc->Instance->GTPR, USART_GTPR_GT, ((hsc->Init.GuardTime)<<8U));
339 
340   /* Set the Smartcard Communication parameters */
341   SMARTCARD_SetConfig(hsc);
342 
343   /* In SmartCard mode, the following bits must be kept cleared:
344   - LINEN bit in the USART_CR2 register
345   - HDSEL and IREN bits in the USART_CR3 register.*/
346   CLEAR_BIT(hsc->Instance->CR2, USART_CR2_LINEN);
347   CLEAR_BIT(hsc->Instance->CR3, (USART_CR3_IREN | USART_CR3_HDSEL));
348 
349   /* Enable the SMARTCARD Parity Error Interrupt */
350   SET_BIT(hsc->Instance->CR1, USART_CR1_PEIE);
351 
352   /* Enable the SMARTCARD Framing Error Interrupt */
353   SET_BIT(hsc->Instance->CR3, USART_CR3_EIE);
354 
355   /* Enable the Peripheral */
356   __HAL_SMARTCARD_ENABLE(hsc);
357 
358   /* Configure the Smartcard NACK state */
359   MODIFY_REG(hsc->Instance->CR3, USART_CR3_NACK, hsc->Init.NACKState);
360 
361   /* Enable the SC mode by setting the SCEN bit in the CR3 register */
362   hsc->Instance->CR3 |= (USART_CR3_SCEN);
363 
364   /* Initialize the SMARTCARD state*/
365   hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
366   hsc->gState= HAL_SMARTCARD_STATE_READY;
367   hsc->RxState= HAL_SMARTCARD_STATE_READY;
368 
369   return HAL_OK;
370 }
371 
372 /**
373   * @brief DeInitializes the USART SmartCard peripheral
374   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
375   *                the configuration information for SMARTCARD module.
376   * @retval HAL status
377   */
HAL_SMARTCARD_DeInit(SMARTCARD_HandleTypeDef * hsc)378 HAL_StatusTypeDef HAL_SMARTCARD_DeInit(SMARTCARD_HandleTypeDef *hsc)
379 {
380   /* Check the SMARTCARD handle allocation */
381   if(hsc == NULL)
382   {
383     return HAL_ERROR;
384   }
385 
386   /* Check the parameters */
387   assert_param(IS_SMARTCARD_INSTANCE(hsc->Instance));
388 
389   hsc->gState = HAL_SMARTCARD_STATE_BUSY;
390 
391   /* Disable the Peripheral */
392   __HAL_SMARTCARD_DISABLE(hsc);
393 
394   /* DeInit the low level hardware */
395 #if USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1
396   if (hsc->MspDeInitCallback == NULL)
397   {
398     hsc->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;
399   }
400   /* DeInit the low level hardware */
401   hsc->MspDeInitCallback(hsc);
402 #else
403   HAL_SMARTCARD_MspDeInit(hsc);
404 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
405 
406   hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
407   hsc->gState = HAL_SMARTCARD_STATE_RESET;
408   hsc->RxState = HAL_SMARTCARD_STATE_RESET;
409 
410   /* Release Lock */
411   __HAL_UNLOCK(hsc);
412 
413   return HAL_OK;
414 }
415 
416 /**
417   * @brief  SMARTCARD MSP Init
418   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
419   *                the configuration information for SMARTCARD module.
420   * @retval None
421   */
HAL_SMARTCARD_MspInit(SMARTCARD_HandleTypeDef * hsc)422 __weak void HAL_SMARTCARD_MspInit(SMARTCARD_HandleTypeDef *hsc)
423 {
424   /* Prevent unused argument(s) compilation warning */
425   UNUSED(hsc);
426 
427   /* NOTE : This function should not be modified, when the callback is needed,
428             the HAL_SMARTCARD_MspInit can be implemented in the user file
429    */
430 }
431 
432 /**
433   * @brief SMARTCARD MSP DeInit
434   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
435   *                the configuration information for SMARTCARD module.
436   * @retval None
437   */
HAL_SMARTCARD_MspDeInit(SMARTCARD_HandleTypeDef * hsc)438 __weak void HAL_SMARTCARD_MspDeInit(SMARTCARD_HandleTypeDef *hsc)
439 {
440   /* Prevent unused argument(s) compilation warning */
441   UNUSED(hsc);
442 
443   /* NOTE : This function should not be modified, when the callback is needed,
444             the HAL_SMARTCARD_MspDeInit can be implemented in the user file
445    */
446 }
447 
448 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
449 /**
450   * @brief  Register a User SMARTCARD Callback
451   *         To be used instead of the weak predefined callback
452   * @param  hsc smartcard handle
453   * @param  CallbackID ID of the callback to be registered
454   *         This parameter can be one of the following values:
455   *           @arg @ref HAL_SMARTCARD_TX_COMPLETE_CB_ID Tx Complete Callback ID
456   *           @arg @ref HAL_SMARTCARD_RX_COMPLETE_CB_ID Rx Complete Callback ID
457   *           @arg @ref HAL_SMARTCARD_ERROR_CB_ID Error Callback ID
458   *           @arg @ref HAL_SMARTCARD_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
459   *           @arg @ref HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
460   *           @arg @ref HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
461   *           @arg @ref HAL_SMARTCARD_MSPINIT_CB_ID MspInit Callback ID
462   *           @arg @ref HAL_SMARTCARD_MSPDEINIT_CB_ID MspDeInit Callback ID
463   * @param  pCallback pointer to the Callback function
464   * @retval HAL status
465   */
HAL_SMARTCARD_RegisterCallback(SMARTCARD_HandleTypeDef * hsc,HAL_SMARTCARD_CallbackIDTypeDef CallbackID,pSMARTCARD_CallbackTypeDef pCallback)466 HAL_StatusTypeDef HAL_SMARTCARD_RegisterCallback(SMARTCARD_HandleTypeDef *hsc, HAL_SMARTCARD_CallbackIDTypeDef CallbackID, pSMARTCARD_CallbackTypeDef pCallback)
467 {
468   HAL_StatusTypeDef status = HAL_OK;
469 
470   if (pCallback == NULL)
471   {
472     /* Update the error code */
473     hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
474 
475     return HAL_ERROR;
476   }
477   /* Process locked */
478   __HAL_LOCK(hsc);
479 
480   if (hsc->gState == HAL_SMARTCARD_STATE_READY)
481   {
482     switch (CallbackID)
483     {
484 
485       case HAL_SMARTCARD_TX_COMPLETE_CB_ID :
486         hsc->TxCpltCallback = pCallback;
487         break;
488 
489       case HAL_SMARTCARD_RX_COMPLETE_CB_ID :
490         hsc->RxCpltCallback = pCallback;
491         break;
492 
493       case HAL_SMARTCARD_ERROR_CB_ID :
494         hsc->ErrorCallback = pCallback;
495         break;
496 
497       case HAL_SMARTCARD_ABORT_COMPLETE_CB_ID :
498         hsc->AbortCpltCallback = pCallback;
499         break;
500 
501       case HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID :
502         hsc->AbortTransmitCpltCallback = pCallback;
503         break;
504 
505       case HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID :
506         hsc->AbortReceiveCpltCallback = pCallback;
507         break;
508 
509 
510       case HAL_SMARTCARD_MSPINIT_CB_ID :
511         hsc->MspInitCallback = pCallback;
512         break;
513 
514       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
515         hsc->MspDeInitCallback = pCallback;
516         break;
517 
518       default :
519         /* Update the error code */
520         hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
521 
522         /* Return error status */
523         status =  HAL_ERROR;
524         break;
525     }
526   }
527   else if (hsc->gState == HAL_SMARTCARD_STATE_RESET)
528   {
529     switch (CallbackID)
530     {
531       case HAL_SMARTCARD_MSPINIT_CB_ID :
532         hsc->MspInitCallback = pCallback;
533         break;
534 
535       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
536         hsc->MspDeInitCallback = pCallback;
537         break;
538 
539       default :
540         /* Update the error code */
541         hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
542 
543         /* Return error status */
544         status =  HAL_ERROR;
545         break;
546     }
547   }
548   else
549   {
550     /* Update the error code */
551     hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
552 
553     /* Return error status */
554     status =  HAL_ERROR;
555   }
556 
557   /* Release Lock */
558   __HAL_UNLOCK(hsc);
559 
560   return status;
561 }
562 
563 /**
564   * @brief  Unregister an SMARTCARD callback
565   *         SMARTCARD callback is redirected to the weak predefined callback
566   * @param  hsc smartcard handle
567   * @param  CallbackID ID of the callback to be unregistered
568   *         This parameter can be one of the following values:
569   *           @arg @ref HAL_SMARTCARD_TX_COMPLETE_CB_ID Tx Complete Callback ID
570   *           @arg @ref HAL_SMARTCARD_RX_COMPLETE_CB_ID Rx Complete Callback ID
571   *           @arg @ref HAL_SMARTCARD_ERROR_CB_ID Error Callback ID
572   *           @arg @ref HAL_SMARTCARD_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
573   *           @arg @ref HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
574   *           @arg @ref HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
575   *           @arg @ref HAL_SMARTCARD_MSPINIT_CB_ID MspInit Callback ID
576   *           @arg @ref HAL_SMARTCARD_MSPDEINIT_CB_ID MspDeInit Callback ID
577   * @retval HAL status
578   */
HAL_SMARTCARD_UnRegisterCallback(SMARTCARD_HandleTypeDef * hsc,HAL_SMARTCARD_CallbackIDTypeDef CallbackID)579 HAL_StatusTypeDef HAL_SMARTCARD_UnRegisterCallback(SMARTCARD_HandleTypeDef *hsc, HAL_SMARTCARD_CallbackIDTypeDef CallbackID)
580 {
581   HAL_StatusTypeDef status = HAL_OK;
582 
583   /* Process locked */
584   __HAL_LOCK(hsc);
585 
586   if (HAL_SMARTCARD_STATE_READY == hsc->gState)
587   {
588     switch (CallbackID)
589     {
590       case HAL_SMARTCARD_TX_COMPLETE_CB_ID :
591         hsc->TxCpltCallback = HAL_SMARTCARD_TxCpltCallback;                       /* Legacy weak TxCpltCallback            */
592         break;
593 
594       case HAL_SMARTCARD_RX_COMPLETE_CB_ID :
595         hsc->RxCpltCallback = HAL_SMARTCARD_RxCpltCallback;                       /* Legacy weak RxCpltCallback            */
596         break;
597 
598       case HAL_SMARTCARD_ERROR_CB_ID :
599         hsc->ErrorCallback = HAL_SMARTCARD_ErrorCallback;                         /* Legacy weak ErrorCallback             */
600         break;
601 
602       case HAL_SMARTCARD_ABORT_COMPLETE_CB_ID :
603         hsc->AbortCpltCallback = HAL_SMARTCARD_AbortCpltCallback;                 /* Legacy weak AbortCpltCallback         */
604         break;
605 
606       case HAL_SMARTCARD_ABORT_TRANSMIT_COMPLETE_CB_ID :
607         hsc->AbortTransmitCpltCallback = HAL_SMARTCARD_AbortTransmitCpltCallback; /* Legacy weak AbortTransmitCpltCallback */
608         break;
609 
610       case HAL_SMARTCARD_ABORT_RECEIVE_COMPLETE_CB_ID :
611         hsc->AbortReceiveCpltCallback = HAL_SMARTCARD_AbortReceiveCpltCallback;   /* Legacy weak AbortReceiveCpltCallback  */
612         break;
613 
614 
615       case HAL_SMARTCARD_MSPINIT_CB_ID :
616         hsc->MspInitCallback = HAL_SMARTCARD_MspInit;                             /* Legacy weak MspInitCallback           */
617         break;
618 
619       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
620         hsc->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;                         /* Legacy weak MspDeInitCallback         */
621         break;
622 
623       default :
624         /* Update the error code */
625         hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
626 
627         /* Return error status */
628         status =  HAL_ERROR;
629         break;
630     }
631   }
632   else if (HAL_SMARTCARD_STATE_RESET == hsc->gState)
633   {
634     switch (CallbackID)
635     {
636       case HAL_SMARTCARD_MSPINIT_CB_ID :
637         hsc->MspInitCallback = HAL_SMARTCARD_MspInit;
638         break;
639 
640       case HAL_SMARTCARD_MSPDEINIT_CB_ID :
641         hsc->MspDeInitCallback = HAL_SMARTCARD_MspDeInit;
642         break;
643 
644       default :
645         /* Update the error code */
646         hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
647 
648         /* Return error status */
649         status =  HAL_ERROR;
650         break;
651     }
652   }
653   else
654   {
655     /* Update the error code */
656     hsc->ErrorCode |= HAL_SMARTCARD_ERROR_INVALID_CALLBACK;
657 
658     /* Return error status */
659     status =  HAL_ERROR;
660   }
661 
662   /* Release Lock */
663   __HAL_UNLOCK(hsc);
664 
665   return status;
666 }
667 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
668 
669 /**
670   * @}
671   */
672 
673 /** @defgroup SMARTCARD_Exported_Functions_Group2 IO operation functions
674   * @brief    SMARTCARD Transmit and Receive functions
675   *
676 @verbatim
677  ===============================================================================
678                       ##### IO operation functions #####
679  ===============================================================================
680  [..]
681    This subsection provides a set of functions allowing to manage the SMARTCARD data transfers.
682 
683  [..]
684     (#) Smartcard is a single wire half duplex communication protocol.
685     The Smartcard interface is designed to support asynchronous protocol Smartcards as
686     defined in the ISO 7816-3 standard.
687     (#) The USART should be configured as:
688        (++) 8 bits plus parity: where M=1 and PCE=1 in the USART_CR1 register
689        (++) 1.5 stop bits when transmitting and receiving: where STOP=11 in the USART_CR2 register.
690 
691     (#) There are two modes of transfer:
692        (++) Blocking mode: The communication is performed in polling mode.
693             The HAL status of all data processing is returned by the same function
694             after finishing transfer.
695        (++) Non Blocking mode: The communication is performed using Interrupts
696            or DMA, These APIs return the HAL status.
697            The end of the data processing will be indicated through the
698            dedicated SMARTCARD IRQ when using Interrupt mode or the DMA IRQ when
699            using DMA mode.
700            The HAL_SMARTCARD_TxCpltCallback(), HAL_SMARTCARD_RxCpltCallback() user callbacks
701            will be executed respectively at the end of the Transmit or Receive process
702            The HAL_SMARTCARD_ErrorCallback() user callback will be executed when a communication error is detected
703 
704     (#) Blocking mode APIs are :
705         (++) HAL_SMARTCARD_Transmit()
706         (++) HAL_SMARTCARD_Receive()
707 
708     (#) Non Blocking mode APIs with Interrupt are :
709         (++) HAL_SMARTCARD_Transmit_IT()
710         (++) HAL_SMARTCARD_Receive_IT()
711         (++) HAL_SMARTCARD_IRQHandler()
712 
713     (#) Non Blocking mode functions with DMA are :
714         (++) HAL_SMARTCARD_Transmit_DMA()
715         (++) HAL_SMARTCARD_Receive_DMA()
716 
717     (#) A set of Transfer Complete Callbacks are provided in non Blocking mode:
718         (++) HAL_SMARTCARD_TxCpltCallback()
719         (++) HAL_SMARTCARD_RxCpltCallback()
720         (++) HAL_SMARTCARD_ErrorCallback()
721 
722     (#) Non-Blocking mode transfers could be aborted using Abort API's :
723         (+) HAL_SMARTCARD_Abort()
724         (+) HAL_SMARTCARD_AbortTransmit()
725         (+) HAL_SMARTCARD_AbortReceive()
726         (+) HAL_SMARTCARD_Abort_IT()
727         (+) HAL_SMARTCARD_AbortTransmit_IT()
728         (+) HAL_SMARTCARD_AbortReceive_IT()
729 
730     (#) For Abort services based on interrupts (HAL_SMARTCARD_Abortxxx_IT), a set of Abort Complete Callbacks are provided:
731         (+) HAL_SMARTCARD_AbortCpltCallback()
732         (+) HAL_SMARTCARD_AbortTransmitCpltCallback()
733         (+) HAL_SMARTCARD_AbortReceiveCpltCallback()
734 
735     (#) In Non-Blocking mode transfers, possible errors are split into 2 categories.
736         Errors are handled as follows :
737        (+) Error is considered as Recoverable and non blocking : Transfer could go till end, but error severity is
738            to be evaluated by user : this concerns Frame Error, Parity Error or Noise Error in Interrupt mode reception .
739            Received character is then retrieved and stored in Rx buffer, Error code is set to allow user to identify error type,
740            and HAL_SMARTCARD_ErrorCallback() user callback is executed. Transfer is kept ongoing on SMARTCARD side.
741            If user wants to abort it, Abort services should be called by user.
742        (+) Error is considered as Blocking : Transfer could not be completed properly and is aborted.
743            This concerns Frame Error in Interrupt mode tranmission, Overrun Error in Interrupt mode reception and all errors in DMA mode.
744            Error code is set to allow user to identify error type, and HAL_SMARTCARD_ErrorCallback() user callback is executed.
745 
746 @endverbatim
747   * @{
748   */
749 
750 /**
751   * @brief Send an amount of data in blocking mode
752   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
753   *                the configuration information for SMARTCARD module.
754   * @param  pData  Pointer to data buffer
755   * @param  Size   Amount of data to be sent
756   * @param  Timeout Timeout duration
757   * @retval HAL status
758   */
HAL_SMARTCARD_Transmit(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size,uint32_t Timeout)759 HAL_StatusTypeDef HAL_SMARTCARD_Transmit(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size, uint32_t Timeout)
760 {
761   uint16_t* tmp;
762   uint32_t tickstart = 0U;
763 
764   if(hsc->gState == HAL_SMARTCARD_STATE_READY)
765   {
766     if((pData == NULL) || (Size == 0U))
767     {
768       return  HAL_ERROR;
769     }
770 
771     /* Process Locked */
772     __HAL_LOCK(hsc);
773 
774     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
775     hsc->gState = HAL_SMARTCARD_STATE_BUSY_TX;
776 
777     /* Init tickstart for timeout managment */
778     tickstart = HAL_GetTick();
779 
780     hsc->TxXferSize = Size;
781     hsc->TxXferCount = Size;
782     while(hsc->TxXferCount > 0U)
783     {
784       hsc->TxXferCount--;
785       if(SMARTCARD_WaitOnFlagUntilTimeout(hsc, SMARTCARD_FLAG_TXE, RESET, tickstart, Timeout) != HAL_OK)
786       {
787         return HAL_TIMEOUT;
788       }
789       tmp = (uint16_t*) pData;
790       hsc->Instance->DR = (*tmp & (uint16_t)0x01FF);
791       pData +=1U;
792     }
793 
794     if(SMARTCARD_WaitOnFlagUntilTimeout(hsc, SMARTCARD_FLAG_TC, RESET, tickstart, Timeout) != HAL_OK)
795     {
796       return HAL_TIMEOUT;
797     }
798 
799 	/* At end of Tx process, restore hsc->gState to Ready */
800     hsc->gState = HAL_SMARTCARD_STATE_READY;
801 
802     /* Process Unlocked */
803     __HAL_UNLOCK(hsc);
804 
805     return HAL_OK;
806   }
807   else
808   {
809     return HAL_BUSY;
810   }
811 }
812 
813 /**
814   * @brief Receive an amount of data in blocking mode
815   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
816   *                the configuration information for SMARTCARD module.
817   * @param  pData  Pointer to data buffer
818   * @param  Size   Amount of data to be received
819   * @param  Timeout Timeout duration
820   * @retval HAL status
821   */
HAL_SMARTCARD_Receive(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size,uint32_t Timeout)822 HAL_StatusTypeDef HAL_SMARTCARD_Receive(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size, uint32_t Timeout)
823 {
824   uint16_t* tmp;
825   uint32_t tickstart = 0U;
826 
827   if(hsc->RxState == HAL_SMARTCARD_STATE_READY)
828   {
829     if((pData == NULL) || (Size == 0U))
830     {
831       return  HAL_ERROR;
832     }
833 
834     /* Process Locked */
835     __HAL_LOCK(hsc);
836 
837     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
838     hsc->RxState = HAL_SMARTCARD_STATE_BUSY_RX;
839 
840     /* Init tickstart for timeout managment */
841     tickstart = HAL_GetTick();
842 
843     hsc->RxXferSize = Size;
844     hsc->RxXferCount = Size;
845 
846     /* Check the remain data to be received */
847     while(hsc->RxXferCount > 0U)
848     {
849       hsc->RxXferCount--;
850       if(SMARTCARD_WaitOnFlagUntilTimeout(hsc, SMARTCARD_FLAG_RXNE, RESET, tickstart, Timeout) != HAL_OK)
851       {
852         return HAL_TIMEOUT;
853       }
854       tmp = (uint16_t*) pData;
855       *tmp = (uint8_t)(hsc->Instance->DR & (uint8_t)0xFF);
856       pData +=1U;
857     }
858 
859     /* At end of Rx process, restore hsc->RxState to Ready */
860     hsc->RxState = HAL_SMARTCARD_STATE_READY;
861 
862     /* Process Unlocked */
863     __HAL_UNLOCK(hsc);
864 
865     return HAL_OK;
866   }
867   else
868   {
869     return HAL_BUSY;
870   }
871 }
872 
873 /**
874   * @brief Send an amount of data in non blocking mode
875   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
876   *                the configuration information for SMARTCARD module.
877   * @param  pData  Pointer to data buffer
878   * @param  Size   Amount of data to be sent
879   * @retval HAL status
880   */
HAL_SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size)881 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size)
882 {
883   /* Check that a Tx process is not already ongoing */
884   if(hsc->gState == HAL_SMARTCARD_STATE_READY)
885   {
886     if((pData == NULL) || (Size == 0U))
887     {
888       return HAL_ERROR;
889     }
890 
891     /* Process Locked */
892     __HAL_LOCK(hsc);
893 
894     hsc->pTxBuffPtr = pData;
895     hsc->TxXferSize = Size;
896     hsc->TxXferCount = Size;
897 
898     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
899     hsc->gState = HAL_SMARTCARD_STATE_BUSY_TX;
900 
901     /* Process Unlocked */
902     __HAL_UNLOCK(hsc);
903 
904     /* Enable the SMARTCARD Parity Error Interrupt */
905     SET_BIT(hsc->Instance->CR1, USART_CR1_PEIE);
906 
907     /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
908     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
909 
910     /* Enable the SMARTCARD Transmit data register empty Interrupt */
911     SET_BIT(hsc->Instance->CR1, USART_CR1_TXEIE);
912 
913     return HAL_OK;
914   }
915   else
916   {
917     return HAL_BUSY;
918   }
919 }
920 
921 /**
922   * @brief Receive an amount of data in non blocking mode
923   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
924   *                the configuration information for SMARTCARD module.
925   * @param  pData  Pointer to data buffer
926   * @param  Size   Amount of data to be received
927   * @retval HAL status
928   */
HAL_SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size)929 HAL_StatusTypeDef HAL_SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size)
930 {
931   /* Check that a Rx process is not already ongoing */
932   if(hsc->RxState == HAL_SMARTCARD_STATE_READY)
933   {
934     if((pData == NULL) || (Size == 0U))
935     {
936       return HAL_ERROR;
937     }
938 
939     /* Process Locked */
940     __HAL_LOCK(hsc);
941 
942     hsc->pRxBuffPtr = pData;
943     hsc->RxXferSize = Size;
944     hsc->RxXferCount = Size;
945 
946     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
947     hsc->RxState = HAL_SMARTCARD_STATE_BUSY_RX;
948 
949     /* Process Unlocked */
950     __HAL_UNLOCK(hsc);
951 
952     /* Enable the SMARTCARD Parity Error and Data Register not empty Interrupts */
953     SET_BIT(hsc->Instance->CR1, USART_CR1_PEIE| USART_CR1_RXNEIE);
954 
955     /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
956     SET_BIT(hsc->Instance->CR3, USART_CR3_EIE);
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 non blocking mode
968   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
969   *                the configuration information for SMARTCARD module.
970   * @param  pData  Pointer to data buffer
971   * @param  Size   Amount of data to be sent
972   * @retval HAL status
973   */
HAL_SMARTCARD_Transmit_DMA(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size)974 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_DMA(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size)
975 {
976   uint32_t *tmp;
977 
978   /* Check that a Tx process is not already ongoing */
979   if(hsc->gState == HAL_SMARTCARD_STATE_READY)
980   {
981     if((pData == NULL) || (Size == 0U))
982     {
983       return HAL_ERROR;
984     }
985 
986     /* Process Locked */
987     __HAL_LOCK(hsc);
988 
989     hsc->pTxBuffPtr = pData;
990     hsc->TxXferSize = Size;
991     hsc->TxXferCount = Size;
992 
993     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
994     hsc->gState = HAL_SMARTCARD_STATE_BUSY_TX;
995 
996     /* Set the SMARTCARD DMA transfer complete callback */
997     hsc->hdmatx->XferCpltCallback = SMARTCARD_DMATransmitCplt;
998 
999     /* Set the DMA error callback */
1000     hsc->hdmatx->XferErrorCallback = SMARTCARD_DMAError;
1001 
1002     /* Set the DMA abort callback */
1003     hsc->hdmatx->XferAbortCallback = NULL;
1004 
1005     /* Enable the SMARTCARD transmit DMA stream */
1006     tmp = (uint32_t*)&pData;
1007     HAL_DMA_Start_IT(hsc->hdmatx, *(uint32_t*)tmp, (uint32_t)&hsc->Instance->DR, Size);
1008 
1009      /* Clear the TC flag in the SR register by writing 0 to it */
1010     __HAL_SMARTCARD_CLEAR_FLAG(hsc, SMARTCARD_FLAG_TC);
1011 
1012     /* Process Unlocked */
1013     __HAL_UNLOCK(hsc);
1014 
1015     /* Enable the DMA transfer for transmit request by setting the DMAT bit
1016     in the SMARTCARD CR3 register */
1017     SET_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1018 
1019     return HAL_OK;
1020   }
1021   else
1022   {
1023     return HAL_BUSY;
1024   }
1025 }
1026 
1027 /**
1028   * @brief Receive an amount of data in non blocking mode
1029   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1030   *                the configuration information for SMARTCARD module.
1031   * @param  pData  Pointer to data buffer
1032   * @param  Size   Amount of data to be received
1033   * @note   When the SMARTCARD parity is enabled (PCE = 1) the data received contain the parity bit.s
1034   * @retval HAL status
1035   */
HAL_SMARTCARD_Receive_DMA(SMARTCARD_HandleTypeDef * hsc,uint8_t * pData,uint16_t Size)1036 HAL_StatusTypeDef HAL_SMARTCARD_Receive_DMA(SMARTCARD_HandleTypeDef *hsc, uint8_t *pData, uint16_t Size)
1037 {
1038   uint32_t *tmp;
1039 
1040   /* Check that a Rx process is not already ongoing */
1041   if(hsc->RxState == HAL_SMARTCARD_STATE_READY)
1042   {
1043     if((pData == NULL) || (Size == 0U))
1044     {
1045       return HAL_ERROR;
1046     }
1047 
1048     /* Process Locked */
1049     __HAL_LOCK(hsc);
1050 
1051     hsc->pRxBuffPtr = pData;
1052     hsc->RxXferSize = Size;
1053 
1054     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1055     hsc->RxState = HAL_SMARTCARD_STATE_BUSY_RX;
1056 
1057     /* Set the SMARTCARD DMA transfer complete callback */
1058     hsc->hdmarx->XferCpltCallback = SMARTCARD_DMAReceiveCplt;
1059 
1060     /* Set the DMA error callback */
1061     hsc->hdmarx->XferErrorCallback = SMARTCARD_DMAError;
1062 
1063     /* Set the DMA abort callback */
1064     hsc->hdmatx->XferAbortCallback = NULL;
1065 
1066     /* Enable the DMA stream */
1067     tmp = (uint32_t*)&pData;
1068     HAL_DMA_Start_IT(hsc->hdmarx, (uint32_t)&hsc->Instance->DR, *(uint32_t*)tmp, Size);
1069 
1070     /* Clear the Overrun flag just before enabling the DMA Rx request: can be mandatory for the second transfer */
1071     __HAL_SMARTCARD_CLEAR_OREFLAG(hsc);
1072 
1073     /* Process Unlocked */
1074     __HAL_UNLOCK(hsc);
1075 
1076     /* Enable the SMARTCARD Parity Error Interrupt */
1077     SET_BIT(hsc->Instance->CR1, USART_CR1_PEIE);
1078 
1079     /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
1080     SET_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1081 
1082     /* Enable the DMA transfer for the receiver request by setting the DMAR bit
1083     in the SMARTCARD CR3 register */
1084     SET_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1085 
1086     return HAL_OK;
1087   }
1088   else
1089   {
1090     return HAL_BUSY;
1091   }
1092 }
1093 
1094 /**
1095   * @brief  Abort ongoing transfers (blocking mode).
1096   * @param  hsc SMARTCARD handle.
1097   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1098   *         This procedure performs following operations :
1099   *           - Disable PPP Interrupts
1100   *           - Disable the DMA transfer in the peripheral register (if enabled)
1101   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1102   *           - Set handle State to READY
1103   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1104   * @retval HAL status
1105 */
HAL_SMARTCARD_Abort(SMARTCARD_HandleTypeDef * hsc)1106 HAL_StatusTypeDef HAL_SMARTCARD_Abort(SMARTCARD_HandleTypeDef *hsc)
1107 {
1108   /* Disable TXEIE, TCIE, RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1109   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE | USART_CR1_TXEIE | USART_CR1_TCIE));
1110   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1111 
1112   /* Disable the SMARTCARD DMA Tx request if enabled */
1113   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT))
1114   {
1115     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1116 
1117     /* Abort the SMARTCARD DMA Tx channel : use blocking DMA Abort API (no callback) */
1118     if(hsc->hdmatx != NULL)
1119     {
1120       /* Set the SMARTCARD DMA Abort callback to Null.
1121          No call back execution at end of DMA abort procedure */
1122       hsc->hdmatx->XferAbortCallback = NULL;
1123 
1124       HAL_DMA_Abort(hsc->hdmatx);
1125     }
1126   }
1127 
1128   /* Disable the SMARTCARD DMA Rx request if enabled */
1129   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1130   {
1131     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1132 
1133     /* Abort the SMARTCARD DMA Rx channel : use blocking DMA Abort API (no callback) */
1134     if(hsc->hdmarx != NULL)
1135     {
1136       /* Set the SMARTCARD DMA Abort callback to Null.
1137          No call back execution at end of DMA abort procedure */
1138       hsc->hdmarx->XferAbortCallback = NULL;
1139 
1140       HAL_DMA_Abort(hsc->hdmarx);
1141     }
1142   }
1143 
1144   /* Reset Tx and Rx transfer counters */
1145   hsc->TxXferCount = 0x00U;
1146   hsc->RxXferCount = 0x00U;
1147 
1148   /* Reset ErrorCode */
1149   hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1150 
1151   /* Restore hsc->RxState and hsc->gState to Ready */
1152   hsc->RxState = HAL_SMARTCARD_STATE_READY;
1153   hsc->gState = HAL_SMARTCARD_STATE_READY;
1154 
1155   return HAL_OK;
1156 }
1157 
1158 /**
1159   * @brief  Abort ongoing Transmit transfer (blocking mode).
1160   * @param  hsc SMARTCARD handle.
1161   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1162   *         This procedure performs following operations :
1163   *           - Disable SMARTCARD Interrupts (Tx)
1164   *           - Disable the DMA transfer in the peripheral register (if enabled)
1165   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1166   *           - Set handle State to READY
1167   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1168   * @retval HAL status
1169 */
HAL_SMARTCARD_AbortTransmit(SMARTCARD_HandleTypeDef * hsc)1170 HAL_StatusTypeDef HAL_SMARTCARD_AbortTransmit(SMARTCARD_HandleTypeDef *hsc)
1171 {
1172   /* Disable TXEIE and TCIE interrupts */
1173   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_TXEIE | USART_CR1_TCIE));
1174 
1175   /* Disable the SMARTCARD DMA Tx request if enabled */
1176   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT))
1177   {
1178     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1179 
1180     /* Abort the SMARTCARD DMA Tx channel : use blocking DMA Abort API (no callback) */
1181     if(hsc->hdmatx != NULL)
1182     {
1183       /* Set the SMARTCARD DMA Abort callback to Null.
1184          No call back execution at end of DMA abort procedure */
1185       hsc->hdmatx->XferAbortCallback = NULL;
1186 
1187       HAL_DMA_Abort(hsc->hdmatx);
1188     }
1189   }
1190 
1191   /* Reset Tx transfer counter */
1192   hsc->TxXferCount = 0x00U;
1193 
1194   /* Restore hsc->gState to Ready */
1195   hsc->gState = HAL_SMARTCARD_STATE_READY;
1196 
1197   return HAL_OK;
1198 }
1199 
1200 /**
1201   * @brief  Abort ongoing Receive transfer (blocking mode).
1202   * @param  hsc SMARTCARD handle.
1203   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1204   *         This procedure performs following operations :
1205   *           - Disable PPP Interrupts
1206   *           - Disable the DMA transfer in the peripheral register (if enabled)
1207   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1208   *           - Set handle State to READY
1209   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1210   * @retval HAL status
1211 */
HAL_SMARTCARD_AbortReceive(SMARTCARD_HandleTypeDef * hsc)1212 HAL_StatusTypeDef HAL_SMARTCARD_AbortReceive(SMARTCARD_HandleTypeDef *hsc)
1213 {
1214   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1215   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE));
1216   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1217 
1218   /* Disable the SMARTCARD DMA Rx request if enabled */
1219   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1220   {
1221     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1222 
1223     /* Abort the SMARTCARD DMA Rx channel : use blocking DMA Abort API (no callback) */
1224     if(hsc->hdmarx != NULL)
1225     {
1226       /* Set the SMARTCARD DMA Abort callback to Null.
1227          No call back execution at end of DMA abort procedure */
1228       hsc->hdmarx->XferAbortCallback = NULL;
1229 
1230       HAL_DMA_Abort(hsc->hdmarx);
1231     }
1232   }
1233 
1234   /* Reset Rx transfer counter */
1235   hsc->RxXferCount = 0x00U;
1236 
1237   /* Restore hsc->RxState to Ready */
1238   hsc->RxState = HAL_SMARTCARD_STATE_READY;
1239 
1240   return HAL_OK;
1241 }
1242 
1243 /**
1244   * @brief  Abort ongoing transfers (Interrupt mode).
1245   * @param  hsc SMARTCARD handle.
1246   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1247   *         This procedure performs following operations :
1248   *           - Disable PPP Interrupts
1249   *           - Disable the DMA transfer in the peripheral register (if enabled)
1250   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1251   *           - Set handle State to READY
1252   *           - At abort completion, call user abort complete callback
1253   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1254   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1255   * @retval HAL status
1256 */
HAL_SMARTCARD_Abort_IT(SMARTCARD_HandleTypeDef * hsc)1257 HAL_StatusTypeDef HAL_SMARTCARD_Abort_IT(SMARTCARD_HandleTypeDef *hsc)
1258 {
1259   uint32_t AbortCplt = 0x01U;
1260 
1261   /* Disable TXEIE, TCIE, RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1262   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE | USART_CR1_TXEIE | USART_CR1_TCIE));
1263   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1264 
1265   /* If DMA Tx and/or DMA Rx Handles are associated to SMARTCARD Handle, DMA Abort complete callbacks should be initialised
1266      before any call to DMA Abort functions */
1267   /* DMA Tx Handle is valid */
1268   if(hsc->hdmatx != NULL)
1269   {
1270     /* Set DMA Abort Complete callback if SMARTCARD DMA Tx request if enabled.
1271        Otherwise, set it to NULL */
1272     if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT))
1273     {
1274       hsc->hdmatx->XferAbortCallback = SMARTCARD_DMATxAbortCallback;
1275     }
1276     else
1277     {
1278       hsc->hdmatx->XferAbortCallback = NULL;
1279     }
1280   }
1281   /* DMA Rx Handle is valid */
1282   if(hsc->hdmarx != NULL)
1283   {
1284     /* Set DMA Abort Complete callback if SMARTCARD DMA Rx request if enabled.
1285        Otherwise, set it to NULL */
1286     if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1287     {
1288       hsc->hdmarx->XferAbortCallback = SMARTCARD_DMARxAbortCallback;
1289     }
1290     else
1291     {
1292       hsc->hdmarx->XferAbortCallback = NULL;
1293     }
1294   }
1295 
1296   /* Disable the SMARTCARD DMA Tx request if enabled */
1297   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT))
1298   {
1299     /* Disable DMA Tx at SMARTCARD level */
1300     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1301 
1302     /* Abort the SMARTCARD DMA Tx channel : use non blocking DMA Abort API (callback) */
1303     if(hsc->hdmatx != NULL)
1304     {
1305       /* SMARTCARD Tx DMA Abort callback has already been initialised :
1306          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1307 
1308       /* Abort DMA TX */
1309       if(HAL_DMA_Abort_IT(hsc->hdmatx) != HAL_OK)
1310       {
1311         hsc->hdmatx->XferAbortCallback = NULL;
1312       }
1313       else
1314       {
1315         AbortCplt = 0x00U;
1316       }
1317     }
1318   }
1319 
1320   /* Disable the SMARTCARD DMA Rx request if enabled */
1321   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1322   {
1323     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1324 
1325     /* Abort the SMARTCARD DMA Rx channel : use non blocking DMA Abort API (callback) */
1326     if(hsc->hdmarx != NULL)
1327     {
1328       /* SMARTCARD Rx DMA Abort callback has already been initialised :
1329          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1330 
1331       /* Abort DMA RX */
1332       if(HAL_DMA_Abort_IT(hsc->hdmarx) != HAL_OK)
1333       {
1334         hsc->hdmarx->XferAbortCallback = NULL;
1335         AbortCplt = 0x01U;
1336       }
1337       else
1338       {
1339         AbortCplt = 0x00U;
1340       }
1341     }
1342   }
1343 
1344   /* if no DMA abort complete callback execution is required => call user Abort Complete callback */
1345   if(AbortCplt == 0x01U)
1346   {
1347     /* Reset Tx and Rx transfer counters */
1348     hsc->TxXferCount = 0x00U;
1349     hsc->RxXferCount = 0x00U;
1350 
1351     /* Reset ErrorCode */
1352     hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1353 
1354     /* Restore hsc->gState and hsc->RxState to Ready */
1355     hsc->gState  = HAL_SMARTCARD_STATE_READY;
1356     hsc->RxState = HAL_SMARTCARD_STATE_READY;
1357 
1358     /* As no DMA to be aborted, call directly user Abort complete callback */
1359 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1360     /* Call registered Abort complete callback */
1361     hsc->AbortCpltCallback(hsc);
1362 #else
1363     /* Call legacy weak Abort complete callback */
1364     HAL_SMARTCARD_AbortCpltCallback(hsc);
1365 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1366   }
1367   return HAL_OK;
1368 }
1369 
1370 /**
1371   * @brief  Abort ongoing Transmit transfer (Interrupt mode).
1372   * @param  hsc SMARTCARD handle.
1373   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1374   *         This procedure performs following operations :
1375   *           - Disable SMARTCARD Interrupts (Tx)
1376   *           - Disable the DMA transfer in the peripheral register (if enabled)
1377   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1378   *           - Set handle State to READY
1379   *           - At abort completion, call user abort complete callback
1380   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1381   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1382   * @retval HAL status
1383 */
HAL_SMARTCARD_AbortTransmit_IT(SMARTCARD_HandleTypeDef * hsc)1384 HAL_StatusTypeDef HAL_SMARTCARD_AbortTransmit_IT(SMARTCARD_HandleTypeDef *hsc)
1385 {
1386   /* Disable TXEIE and TCIE interrupts */
1387   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_TXEIE | USART_CR1_TCIE));
1388 
1389   /* Disable the SMARTCARD DMA Tx request if enabled */
1390   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT))
1391   {
1392     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1393 
1394     /* Abort the SMARTCARD DMA Tx channel : use blocking DMA Abort API (no callback) */
1395     if(hsc->hdmatx != NULL)
1396     {
1397       /* Set the SMARTCARD DMA Abort callback :
1398          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1399       hsc->hdmatx->XferAbortCallback = SMARTCARD_DMATxOnlyAbortCallback;
1400 
1401       /* Abort DMA TX */
1402       if(HAL_DMA_Abort_IT(hsc->hdmatx) != HAL_OK)
1403       {
1404         /* Call Directly hsc->hdmatx->XferAbortCallback function in case of error */
1405         hsc->hdmatx->XferAbortCallback(hsc->hdmatx);
1406       }
1407     }
1408     else
1409     {
1410       /* Reset Tx transfer counter */
1411       hsc->TxXferCount = 0x00U;
1412 
1413       /* Restore hsc->gState to Ready */
1414       hsc->gState = HAL_SMARTCARD_STATE_READY;
1415 
1416       /* As no DMA to be aborted, call directly user Abort complete callback */
1417 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1418       /* Call registered Abort Transmit Complete Callback */
1419       hsc->AbortTransmitCpltCallback(hsc);
1420 #else
1421       /* Call legacy weak Abort Transmit Complete Callback */
1422       HAL_SMARTCARD_AbortTransmitCpltCallback(hsc);
1423 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1424     }
1425   }
1426   else
1427   {
1428     /* Reset Tx transfer counter */
1429     hsc->TxXferCount = 0x00U;
1430 
1431     /* Restore hsc->gState to Ready */
1432     hsc->gState = HAL_SMARTCARD_STATE_READY;
1433 
1434     /* As no DMA to be aborted, call directly user Abort complete callback */
1435 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1436     /* Call registered Abort Transmit Complete Callback */
1437     hsc->AbortTransmitCpltCallback(hsc);
1438 #else
1439     /* Call legacy weak Abort Transmit Complete Callback */
1440     HAL_SMARTCARD_AbortTransmitCpltCallback(hsc);
1441 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1442   }
1443 
1444   return HAL_OK;
1445 }
1446 
1447 /**
1448   * @brief  Abort ongoing Receive transfer (Interrupt mode).
1449   * @param  hsc SMARTCARD handle.
1450   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1451   *         This procedure performs following operations :
1452   *           - Disable SMARTCARD Interrupts (Rx)
1453   *           - Disable the DMA transfer in the peripheral register (if enabled)
1454   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1455   *           - Set handle State to READY
1456   *           - At abort completion, call user abort complete callback
1457   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1458   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1459   * @retval HAL status
1460 */
HAL_SMARTCARD_AbortReceive_IT(SMARTCARD_HandleTypeDef * hsc)1461 HAL_StatusTypeDef HAL_SMARTCARD_AbortReceive_IT(SMARTCARD_HandleTypeDef *hsc)
1462 {
1463   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1464   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE));
1465   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1466 
1467   /* Disable the SMARTCARD DMA Rx request if enabled */
1468   if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1469   {
1470     CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1471 
1472     /* Abort the SMARTCARD DMA Rx channel : use blocking DMA Abort API (no callback) */
1473     if(hsc->hdmarx != NULL)
1474     {
1475       /* Set the SMARTCARD DMA Abort callback :
1476          will lead to call HAL_SMARTCARD_AbortCpltCallback() at end of DMA abort procedure */
1477       hsc->hdmarx->XferAbortCallback = SMARTCARD_DMARxOnlyAbortCallback;
1478 
1479       /* Abort DMA RX */
1480       if(HAL_DMA_Abort_IT(hsc->hdmarx) != HAL_OK)
1481       {
1482         /* Call Directly hsc->hdmarx->XferAbortCallback function in case of error */
1483         hsc->hdmarx->XferAbortCallback(hsc->hdmarx);
1484       }
1485     }
1486     else
1487     {
1488       /* Reset Rx transfer counter */
1489       hsc->RxXferCount = 0x00U;
1490 
1491       /* Restore hsc->RxState to Ready */
1492       hsc->RxState = HAL_SMARTCARD_STATE_READY;
1493 
1494       /* As no DMA to be aborted, call directly user Abort complete callback */
1495 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1496       /* Call registered Abort Receive Complete Callback */
1497       hsc->AbortReceiveCpltCallback(hsc);
1498 #else
1499       /* Call legacy weak Abort Receive Complete Callback */
1500       HAL_SMARTCARD_AbortReceiveCpltCallback(hsc);
1501 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1502     }
1503   }
1504   else
1505   {
1506     /* Reset Rx transfer counter */
1507     hsc->RxXferCount = 0x00U;
1508 
1509     /* Restore hsc->RxState to Ready */
1510     hsc->RxState = HAL_SMARTCARD_STATE_READY;
1511 
1512     /* As no DMA to be aborted, call directly user Abort complete callback */
1513 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1514     /* Call registered Abort Receive Complete Callback */
1515     hsc->AbortReceiveCpltCallback(hsc);
1516 #else
1517     /* Call legacy weak Abort Receive Complete Callback */
1518     HAL_SMARTCARD_AbortReceiveCpltCallback(hsc);
1519 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1520   }
1521 
1522   return HAL_OK;
1523 }
1524 
1525 /**
1526   * @brief This function handles SMARTCARD interrupt request.
1527   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1528   *                the configuration information for SMARTCARD module.
1529   * @retval None
1530   */
HAL_SMARTCARD_IRQHandler(SMARTCARD_HandleTypeDef * hsc)1531 void HAL_SMARTCARD_IRQHandler(SMARTCARD_HandleTypeDef *hsc)
1532 {
1533   uint32_t isrflags   = READ_REG(hsc->Instance->SR);
1534   uint32_t cr1its     = READ_REG(hsc->Instance->CR1);
1535   uint32_t cr3its     = READ_REG(hsc->Instance->CR3);
1536   uint32_t dmarequest = 0x00U;
1537   uint32_t errorflags = 0x00U;
1538 
1539   /* If no error occurs */
1540   errorflags = (isrflags & (uint32_t)(USART_SR_PE | USART_SR_FE | USART_SR_ORE | USART_SR_NE));
1541   if(errorflags == RESET)
1542   {
1543     /* SMARTCARD in mode Receiver -------------------------------------------------*/
1544     if(((isrflags & USART_SR_RXNE) != RESET) && ((cr1its & USART_CR1_RXNEIE) != RESET))
1545     {
1546       SMARTCARD_Receive_IT(hsc);
1547       return;
1548     }
1549   }
1550 
1551   /* If some errors occur */
1552   if((errorflags != RESET) && (((cr3its & USART_CR3_EIE) != RESET) || ((cr1its & (USART_CR1_RXNEIE | USART_CR1_PEIE)) != RESET)))
1553   {
1554     /* SMARTCARD parity error interrupt occurred ---------------------------*/
1555     if(((isrflags & SMARTCARD_FLAG_PE) != RESET) && ((cr1its & USART_CR1_PEIE) != RESET))
1556     {
1557       hsc->ErrorCode |= HAL_SMARTCARD_ERROR_PE;
1558     }
1559 
1560     /* SMARTCARD frame error interrupt occurred ----------------------------*/
1561     if(((isrflags & SMARTCARD_FLAG_FE) != RESET) && ((cr3its & USART_CR3_EIE) != RESET))
1562     {
1563       hsc->ErrorCode |= HAL_SMARTCARD_ERROR_FE;
1564     }
1565 
1566     /* SMARTCARD noise error interrupt occurred ----------------------------*/
1567     if(((isrflags & SMARTCARD_FLAG_NE) != RESET) && ((cr3its & USART_CR3_EIE) != RESET))
1568     {
1569       hsc->ErrorCode |= HAL_SMARTCARD_ERROR_NE;
1570     }
1571 
1572     /* SMARTCARD Over-Run interrupt occurred -------------------------------*/
1573     if(((isrflags & SMARTCARD_FLAG_ORE) != RESET) && (((cr1its & USART_CR1_RXNEIE) != RESET) || ((cr3its & USART_CR3_EIE) != RESET)))
1574     {
1575       hsc->ErrorCode |= HAL_SMARTCARD_ERROR_ORE;
1576     }
1577     /* Call the Error call Back in case of Errors --------------------------*/
1578     if(hsc->ErrorCode != HAL_SMARTCARD_ERROR_NONE)
1579     {
1580       /* SMARTCARD in mode Receiver ----------------------------------------*/
1581       if(((isrflags & USART_SR_RXNE) != RESET) && ((cr1its & USART_CR1_RXNEIE) != RESET))
1582       {
1583         SMARTCARD_Receive_IT(hsc);
1584       }
1585 
1586       /* If Overrun error occurs, or if any error occurs in DMA mode reception,
1587          consider error as blocking */
1588       dmarequest = HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR);
1589       if(((hsc->ErrorCode & HAL_SMARTCARD_ERROR_ORE) != RESET) || dmarequest)
1590       {
1591         /* Blocking error : transfer is aborted
1592           Set the SMARTCARD state ready to be able to start again the process,
1593           Disable Rx Interrupts, and disable Rx DMA request, if ongoing */
1594         SMARTCARD_EndRxTransfer(hsc);
1595         /* Disable the SMARTCARD DMA Rx request if enabled */
1596         if(HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR))
1597         {
1598           CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1599 
1600           /* Abort the SMARTCARD DMA Rx channel */
1601           if(hsc->hdmarx != NULL)
1602           {
1603             /* Set the SMARTCARD DMA Abort callback :
1604               will lead to call HAL_SMARTCARD_ErrorCallback() at end of DMA abort procedure */
1605             hsc->hdmarx->XferAbortCallback = SMARTCARD_DMAAbortOnError;
1606 
1607            if(HAL_DMA_Abort_IT(hsc->hdmarx) != HAL_OK)
1608             {
1609               /* Call Directly XferAbortCallback function in case of error */
1610               hsc->hdmarx->XferAbortCallback(hsc->hdmarx);
1611             }
1612           }
1613           else
1614           {
1615 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1616             /* Call registered user error callback */
1617             hsc->ErrorCallback(hsc);
1618 #else
1619             /* Call legacy weak user error callback */
1620             HAL_SMARTCARD_ErrorCallback(hsc);
1621 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1622           }
1623         }
1624         else
1625         {
1626 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1627           /* Call registered user error callback */
1628           hsc->ErrorCallback(hsc);
1629 #else
1630           /* Call legacy weak user error callback */
1631           HAL_SMARTCARD_ErrorCallback(hsc);
1632 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1633         }
1634       }
1635       else
1636       {
1637         /* Non Blocking error : transfer could go on.
1638            Error is notified to user through user error callback */
1639 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1640         /* Call registered user error callback */
1641         hsc->ErrorCallback(hsc);
1642 #else
1643         /* Call legacy weak user error callback */
1644         HAL_SMARTCARD_ErrorCallback(hsc);
1645 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1646         hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
1647       }
1648     }
1649     return;
1650   } /* End if some error occurs */
1651 
1652   /* SMARTCARD in mode Transmitter ------------------------------------------*/
1653   if(((isrflags & SMARTCARD_FLAG_TXE) != RESET) && ((cr1its & USART_CR1_TXEIE) != RESET))
1654   {
1655     SMARTCARD_Transmit_IT(hsc);
1656     return;
1657   }
1658 
1659   /* SMARTCARD in mode Transmitter (transmission end) -----------------------*/
1660   if(((isrflags & SMARTCARD_FLAG_TC) != RESET) && ((cr1its & USART_CR1_TCIE) != RESET))
1661   {
1662     SMARTCARD_EndTransmit_IT(hsc);
1663     return;
1664   }
1665 }
1666 
1667 /**
1668   * @brief Tx Transfer completed callbacks
1669   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1670   *                the configuration information for SMARTCARD module.
1671   * @retval None
1672   */
HAL_SMARTCARD_TxCpltCallback(SMARTCARD_HandleTypeDef * hsc)1673 __weak void HAL_SMARTCARD_TxCpltCallback(SMARTCARD_HandleTypeDef *hsc)
1674 {
1675   /* Prevent unused argument(s) compilation warning */
1676   UNUSED(hsc);
1677 
1678   /* NOTE : This function should not be modified, when the callback is needed,
1679             the HAL_SMARTCARD_TxCpltCallback can be implemented in the user file.
1680    */
1681 }
1682 
1683 /**
1684   * @brief Rx Transfer completed callback
1685   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1686   *                the configuration information for SMARTCARD module.
1687   * @retval None
1688   */
HAL_SMARTCARD_RxCpltCallback(SMARTCARD_HandleTypeDef * hsc)1689 __weak void HAL_SMARTCARD_RxCpltCallback(SMARTCARD_HandleTypeDef *hsc)
1690 {
1691   /* Prevent unused argument(s) compilation warning */
1692   UNUSED(hsc);
1693 
1694   /* NOTE : This function should not be modified, when the callback is needed,
1695             the HAL_SMARTCARD_RxCpltCallback can be implemented in the user file.
1696    */
1697 }
1698 
1699 /**
1700   * @brief SMARTCARD error callback
1701   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1702   *                the configuration information for SMARTCARD module.
1703   * @retval None
1704   */
HAL_SMARTCARD_ErrorCallback(SMARTCARD_HandleTypeDef * hsc)1705 __weak void HAL_SMARTCARD_ErrorCallback(SMARTCARD_HandleTypeDef *hsc)
1706 {
1707   /* Prevent unused argument(s) compilation warning */
1708   UNUSED(hsc);
1709 
1710   /* NOTE : This function should not be modified, when the callback is needed,
1711             the HAL_SMARTCARD_ErrorCallback can be implemented in the user file.
1712    */
1713 }
1714 
1715 /**
1716   * @brief  SMARTCARD Abort Complete callback.
1717   * @param  hsc SMARTCARD handle.
1718   * @retval None
1719   */
HAL_SMARTCARD_AbortCpltCallback(SMARTCARD_HandleTypeDef * hsc)1720 __weak void HAL_SMARTCARD_AbortCpltCallback (SMARTCARD_HandleTypeDef *hsc)
1721 {
1722   /* Prevent unused argument(s) compilation warning */
1723   UNUSED(hsc);
1724 
1725   /* NOTE : This function should not be modified, when the callback is needed,
1726             the HAL_SMARTCARD_AbortCpltCallback can be implemented in the user file.
1727    */
1728 }
1729 
1730 /**
1731   * @brief  SMARTCARD Abort Transmit Complete callback.
1732   * @param  hsc SMARTCARD handle.
1733   * @retval None
1734   */
HAL_SMARTCARD_AbortTransmitCpltCallback(SMARTCARD_HandleTypeDef * hsc)1735 __weak void HAL_SMARTCARD_AbortTransmitCpltCallback (SMARTCARD_HandleTypeDef *hsc)
1736 {
1737     /* Prevent unused argument(s) compilation warning */
1738     UNUSED(hsc);
1739 
1740   /* NOTE : This function should not be modified, when the callback is needed,
1741             the HAL_SMARTCARD_AbortTransmitCpltCallback can be implemented in the user file.
1742    */
1743 }
1744 
1745 /**
1746   * @brief  SMARTCARD Abort Receive Complete callback.
1747   * @param  hsc SMARTCARD handle.
1748   * @retval None
1749   */
HAL_SMARTCARD_AbortReceiveCpltCallback(SMARTCARD_HandleTypeDef * hsc)1750 __weak void HAL_SMARTCARD_AbortReceiveCpltCallback (SMARTCARD_HandleTypeDef *hsc)
1751 {
1752     /* Prevent unused argument(s) compilation warning */
1753     UNUSED(hsc);
1754 
1755   /* NOTE : This function should not be modified, when the callback is needed,
1756             the HAL_SMARTCARD_AbortReceiveCpltCallback can be implemented in the user file.
1757    */
1758 }
1759 
1760 /**
1761   * @}
1762   */
1763 
1764 /** @defgroup SMARTCARD_Exported_Functions_Group3 Peripheral State and Errors functions
1765   *  @brief   SMARTCARD State and Errors functions
1766   *
1767 @verbatim
1768  ===============================================================================
1769                 ##### Peripheral State and Errors functions #####
1770  ===============================================================================
1771     [..]
1772     This subsection provides a set of functions allowing to control the SmartCard.
1773      (+) HAL_SMARTCARD_GetState() API can be helpful to check in run-time the state of the SmartCard peripheral.
1774      (+) HAL_SMARTCARD_GetError() check in run-time errors that could be occurred during communication.
1775 @endverbatim
1776   * @{
1777   */
1778 
1779 /**
1780   * @brief Return the SMARTCARD handle state
1781   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1782   *                the configuration information for SMARTCARD module.
1783   * @retval HAL state
1784   */
HAL_SMARTCARD_GetState(SMARTCARD_HandleTypeDef * hsc)1785 HAL_SMARTCARD_StateTypeDef HAL_SMARTCARD_GetState(SMARTCARD_HandleTypeDef *hsc)
1786 {
1787   uint32_t temp1= 0x00U, temp2 = 0x00U;
1788   temp1 = hsc->gState;
1789   temp2 = hsc->RxState;
1790 
1791   return (HAL_SMARTCARD_StateTypeDef)(temp1 | temp2);
1792 }
1793 
1794 /**
1795   * @brief  Return the SMARTCARD error code
1796   * @param  hsc  Pointer to a SMARTCARD_HandleTypeDef structure that contains
1797   *              the configuration information for the specified SMARTCARD.
1798   * @retval SMARTCARD Error Code
1799   */
HAL_SMARTCARD_GetError(SMARTCARD_HandleTypeDef * hsc)1800 uint32_t HAL_SMARTCARD_GetError(SMARTCARD_HandleTypeDef *hsc)
1801 {
1802   return hsc->ErrorCode;
1803 }
1804 
1805 /**
1806   * @}
1807   */
1808 
1809 /**
1810   * @}
1811   */
1812 
1813 /** @defgroup SMARTCARD_Private_Functions SMARTCARD Private Functions
1814   * @{
1815   */
1816 
1817 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1818 /**
1819   * @brief  Initialize the callbacks to their default values.
1820   * @param  hsc SMARTCARD handle.
1821   * @retval none
1822   */
SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef * hsc)1823 void SMARTCARD_InitCallbacksToDefault(SMARTCARD_HandleTypeDef *hsc)
1824 {
1825   /* Init the SMARTCARD Callback settings */
1826   hsc->TxCpltCallback            = HAL_SMARTCARD_TxCpltCallback;            /* Legacy weak TxCpltCallback            */
1827   hsc->RxCpltCallback            = HAL_SMARTCARD_RxCpltCallback;            /* Legacy weak RxCpltCallback            */
1828   hsc->ErrorCallback             = HAL_SMARTCARD_ErrorCallback;             /* Legacy weak ErrorCallback             */
1829   hsc->AbortCpltCallback         = HAL_SMARTCARD_AbortCpltCallback;         /* Legacy weak AbortCpltCallback         */
1830   hsc->AbortTransmitCpltCallback = HAL_SMARTCARD_AbortTransmitCpltCallback; /* Legacy weak AbortTransmitCpltCallback */
1831   hsc->AbortReceiveCpltCallback  = HAL_SMARTCARD_AbortReceiveCpltCallback;  /* Legacy weak AbortReceiveCpltCallback  */
1832 
1833 }
1834 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACKS */
1835 
1836 /**
1837   * @brief DMA SMARTCARD transmit process complete callback
1838   * @param  hdma   Pointer to a DMA_HandleTypeDef structure that contains
1839   *                the configuration information for the specified DMA module.
1840   * @retval None
1841   */
SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef * hdma)1842 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma)
1843 {
1844   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
1845 
1846   hsc->TxXferCount = 0U;
1847 
1848   /* Disable the DMA transfer for transmit request by setting the DMAT bit
1849      in the USART CR3 register */
1850   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAT);
1851 
1852   /* Enable the SMARTCARD Transmit Complete Interrupt */
1853   SET_BIT(hsc->Instance->CR1, USART_CR1_TCIE);
1854 }
1855 
1856 /**
1857   * @brief DMA SMARTCARD receive process complete callback
1858   * @param  hdma   Pointer to a DMA_HandleTypeDef structure that contains
1859   *                the configuration information for the specified DMA module.
1860   * @retval None
1861   */
SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef * hdma)1862 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma)
1863 {
1864   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
1865 
1866   hsc->RxXferCount = 0U;
1867 
1868   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1869   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE));
1870   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1871 
1872   /* Disable the DMA transfer for the receiver request by setting the DMAR bit
1873      in the USART CR3 register */
1874   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_DMAR);
1875 
1876   /* At end of Rx process, restore hsc->RxState to Ready */
1877   hsc->RxState = HAL_SMARTCARD_STATE_READY;
1878 
1879 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1880   /* Call registered Rx complete callback */
1881   hsc->RxCpltCallback(hsc);
1882 #else
1883   /* Call legacy weak Rx complete callback */
1884   HAL_SMARTCARD_RxCpltCallback(hsc);
1885 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1886 }
1887 
1888 /**
1889   * @brief DMA SMARTCARD communication error callback
1890   * @param  hdma   Pointer to a DMA_HandleTypeDef structure that contains
1891   *                the configuration information for the specified DMA module.
1892   * @retval None
1893   */
SMARTCARD_DMAError(DMA_HandleTypeDef * hdma)1894 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma)
1895 {
1896   uint32_t dmarequest = 0x00U;
1897   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
1898   hsc->RxXferCount = 0U;
1899   hsc->TxXferCount = 0U;
1900   hsc->ErrorCode = HAL_SMARTCARD_ERROR_DMA;
1901 
1902   /* Stop SMARTCARD DMA Tx request if ongoing */
1903   dmarequest = HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAT);
1904   if((hsc->gState == HAL_SMARTCARD_STATE_BUSY_TX) && dmarequest)
1905   {
1906     SMARTCARD_EndTxTransfer(hsc);
1907   }
1908 
1909   /* Stop SMARTCARD DMA Rx request if ongoing */
1910   dmarequest = HAL_IS_BIT_SET(hsc->Instance->CR3, USART_CR3_DMAR);
1911   if((hsc->RxState == HAL_SMARTCARD_STATE_BUSY_RX) && dmarequest)
1912   {
1913     SMARTCARD_EndRxTransfer(hsc);
1914   }
1915 
1916 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
1917   /* Call registered user error callback */
1918   hsc->ErrorCallback(hsc);
1919 #else
1920   /* Call legacy weak user error callback */
1921   HAL_SMARTCARD_ErrorCallback(hsc);
1922 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
1923 }
1924 
1925 /**
1926   * @brief  This function handles SMARTCARD Communication Timeout.
1927   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1928   *                the configuration information for SMARTCARD module.
1929   * @param  Flag   Specifies the SMARTCARD flag to check.
1930   * @param  Status The new Flag status (SET or RESET).
1931   * @param  Timeout Timeout duration
1932   * @param  Tickstart Tick start value
1933   * @retval HAL status
1934   */
SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef * hsc,uint32_t Flag,FlagStatus Status,uint32_t Tickstart,uint32_t Timeout)1935 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsc, uint32_t Flag, FlagStatus Status, uint32_t Tickstart, uint32_t Timeout)
1936 {
1937   /* Wait until flag is set */
1938   while((__HAL_SMARTCARD_GET_FLAG(hsc, Flag) ? SET : RESET) == Status)
1939   {
1940     /* Check for the Timeout */
1941     if(Timeout != HAL_MAX_DELAY)
1942     {
1943       if((Timeout == 0U)||((HAL_GetTick() - Tickstart ) > Timeout))
1944       {
1945         /* Disable TXE and RXNE interrupts for the interrupt process */
1946         CLEAR_BIT(hsc->Instance->CR1, USART_CR1_TXEIE);
1947         CLEAR_BIT(hsc->Instance->CR1, USART_CR1_RXNEIE);
1948 
1949         hsc->gState= HAL_SMARTCARD_STATE_READY;
1950         hsc->RxState= HAL_SMARTCARD_STATE_READY;
1951 
1952         /* Process Unlocked */
1953         __HAL_UNLOCK(hsc);
1954 
1955         return HAL_TIMEOUT;
1956       }
1957     }
1958   }
1959   return HAL_OK;
1960 }
1961 
1962 /**
1963   * @brief  End ongoing Tx transfer on SMARTCARD peripheral (following error detection or Transmit completion).
1964   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1965   *                the configuration information for SMARTCARD module.
1966   * @retval None
1967   */
SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef * hsc)1968 static void SMARTCARD_EndTxTransfer(SMARTCARD_HandleTypeDef *hsc)
1969 {
1970   /* At end of Tx process, restore hsc->gState to Ready */
1971   hsc->gState = HAL_SMARTCARD_STATE_READY;
1972 
1973   /* Disable TXEIE and TCIE interrupts */
1974   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_TXEIE | USART_CR1_TCIE));
1975 }
1976 
1977 
1978 /**
1979   * @brief  End ongoing Rx transfer on SMARTCARD peripheral (following error detection or Reception completion).
1980   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1981   *                the configuration information for SMARTCARD module.
1982   * @retval None
1983   */
SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef * hsc)1984 static void SMARTCARD_EndRxTransfer(SMARTCARD_HandleTypeDef *hsc)
1985 {
1986   /* At end of Rx process, restore hsc->RxState to Ready */
1987   hsc->RxState = HAL_SMARTCARD_STATE_READY;
1988 
1989   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
1990   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE));
1991   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
1992 }
1993 
1994 /**
1995   * @brief Send an amount of data in non blocking mode
1996   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
1997   *                the configuration information for SMARTCARD module.
1998   * @retval HAL status
1999   */
SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef * hsc)2000 static HAL_StatusTypeDef SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsc)
2001 {
2002   uint16_t* tmp;
2003 
2004   /* Check that a Tx process is ongoing */
2005   if(hsc->gState == HAL_SMARTCARD_STATE_BUSY_TX)
2006   {
2007     tmp = (uint16_t*) hsc->pTxBuffPtr;
2008     hsc->Instance->DR = (uint16_t)(*tmp & (uint16_t)0x01FF);
2009     hsc->pTxBuffPtr += 1U;
2010 
2011     if(--hsc->TxXferCount == 0U)
2012     {
2013       /* Disable the SMARTCARD Transmit data register empty Interrupt */
2014       CLEAR_BIT(hsc->Instance->CR1, USART_CR1_TXEIE);
2015 
2016       /* Enable the SMARTCARD Transmit Complete Interrupt */
2017       SET_BIT(hsc->Instance->CR1, USART_CR1_TCIE);
2018     }
2019 
2020     return HAL_OK;
2021   }
2022   else
2023   {
2024     return HAL_BUSY;
2025   }
2026 }
2027 
2028 /**
2029   * @brief  Wraps up transmission in non blocking mode.
2030   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
2031   *                the configuration information for the specified SMARTCARD module.
2032   * @retval HAL status
2033   */
SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef * hsc)2034 static HAL_StatusTypeDef SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsc)
2035 {
2036   /* Disable the SMARTCARD Transmit Complete Interrupt */
2037   CLEAR_BIT(hsc->Instance->CR1, USART_CR1_TCIE);
2038 
2039   /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
2040   CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
2041 
2042   /* Tx process is ended, restore hsc->gState to Ready */
2043   hsc->gState = HAL_SMARTCARD_STATE_READY;
2044 
2045 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2046   /* Call registered Tx complete callback */
2047   hsc->TxCpltCallback(hsc);
2048 #else
2049   /* Call legacy weak Tx complete callback */
2050   HAL_SMARTCARD_TxCpltCallback(hsc);
2051 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2052 
2053   return HAL_OK;
2054 }
2055 
2056 /**
2057   * @brief Receive an amount of data in non blocking mode
2058   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
2059   *                the configuration information for SMARTCARD module.
2060   * @retval HAL status
2061   */
SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef * hsc)2062 static HAL_StatusTypeDef SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsc)
2063 {
2064   uint16_t* tmp;
2065 
2066   /* Check that a Rx process is ongoing */
2067   if(hsc->RxState == HAL_SMARTCARD_STATE_BUSY_RX)
2068   {
2069     tmp = (uint16_t*) hsc->pRxBuffPtr;
2070     *tmp = (uint8_t)(hsc->Instance->DR & (uint8_t)0x00FF);
2071     hsc->pRxBuffPtr += 1U;
2072 
2073     if(--hsc->RxXferCount == 0U)
2074     {
2075       CLEAR_BIT(hsc->Instance->CR1, USART_CR1_RXNEIE);
2076 
2077       /* Disable the SMARTCARD Parity Error Interrupt */
2078       CLEAR_BIT(hsc->Instance->CR1, USART_CR1_PEIE);
2079 
2080       /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
2081       CLEAR_BIT(hsc->Instance->CR3, USART_CR3_EIE);
2082 
2083       /* Rx process is completed, restore hsc->RxState to Ready */
2084       hsc->RxState = HAL_SMARTCARD_STATE_READY;
2085 
2086 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2087       /* Call registered Rx complete callback */
2088       hsc->RxCpltCallback(hsc);
2089 #else
2090       /* Call legacy weak Rx complete callback */
2091       HAL_SMARTCARD_RxCpltCallback(hsc);
2092 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2093 
2094       return HAL_OK;
2095     }
2096     return HAL_OK;
2097   }
2098   else
2099   {
2100     return HAL_BUSY;
2101   }
2102 }
2103 
2104 /**
2105   * @brief  DMA SMARTCARD communication abort callback, when initiated by HAL services on Error
2106   *         (To be called at end of DMA Abort procedure following error occurrence).
2107   * @param  hdma DMA handle.
2108   * @retval None
2109   */
SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef * hdma)2110 static void SMARTCARD_DMAAbortOnError(DMA_HandleTypeDef *hdma)
2111 {
2112   SMARTCARD_HandleTypeDef* hsc = (SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
2113   hsc->RxXferCount = 0x00U;
2114   hsc->TxXferCount = 0x00U;
2115 
2116 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2117   /* Call registered user error callback */
2118   hsc->ErrorCallback(hsc);
2119 #else
2120   /* Call legacy weak user error callback */
2121   HAL_SMARTCARD_ErrorCallback(hsc);
2122 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2123 }
2124 
2125 /**
2126   * @brief  DMA SMARTCARD Tx communication abort callback, when initiated by user
2127   *         (To be called at end of DMA Tx Abort procedure following user abort request).
2128   * @note   When this callback is executed, User Abort complete call back is called only if no
2129   *         Abort still ongoing for Rx DMA Handle.
2130   * @param  hdma DMA handle.
2131   * @retval None
2132   */
SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef * hdma)2133 static void SMARTCARD_DMATxAbortCallback(DMA_HandleTypeDef *hdma)
2134 {
2135   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
2136 
2137   hsc->hdmatx->XferAbortCallback = NULL;
2138 
2139   /* Check if an Abort process is still ongoing */
2140   if(hsc->hdmarx != NULL)
2141   {
2142     if(hsc->hdmarx->XferAbortCallback != NULL)
2143     {
2144       return;
2145     }
2146   }
2147 
2148   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
2149   hsc->TxXferCount = 0x00U;
2150   hsc->RxXferCount = 0x00U;
2151 
2152   /* Reset ErrorCode */
2153   hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2154 
2155   /* Restore hsc->gState and hsc->RxState to Ready */
2156   hsc->gState  = HAL_SMARTCARD_STATE_READY;
2157   hsc->RxState = HAL_SMARTCARD_STATE_READY;
2158 
2159 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2160   /* Call registered Abort complete callback */
2161   hsc->AbortCpltCallback(hsc);
2162 #else
2163   /* Call legacy weak Abort complete callback */
2164   HAL_SMARTCARD_AbortCpltCallback(hsc);
2165 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2166 }
2167 
2168 /**
2169   * @brief  DMA SMARTCARD Rx communication abort callback, when initiated by user
2170   *         (To be called at end of DMA Rx Abort procedure following user abort request).
2171   * @note   When this callback is executed, User Abort complete call back is called only if no
2172   *         Abort still ongoing for Tx DMA Handle.
2173   * @param  hdma DMA handle.
2174   * @retval None
2175   */
SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef * hdma)2176 static void SMARTCARD_DMARxAbortCallback(DMA_HandleTypeDef *hdma)
2177 {
2178   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
2179 
2180   hsc->hdmarx->XferAbortCallback = NULL;
2181 
2182   /* Check if an Abort process is still ongoing */
2183   if(hsc->hdmatx != NULL)
2184   {
2185     if(hsc->hdmatx->XferAbortCallback != NULL)
2186     {
2187       return;
2188     }
2189   }
2190 
2191   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
2192   hsc->TxXferCount = 0x00U;
2193   hsc->RxXferCount = 0x00U;
2194 
2195   /* Reset ErrorCode */
2196   hsc->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
2197 
2198   /* Restore hsc->gState and hsc->RxState to Ready */
2199   hsc->gState  = HAL_SMARTCARD_STATE_READY;
2200   hsc->RxState = HAL_SMARTCARD_STATE_READY;
2201 
2202 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2203   /* Call registered Abort complete callback */
2204   hsc->AbortCpltCallback(hsc);
2205 #else
2206   /* Call legacy weak Abort complete callback */
2207   HAL_SMARTCARD_AbortCpltCallback(hsc);
2208 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2209 }
2210 
2211 /**
2212   * @brief  DMA SMARTCARD Tx communication abort callback, when initiated by user by a call to
2213   *         HAL_SMARTCARD_AbortTransmit_IT API (Abort only Tx transfer)
2214   *         (This callback is executed at end of DMA Tx Abort procedure following user abort request,
2215   *         and leads to user Tx Abort Complete callback execution).
2216   * @param  hdma DMA handle.
2217   * @retval None
2218   */
SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef * hdma)2219 static void SMARTCARD_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
2220 {
2221   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
2222 
2223   hsc->TxXferCount = 0x00U;
2224 
2225   /* Restore hsc->gState to Ready */
2226   hsc->gState = HAL_SMARTCARD_STATE_READY;
2227 
2228 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2229   /* Call registered Abort Transmit Complete Callback */
2230   hsc->AbortTransmitCpltCallback(hsc);
2231 #else
2232   /* Call legacy weak Abort Transmit Complete Callback */
2233   HAL_SMARTCARD_AbortTransmitCpltCallback(hsc);
2234 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2235 }
2236 
2237 /**
2238   * @brief  DMA SMARTCARD Rx communication abort callback, when initiated by user by a call to
2239   *         HAL_SMARTCARD_AbortReceive_IT API (Abort only Rx transfer)
2240   *         (This callback is executed at end of DMA Rx Abort procedure following user abort request,
2241   *         and leads to user Rx Abort Complete callback execution).
2242   * @param  hdma DMA handle.
2243   * @retval None
2244   */
SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef * hdma)2245 static void SMARTCARD_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
2246 {
2247   SMARTCARD_HandleTypeDef* hsc = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
2248 
2249   hsc->RxXferCount = 0x00U;
2250 
2251   /* Restore hsc->RxState to Ready */
2252   hsc->RxState = HAL_SMARTCARD_STATE_READY;
2253 
2254 #if (USE_HAL_SMARTCARD_REGISTER_CALLBACKS == 1)
2255   /* Call registered Abort Receive Complete Callback */
2256   hsc->AbortReceiveCpltCallback(hsc);
2257 #else
2258   /* Call legacy weak Abort Receive Complete Callback */
2259   HAL_SMARTCARD_AbortReceiveCpltCallback(hsc);
2260 #endif /* USE_HAL_SMARTCARD_REGISTER_CALLBACK */
2261 }
2262 
2263 /**
2264   * @brief Configure the SMARTCARD peripheral
2265   * @param  hsc    Pointer to a SMARTCARD_HandleTypeDef structure that contains
2266   *                the configuration information for SMARTCARD module.
2267   * @retval None
2268   */
SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef * hsc)2269 static void SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef *hsc)
2270 {
2271   uint32_t tmpreg = 0x00U;
2272   uint32_t pclk;
2273 
2274   /* Check the parameters */
2275   assert_param(IS_SMARTCARD_INSTANCE(hsc->Instance));
2276   assert_param(IS_SMARTCARD_POLARITY(hsc->Init.CLKPolarity));
2277   assert_param(IS_SMARTCARD_PHASE(hsc->Init.CLKPhase));
2278   assert_param(IS_SMARTCARD_LASTBIT(hsc->Init.CLKLastBit));
2279   assert_param(IS_SMARTCARD_BAUDRATE(hsc->Init.BaudRate));
2280   assert_param(IS_SMARTCARD_WORD_LENGTH(hsc->Init.WordLength));
2281   assert_param(IS_SMARTCARD_STOPBITS(hsc->Init.StopBits));
2282   assert_param(IS_SMARTCARD_PARITY(hsc->Init.Parity));
2283   assert_param(IS_SMARTCARD_MODE(hsc->Init.Mode));
2284   assert_param(IS_SMARTCARD_NACK_STATE(hsc->Init.NACKState));
2285 
2286   /* The LBCL, CPOL and CPHA bits have to be selected when both the transmitter and the
2287      receiver are disabled (TE=RE=0) to ensure that the clock pulses function correctly. */
2288   CLEAR_BIT(hsc->Instance->CR1, (USART_CR1_TE | USART_CR1_RE));
2289 
2290   /*---------------------------- USART CR2 Configuration ---------------------*/
2291   tmpreg = hsc->Instance->CR2;
2292   /* Clear CLKEN, CPOL, CPHA and LBCL bits */
2293   tmpreg &= (uint32_t)~((uint32_t)(USART_CR2_CPHA | USART_CR2_CPOL | USART_CR2_CLKEN | USART_CR2_LBCL));
2294   /* Configure the SMARTCARD Clock, CPOL, CPHA and LastBit -----------------------*/
2295   /* Set CPOL bit according to hsc->Init.CLKPolarity value */
2296   /* Set CPHA bit according to hsc->Init.CLKPhase value */
2297   /* Set LBCL bit according to hsc->Init.CLKLastBit value */
2298   /* Set Stop Bits: Set STOP[13:12] bits according to hsc->Init.StopBits value */
2299   tmpreg |= (uint32_t)(USART_CR2_CLKEN | hsc->Init.CLKPolarity |
2300                       hsc->Init.CLKPhase| hsc->Init.CLKLastBit | hsc->Init.StopBits);
2301   /* Write to USART CR2 */
2302   WRITE_REG(hsc->Instance->CR2, (uint32_t)tmpreg);
2303 
2304   tmpreg = hsc->Instance->CR2;
2305 
2306   /* Clear STOP[13:12] bits */
2307   tmpreg &= (uint32_t)~((uint32_t)USART_CR2_STOP);
2308 
2309   /* Set Stop Bits: Set STOP[13:12] bits according to hsc->Init.StopBits value */
2310   tmpreg |= (uint32_t)(hsc->Init.StopBits);
2311 
2312   /* Write to USART CR2 */
2313   WRITE_REG(hsc->Instance->CR2, (uint32_t)tmpreg);
2314 
2315   /*-------------------------- USART CR1 Configuration -----------------------*/
2316   tmpreg = hsc->Instance->CR1;
2317 
2318   /* Clear M, PCE, PS, TE and RE bits */
2319   tmpreg &= (uint32_t)~((uint32_t)(USART_CR1_M | USART_CR1_PCE | USART_CR1_PS | USART_CR1_TE | \
2320                                    USART_CR1_RE));
2321 
2322   /* Configure the SMARTCARD Word Length, Parity and mode:
2323      Set the M bits according to hsc->Init.WordLength value
2324      Set PCE and PS bits according to hsc->Init.Parity value
2325      Set TE and RE bits according to hsc->Init.Mode value */
2326   tmpreg |= (uint32_t)hsc->Init.WordLength | hsc->Init.Parity | hsc->Init.Mode;
2327 
2328   /* Write to USART CR1 */
2329   WRITE_REG(hsc->Instance->CR1, (uint32_t)tmpreg);
2330 
2331   /*-------------------------- USART CR3 Configuration -----------------------*/
2332   /* Clear CTSE and RTSE bits */
2333   CLEAR_BIT(hsc->Instance->CR3, (USART_CR3_RTSE | USART_CR3_CTSE));
2334 
2335   /*-------------------------- USART BRR Configuration -----------------------*/
2336 #if defined(USART6)
2337   if((hsc->Instance == USART1) || (hsc->Instance == USART6))
2338   {
2339     pclk = HAL_RCC_GetPCLK2Freq();
2340     hsc->Instance->BRR = SMARTCARD_BRR(pclk, hsc->Init.BaudRate);
2341   }
2342 #else
2343   if(hsc->Instance == USART1)
2344   {
2345     pclk = HAL_RCC_GetPCLK2Freq();
2346     hsc->Instance->BRR = SMARTCARD_BRR(pclk, hsc->Init.BaudRate);
2347   }
2348 #endif /* USART6 */
2349   else
2350   {
2351     pclk = HAL_RCC_GetPCLK1Freq();
2352     hsc->Instance->BRR = SMARTCARD_BRR(pclk, hsc->Init.BaudRate);
2353   }
2354 }
2355 
2356 /**
2357   * @}
2358   */
2359 
2360 #endif /* HAL_SMARTCARD_MODULE_ENABLED */
2361 /**
2362   * @}
2363   */
2364 
2365 /**
2366   * @}
2367   */
2368 
2369 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
2370