TUKS MCU Introductory course / TUKS-COURSE-2-LED
Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers stm32l4xx_hal_smartcard.c Source File

stm32l4xx_hal_smartcard.c

Go to the documentation of this file.
00001 /**
00002   ******************************************************************************
00003   * @file    stm32l4xx_hal_smartcard.c
00004   * @author  MCD Application Team
00005   * @version V1.5.1
00006   * @date    31-May-2016
00007   * @brief   SMARTCARD HAL module driver.
00008   *          This file provides firmware functions to manage the following
00009   *          functionalities of the SMARTCARD peripheral:
00010   *           + Initialization and de-initialization functions
00011   *           + IO operation functions
00012   *           + Peripheral Control functions
00013   *           + Peripheral State and Error functions
00014   *
00015   @verbatim
00016   ==============================================================================
00017                         ##### How to use this driver #####
00018   ==============================================================================
00019   [..]
00020     The SMARTCARD HAL driver can be used as follows:
00021 
00022     (#) Declare a SMARTCARD_HandleTypeDef handle structure (eg. SMARTCARD_HandleTypeDef hsmartcard).
00023     (#) Associate a USART to the SMARTCARD handle hsmartcard.
00024     (#) Initialize the SMARTCARD low level resources by implementing the HAL_SMARTCARD_MspInit() API:
00025         (++) Enable the USARTx interface clock.
00026         (++) USART pins configuration:
00027              (+++) Enable the clock for the USART GPIOs.
00028              (+++) Configure the USART pins (TX as alternate function pull-up, RX as alternate function Input).
00029         (++) NVIC configuration if you need to use interrupt process (HAL_SMARTCARD_Transmit_IT()
00030              and HAL_SMARTCARD_Receive_IT() APIs):
00031              (++) Configure the USARTx interrupt priority.
00032              (++) Enable the NVIC USART IRQ handle.
00033         (++) DMA Configuration if you need to use DMA process (HAL_SMARTCARD_Transmit_DMA()
00034              and HAL_SMARTCARD_Receive_DMA() APIs):
00035              (+++) Declare a DMA handle structure for the Tx/Rx channel.
00036              (+++) Enable the DMAx interface clock.
00037              (+++) Configure the declared DMA handle structure with the required Tx/Rx parameters.
00038              (+++) Configure the DMA Tx/Rx channel.
00039              (+++) Associate the initialized DMA handle to the SMARTCARD DMA Tx/Rx handle.
00040              (+++) Configure the priority and enable the NVIC for the transfer complete interrupt on the DMA Tx/Rx channel.
00041 
00042     (#) Program the Baud Rate, Parity, Mode(Receiver/Transmitter), clock enabling/disabling and accordingly,
00043         the clock parameters (parity, phase, last bit), prescaler value, guard time and NACK on transmission
00044         error enabling or disabling in the hsmartcard handle Init structure.
00045 
00046     (#) If required, program SMARTCARD advanced features (TX/RX pins swap, TimeOut, auto-retry counter,...)
00047         in the hsmartcard handle AdvancedInit structure.
00048 
00049     (#) Initialize the SMARTCARD registers by calling the HAL_SMARTCARD_Init() API:
00050         (++) This API configures also the low level Hardware GPIO, CLOCK, CORTEX...etc)
00051              by calling the customized HAL_SMARTCARD_MspInit() API.
00052         [..]
00053         (@) The specific SMARTCARD interrupts (Transmission complete interrupt,
00054              RXNE interrupt and Error Interrupts) will be managed using the macros
00055              __HAL_SMARTCARD_ENABLE_IT() and __HAL_SMARTCARD_DISABLE_IT() inside the transmit and receive process.
00056 
00057     [..]
00058     [..] Three operation modes are available within this driver :
00059 
00060      *** Polling mode IO operation ***
00061      =================================
00062      [..]
00063        (+) Send an amount of data in blocking mode using HAL_SMARTCARD_Transmit()
00064        (+) Receive an amount of data in blocking mode using HAL_SMARTCARD_Receive()
00065 
00066      *** Interrupt mode IO operation ***
00067      ===================================
00068      [..]
00069        (+) Send an amount of data in non-blocking mode using HAL_SMARTCARD_Transmit_IT()
00070        (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback() is executed and user can
00071             add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback()
00072        (+) Receive an amount of data in non-blocking mode using HAL_SMARTCARD_Receive_IT()
00073        (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback() is executed and user can
00074             add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback()
00075        (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
00076             add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback()
00077 
00078      *** DMA mode IO operation ***
00079      ==============================
00080      [..]
00081        (+) Send an amount of data in non-blocking mode (DMA) using HAL_SMARTCARD_Transmit_DMA()
00082        (+) At transmission end of transfer HAL_SMARTCARD_TxCpltCallback() is executed and user can
00083             add his own code by customization of function pointer HAL_SMARTCARD_TxCpltCallback()
00084        (+) Receive an amount of data in non-blocking mode (DMA) using HAL_SMARTCARD_Receive_DMA()
00085        (+) At reception end of transfer HAL_SMARTCARD_RxCpltCallback() is executed and user can
00086             add his own code by customization of function pointer HAL_SMARTCARD_RxCpltCallback()
00087        (+) In case of transfer Error, HAL_SMARTCARD_ErrorCallback() function is executed and user can
00088             add his own code by customization of function pointer HAL_SMARTCARD_ErrorCallback()
00089 
00090      *** SMARTCARD HAL driver macros list ***
00091      ========================================
00092      [..]
00093        Below the list of most used macros in SMARTCARD HAL driver.
00094 
00095        (+) __HAL_SMARTCARD_GET_FLAG : Check whether or not the specified SMARTCARD flag is set
00096        (+) __HAL_SMARTCARD_CLEAR_FLAG : Clear the specified SMARTCARD pending flag
00097        (+) __HAL_SMARTCARD_ENABLE_IT: Enable the specified SMARTCARD interrupt
00098        (+) __HAL_SMARTCARD_DISABLE_IT: Disable the specified SMARTCARD interrupt
00099        (+) __HAL_SMARTCARD_GET_IT_SOURCE: Check whether or not the specified SMARTCARD interrupt is enabled
00100 
00101      [..]
00102        (@) You can refer to the SMARTCARD HAL driver header file for more useful macros
00103 
00104   @endverbatim
00105   ******************************************************************************
00106   * @attention
00107   *
00108   * <h2><center>&copy; COPYRIGHT(c) 2016 STMicroelectronics</center></h2>
00109   *
00110   * Redistribution and use in source and binary forms, with or without modification,
00111   * are permitted provided that the following conditions are met:
00112   *   1. Redistributions of source code must retain the above copyright notice,
00113   *      this list of conditions and the following disclaimer.
00114   *   2. Redistributions in binary form must reproduce the above copyright notice,
00115   *      this list of conditions and the following disclaimer in the documentation
00116   *      and/or other materials provided with the distribution.
00117   *   3. Neither the name of STMicroelectronics nor the names of its contributors
00118   *      may be used to endorse or promote products derived from this software
00119   *      without specific prior written permission.
00120   *
00121   * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00122   * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00123   * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
00124   * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
00125   * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00126   * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
00127   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00128   * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
00129   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
00130   * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00131   *
00132   ******************************************************************************
00133   */
00134 
00135 /* Includes ------------------------------------------------------------------*/
00136 #include "stm32l4xx_hal.h"
00137 
00138 /** @addtogroup STM32L4xx_HAL_Driver
00139   * @{
00140   */
00141 
00142 /** @defgroup SMARTCARD SMARTCARD
00143   * @brief HAL SMARTCARD module driver
00144   * @{
00145   */
00146 
00147 #ifdef HAL_SMARTCARD_MODULE_ENABLED
00148 
00149 /* Private typedef -----------------------------------------------------------*/
00150 /* Private define ------------------------------------------------------------*/
00151 /** @defgroup SMARTCARD_Private_Constants SMARTCARD Private Constants
00152  * @{
00153  */
00154 #define SMARTCARD_TEACK_REACK_TIMEOUT               1000      /*!< SMARTCARD TX or RX enable acknowledge time-out value  */
00155 
00156 #define USART_CR1_FIELDS      ((uint32_t)(USART_CR1_M | USART_CR1_PCE | USART_CR1_PS | \
00157                                      USART_CR1_TE | USART_CR1_RE | USART_CR1_OVER8))       /*!< USART CR1 fields of parameters set by SMARTCARD_SetConfig API */
00158 #define USART_CR2_CLK_FIELDS  ((uint32_t)(USART_CR2_CLKEN|USART_CR2_CPOL|USART_CR2_CPHA|USART_CR2_LBCL)) /*!< SMARTCARD clock-related USART CR2 fields of parameters */
00159 #define USART_CR2_FIELDS      ((uint32_t)(USART_CR2_RTOEN|USART_CR2_CLK_FIELDS|USART_CR2_STOP)) /*!< USART CR2 fields of parameters set by SMARTCARD_SetConfig API */
00160 #define USART_CR3_FIELDS      ((uint32_t)(USART_CR3_ONEBIT|USART_CR3_NACK|USART_CR3_SCARCNT))   /*!< USART CR3 fields of parameters set by SMARTCARD_SetConfig API */
00161 /**
00162   * @}
00163   */
00164 
00165 /* Private macros ------------------------------------------------------------*/
00166 /* Private variables ---------------------------------------------------------*/
00167 /* Private function prototypes -----------------------------------------------*/
00168 /** @addtogroup SMARTCARD_Private_Functions
00169   * @{
00170   */
00171 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma);
00172 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma);
00173 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma);
00174 static HAL_StatusTypeDef SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef *hsmartcard);
00175 static void SMARTCARD_AdvFeatureConfig(SMARTCARD_HandleTypeDef *hsmartcard);
00176 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsmartcard, uint32_t Flag, FlagStatus Status, uint32_t Tickstart, uint32_t Timeout);
00177 static HAL_StatusTypeDef SMARTCARD_CheckIdleState(SMARTCARD_HandleTypeDef *hsmartcard);
00178 static HAL_StatusTypeDef SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsmartcard);
00179 static HAL_StatusTypeDef SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsmartcard);
00180 static HAL_StatusTypeDef SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsmartcard);
00181 /**
00182   * @}
00183   */
00184 
00185 /* Exported functions --------------------------------------------------------*/
00186 
00187 /** @defgroup SMARTCARD_Exported_Functions SMARTCARD Exported Functions
00188   * @{
00189   */
00190 
00191 /** @defgroup SMARTCARD_Exported_Functions_Group1 Initialization and de-initialization functions
00192   *  @brief    Initialization and Configuration functions
00193   *
00194 @verbatim
00195   ===============================================================================
00196               ##### Initialization and Configuration functions #####
00197   ===============================================================================
00198   [..]
00199   This subsection provides a set of functions allowing to initialize the USARTx
00200   associated to the SmartCard.
00201   (+) These parameters can be configured:
00202       (++) Baud Rate
00203       (++) Parity: parity should be enabled, frame Length is fixed to 8 bits plus parity
00204       (++) Receiver/transmitter modes
00205       (++) Synchronous mode (and if enabled, phase, polarity and last bit parameters)
00206       (++) Prescaler value
00207       (++) Guard bit time
00208       (++) NACK enabling or disabling on transmission error
00209 
00210   (+) The following advanced features can be configured as well:
00211       (++) TX and/or RX pin level inversion
00212       (++) data logical level inversion
00213       (++) RX and TX pins swap
00214       (++) RX overrun detection disabling
00215       (++) DMA disabling on RX error
00216       (++) MSB first on communication line
00217       (++) Time out enabling (and if activated, timeout value)
00218       (++) Block length
00219       (++) Auto-retry counter
00220   [..]
00221   The HAL_SMARTCARD_Init() API follows the USART synchronous configuration procedures
00222   (details for the procedures are available in reference manual).
00223 
00224 @endverbatim
00225 
00226   The USART frame format is given in the following table:
00227 
00228     Table 1. USART frame format.
00229     +---------------------------------------------------------------+        
00230     | M1M0 bits |  PCE bit  |            USART frame                |        
00231     |-----------------------|---------------------------------------|        
00232     |     01    |    1      |    | SB | 8 bit data | PB | STB |     |        
00233     +---------------------------------------------------------------+        
00234 
00235 
00236   * @{
00237   */
00238 
00239 /**
00240   * @brief Initialize the SMARTCARD mode according to the specified
00241   *        parameters in the SMARTCARD_HandleTypeDef and initialize the associated handle.
00242   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00243   *                    the configuration information for the specified SMARTCARD module.
00244   * @retval HAL status
00245   */
00246 HAL_StatusTypeDef HAL_SMARTCARD_Init(SMARTCARD_HandleTypeDef *hsmartcard)
00247 {
00248   /* Check the SMARTCARD handle allocation */
00249   if(hsmartcard == NULL)
00250   {
00251     return HAL_ERROR;
00252   }
00253 
00254   /* Check the USART associated to the SmartCard */
00255   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
00256 
00257   if(hsmartcard->gState == HAL_SMARTCARD_STATE_RESET)
00258   {
00259     /* Allocate lock resource and initialize it */
00260     hsmartcard->Lock = HAL_UNLOCKED;
00261 
00262     /* Init the low level hardware : GPIO, CLOCK */
00263     HAL_SMARTCARD_MspInit(hsmartcard);
00264   }
00265 
00266   hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY;
00267 
00268   /* Disable the Peripheral to set smartcard mode */
00269   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00270 
00271   /* In SmartCard mode, the following bits must be kept cleared:
00272   - LINEN in the USART_CR2 register,
00273   - HDSEL and IREN  bits in the USART_CR3 register.*/
00274   CLEAR_BIT(hsmartcard->Instance->CR2, USART_CR2_LINEN);
00275   CLEAR_BIT(hsmartcard->Instance->CR3, (USART_CR3_HDSEL | USART_CR3_IREN));
00276 
00277   /* set the USART in SMARTCARD mode */
00278   SET_BIT(hsmartcard->Instance->CR3, USART_CR3_SCEN);
00279 
00280   /* Set the SMARTCARD Communication parameters */
00281   if (SMARTCARD_SetConfig(hsmartcard) == HAL_ERROR)
00282   {
00283     return HAL_ERROR;
00284   }
00285   
00286   /* Set the SMARTCARD transmission completion indication */  
00287   SMARTCARD_TRANSMISSION_COMPLETION_SETTING(hsmartcard);
00288 
00289   if (hsmartcard->AdvancedInit.AdvFeatureInit != SMARTCARD_ADVFEATURE_NO_INIT)
00290   {
00291     SMARTCARD_AdvFeatureConfig(hsmartcard);
00292   }
00293 
00294   /* Enable the Peripheral */
00295   SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00296 
00297   /* TEACK and/or REACK to check before moving hsmartcard->gState and hsmartcard->RxState to Ready */
00298   return (SMARTCARD_CheckIdleState(hsmartcard));
00299 }
00300 
00301 
00302 /**
00303   * @brief DeInitialize the SMARTCARD peripheral.
00304   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00305   *                    the configuration information for the specified SMARTCARD module.
00306   * @retval HAL status
00307   */
00308 HAL_StatusTypeDef HAL_SMARTCARD_DeInit(SMARTCARD_HandleTypeDef *hsmartcard)
00309 {
00310   /* Check the SMARTCARD handle allocation */
00311   if(hsmartcard == NULL)
00312   {
00313     return HAL_ERROR;
00314   }
00315 
00316   /* Check the parameters */
00317   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
00318 
00319   hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY;
00320 
00321   /* Disable the Peripheral */
00322   CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00323 
00324   WRITE_REG(hsmartcard->Instance->CR1, 0x0);
00325   WRITE_REG(hsmartcard->Instance->CR2, 0x0);
00326   WRITE_REG(hsmartcard->Instance->CR3, 0x0);
00327   WRITE_REG(hsmartcard->Instance->RTOR, 0x0);
00328   WRITE_REG(hsmartcard->Instance->GTPR, 0x0);
00329 
00330   /* DeInit the low level hardware */
00331   HAL_SMARTCARD_MspDeInit(hsmartcard);
00332 
00333   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00334   hsmartcard->gState    = HAL_SMARTCARD_STATE_RESET;
00335   hsmartcard->RxState   = HAL_SMARTCARD_STATE_RESET;
00336 
00337   /* Process Unlock */
00338   __HAL_UNLOCK(hsmartcard);
00339 
00340   return HAL_OK;
00341 }
00342 
00343 /**
00344   * @brief Initialize the SMARTCARD MSP.
00345   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00346   *                    the configuration information for the specified SMARTCARD module.
00347   * @retval None
00348   */
00349 __weak void HAL_SMARTCARD_MspInit(SMARTCARD_HandleTypeDef *hsmartcard)
00350 {
00351   /* Prevent unused argument(s) compilation warning */
00352   UNUSED(hsmartcard);
00353 
00354   /* NOTE : This function should not be modified, when the callback is needed,
00355             the HAL_SMARTCARD_MspInit can be implemented in the user file
00356    */
00357 }
00358 
00359 /**
00360   * @brief DeInitialize the SMARTCARD MSP.
00361   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00362   *                    the configuration information for the specified SMARTCARD module.
00363   * @retval None
00364   */
00365 __weak void HAL_SMARTCARD_MspDeInit(SMARTCARD_HandleTypeDef *hsmartcard)
00366 {
00367   /* Prevent unused argument(s) compilation warning */
00368   UNUSED(hsmartcard);
00369 
00370   /* NOTE : This function should not be modified, when the callback is needed,
00371             the HAL_SMARTCARD_MspDeInit can be implemented in the user file
00372    */
00373 }
00374 
00375 /**
00376   * @}
00377   */
00378 
00379 /** @defgroup SMARTCARD_Exported_Functions_Group2 IO operation functions
00380   *  @brief   SMARTCARD Transmit and Receive functions
00381   *
00382 @verbatim
00383   ==============================================================================
00384                          ##### IO operation functions #####
00385   ==============================================================================
00386   [..]
00387     This subsection provides a set of functions allowing to manage the SMARTCARD data transfers.
00388 
00389   [..]
00390     Smartcard is a single wire half duplex communication protocol.
00391     The Smartcard interface is designed to support asynchronous protocol Smartcards as
00392     defined in the ISO 7816-3 standard. The USART should be configured as:
00393     (+) 8 bits plus parity: where M=1 and PCE=1 in the USART_CR1 register
00394     (+) 1.5 stop bits when transmitting and receiving: where STOP=11 in the USART_CR2 register.
00395 
00396   [..]
00397     (+) There are two modes of transfer:
00398         (++) Blocking mode: The communication is performed in polling mode.
00399              The HAL status of all data processing is returned by the same function
00400              after finishing transfer.
00401         (++) No-Blocking mode: The communication is performed using Interrupts
00402              or DMA, the relevant API's return the HAL status.
00403              The end of the data processing will be indicated through the
00404              dedicated SMARTCARD IRQ when using Interrupt mode or the DMA IRQ when
00405              using DMA mode.
00406         (++) The HAL_SMARTCARD_TxCpltCallback(), HAL_SMARTCARD_RxCpltCallback() user callbacks
00407              will be executed respectively at the end of the Transmit or Receive process
00408              The HAL_SMARTCARD_ErrorCallback() user callback will be executed when a communication
00409              error is detected.
00410 
00411     (+) Blocking mode APIs are :
00412         (++) HAL_SMARTCARD_Transmit()
00413         (++) HAL_SMARTCARD_Receive()
00414 
00415     (+) Non Blocking mode APIs with Interrupt are :
00416         (++) HAL_SMARTCARD_Transmit_IT()
00417         (++) HAL_SMARTCARD_Receive_IT()
00418         (++) HAL_SMARTCARD_IRQHandler()
00419 
00420     (+) Non Blocking mode functions with DMA are :
00421         (++) HAL_SMARTCARD_Transmit_DMA()
00422         (++) HAL_SMARTCARD_Receive_DMA()
00423 
00424     (+) A set of Transfer Complete Callbacks are provided in non Blocking mode:
00425         (++) HAL_SMARTCARD_TxCpltCallback()
00426         (++) HAL_SMARTCARD_RxCpltCallback()
00427         (++) HAL_SMARTCARD_ErrorCallback()
00428 
00429 @endverbatim
00430   * @{
00431   */
00432 
00433 /**
00434   * @brief Send an amount of data in blocking mode.
00435   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00436   *                    the configuration information for the specified SMARTCARD module.
00437   * @param pData: pointer to data buffer.
00438   * @param Size: amount of data to be sent.
00439   * @param Timeout : Timeout duration.
00440   * @retval HAL status
00441   */
00442 HAL_StatusTypeDef HAL_SMARTCARD_Transmit(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size, uint32_t Timeout)
00443 {
00444   uint32_t tickstart = 0;
00445 
00446   /* Check that a Tx process is not already ongoing */
00447   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
00448   {
00449     if((pData == NULL) || (Size == 0))
00450     {
00451       return  HAL_ERROR;
00452     }
00453 
00454     /* Process Locked */
00455     __HAL_LOCK(hsmartcard);
00456 
00457     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
00458 
00459     /* Init tickstart for timeout managment*/
00460     tickstart = HAL_GetTick();
00461     
00462     /* Disable the Peripheral first to update mode for TX master */
00463     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00464 
00465     /* Disable Rx, enable Tx */
00466     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
00467     SET_BIT(hsmartcard->Instance->RQR, SMARTCARD_RXDATA_FLUSH_REQUEST);
00468     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
00469     
00470     /* Enable the Peripheral */
00471     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00472 
00473     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00474     hsmartcard->TxXferSize = Size;
00475     hsmartcard->TxXferCount = Size;
00476 
00477     while(hsmartcard->TxXferCount > 0)
00478     {
00479       hsmartcard->TxXferCount--;
00480       if(SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_FLAG_TXE, RESET, tickstart, Timeout) != HAL_OK)
00481       {
00482         return HAL_TIMEOUT;
00483       }
00484       hsmartcard->Instance->TDR = (*pData++ & (uint8_t)0xFF);
00485     }
00486     if(SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_TRANSMISSION_COMPLETION_FLAG(hsmartcard), RESET, tickstart, Timeout) != HAL_OK)
00487     {
00488       return HAL_TIMEOUT;
00489     }
00490     /* Re-enable Rx at end of transmission if initial mode is Rx/Tx */
00491     if(hsmartcard->Init.Mode == SMARTCARD_MODE_TX_RX)
00492     {
00493       /* Disable the Peripheral first to update modes */
00494       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00495       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
00496       /* Enable the Peripheral */
00497       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00498     }
00499     
00500     /* At end of Tx process, restore hsmartcard->gState to Ready */
00501     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00502 
00503     /* Process Unlocked */
00504     __HAL_UNLOCK(hsmartcard);
00505 
00506     return HAL_OK;
00507   }
00508   else
00509   {
00510     return HAL_BUSY;
00511   }
00512 }
00513 
00514 /**
00515   * @brief Receive an amount of data in blocking mode.
00516   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00517   *                    the configuration information for the specified SMARTCARD module.
00518   * @param pData: pointer to data buffer.
00519   * @param Size: amount of data to be received.
00520   * @param Timeout : Timeout duration.
00521   * @retval HAL status
00522   */
00523 HAL_StatusTypeDef HAL_SMARTCARD_Receive(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size, uint32_t Timeout)
00524 {
00525   uint32_t tickstart = 0;
00526 
00527   /* Check that a Rx process is not already ongoing */
00528   if(hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
00529   {
00530     if((pData == NULL) || (Size == 0))
00531     {
00532       return  HAL_ERROR;
00533     }
00534 
00535     /* Process Locked */
00536     __HAL_LOCK(hsmartcard);
00537 
00538     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00539     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
00540 
00541     /* Init tickstart for timeout managment*/
00542     tickstart = HAL_GetTick();
00543     
00544     hsmartcard->RxXferSize = Size;
00545     hsmartcard->RxXferCount = Size;
00546 
00547     /* Check the remain data to be received */
00548     while(hsmartcard->RxXferCount > 0)
00549     {
00550       hsmartcard->RxXferCount--;
00551       if(SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, SMARTCARD_FLAG_RXNE, RESET, tickstart, Timeout) != HAL_OK)
00552       {
00553         return HAL_TIMEOUT;
00554       }
00555       *pData++ = (uint8_t)(hsmartcard->Instance->RDR & (uint8_t)0x00FF);
00556     }
00557 
00558     /* At end of Rx process, restore hsmartcard->RxState to Ready */
00559     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00560 
00561     /* Process Unlocked */
00562     __HAL_UNLOCK(hsmartcard);
00563 
00564     return HAL_OK;
00565   }
00566   else
00567   {
00568     return HAL_BUSY;
00569   }
00570 }
00571 
00572 /**
00573   * @brief Send an amount of data in interrupt mode.
00574   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00575   *                    the configuration information for the specified SMARTCARD module.
00576   * @param pData: pointer to data buffer.
00577   * @param Size: amount of data to be sent.
00578   * @retval HAL status
00579   */
00580 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
00581 {
00582   /* Check that a Tx process is not already ongoing */
00583   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
00584   {
00585     if((pData == NULL) || (Size == 0))
00586     {
00587       return HAL_ERROR;
00588     }
00589 
00590     /* Process Locked */
00591     __HAL_LOCK(hsmartcard);
00592 
00593     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00594     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
00595 
00596     hsmartcard->pTxBuffPtr = pData;
00597     hsmartcard->TxXferSize = Size;
00598     hsmartcard->TxXferCount = Size;
00599 
00600     /* Disable the Peripheral first to update mode for TX master */
00601     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00602 
00603     /* Disable Rx, enable Tx */
00604     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
00605     SET_BIT(hsmartcard->Instance->RQR, SMARTCARD_RXDATA_FLUSH_REQUEST);
00606     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
00607     
00608     /* Enable the Peripheral */
00609     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00610 
00611     /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
00612     __HAL_SMARTCARD_ENABLE_IT(hsmartcard, SMARTCARD_IT_ERR);
00613 
00614     /* Process Unlocked */
00615     __HAL_UNLOCK(hsmartcard);
00616 
00617     /* Enable the SMARTCARD Transmit Data Register Empty Interrupt */
00618     __HAL_SMARTCARD_ENABLE_IT(hsmartcard, SMARTCARD_IT_TXE);
00619 
00620     return HAL_OK;
00621   }
00622   else
00623   {
00624     return HAL_BUSY;
00625   }
00626 }
00627 
00628 /**
00629   * @brief Receive an amount of data in interrupt mode.
00630   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00631   *                    the configuration information for the specified SMARTCARD module.
00632   * @param pData: pointer to data buffer.
00633   * @param Size: amount of data to be received.
00634   * @retval HAL status
00635   */
00636 HAL_StatusTypeDef HAL_SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
00637 {
00638   /* Check that a Rx process is not already ongoing */
00639   if(hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
00640   {
00641     if((pData == NULL) || (Size == 0))
00642     {
00643       return HAL_ERROR;
00644     }
00645 
00646     /* Process Locked */
00647     __HAL_LOCK(hsmartcard);
00648 
00649     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00650     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
00651 
00652     hsmartcard->pRxBuffPtr = pData;
00653     hsmartcard->RxXferSize = Size;
00654     hsmartcard->RxXferCount = Size;
00655 
00656     /* Process Unlocked */
00657     __HAL_UNLOCK(hsmartcard);
00658 
00659     /* Enable the SMARTCARD Parity Error Interrupt */
00660     __HAL_SMARTCARD_ENABLE_IT(hsmartcard, SMARTCARD_IT_PE);
00661 
00662     /* Enable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
00663     __HAL_SMARTCARD_ENABLE_IT(hsmartcard, SMARTCARD_IT_ERR);
00664 
00665     /* Enable the SMARTCARD Data Register not empty Interrupt */
00666     __HAL_SMARTCARD_ENABLE_IT(hsmartcard, SMARTCARD_IT_RXNE);
00667 
00668     return HAL_OK;
00669   }
00670   else
00671   {
00672     return HAL_BUSY;
00673   }
00674 }
00675 
00676 /**
00677   * @brief Send an amount of data in DMA mode.
00678   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00679   *                    the configuration information for the specified SMARTCARD module.
00680   * @param pData: pointer to data buffer.
00681   * @param Size: amount of data to be sent.
00682   * @retval HAL status
00683   */
00684 HAL_StatusTypeDef HAL_SMARTCARD_Transmit_DMA(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
00685 {
00686   uint32_t *tmp;
00687 
00688   /* Check that a Tx process is not already ongoing */
00689   if (hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
00690   {
00691     if((pData == NULL) || (Size == 0))
00692     {
00693       return HAL_ERROR;
00694     }
00695 
00696     /* Process Locked */
00697     __HAL_LOCK(hsmartcard);
00698 
00699     hsmartcard->gState = HAL_SMARTCARD_STATE_BUSY_TX;
00700 
00701     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00702     hsmartcard->pTxBuffPtr = pData;
00703     hsmartcard->TxXferSize = Size;
00704     hsmartcard->TxXferCount = Size;
00705 
00706     /* Disable the Peripheral first to update mode for TX master */
00707     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00708 
00709     /* Disable Rx, enable Tx */
00710     CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
00711     SET_BIT(hsmartcard->Instance->RQR, SMARTCARD_RXDATA_FLUSH_REQUEST);
00712     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_TE);
00713     
00714     /* Enable the Peripheral */
00715     SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
00716 
00717     /* Set the SMARTCARD DMA transfer complete callback */
00718     hsmartcard->hdmatx->XferCpltCallback = SMARTCARD_DMATransmitCplt;
00719 
00720     /* Set the SMARTCARD error callback */
00721     hsmartcard->hdmatx->XferErrorCallback = SMARTCARD_DMAError;
00722 
00723     /* Enable the SMARTCARD transmit DMA channel */
00724     tmp = (uint32_t*)&pData;
00725     HAL_DMA_Start_IT(hsmartcard->hdmatx, *(uint32_t*)tmp, (uint32_t)&hsmartcard->Instance->TDR, Size);
00726 
00727     /* Clear the TC flag in the ICR register */
00728     __HAL_SMARTCARD_CLEAR_FLAG(hsmartcard, SMARTCARD_CLEAR_TCF);
00729 
00730     /* Enable the DMA transfer for transmit request by setting the DMAT bit
00731        in the SMARTCARD associated USART CR3 register */
00732     SET_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
00733 
00734     /* Process Unlocked */
00735     __HAL_UNLOCK(hsmartcard);
00736 
00737     return HAL_OK;
00738   }
00739   else
00740   {
00741     return HAL_BUSY;
00742   }
00743 }
00744 
00745 /**
00746   * @brief Receive an amount of data in DMA mode.
00747   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00748   *                    the configuration information for the specified SMARTCARD module.
00749   * @param pData: pointer to data buffer.
00750   * @param Size: amount of data to be received.
00751   * @note   The SMARTCARD-associated USART parity is enabled (PCE = 1),
00752   *         the received data contain the parity bit (MSB position).
00753   * @retval HAL status
00754   */
00755 HAL_StatusTypeDef HAL_SMARTCARD_Receive_DMA(SMARTCARD_HandleTypeDef *hsmartcard, uint8_t *pData, uint16_t Size)
00756 {
00757   uint32_t *tmp;
00758 
00759   /* Check that a Rx process is not already ongoing */
00760   if(hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
00761   {
00762     if((pData == NULL) || (Size == 0))
00763     {
00764       return HAL_ERROR;
00765     }
00766 
00767     /* Process Locked */
00768     __HAL_LOCK(hsmartcard);
00769 
00770     hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
00771     hsmartcard->RxState   = HAL_SMARTCARD_STATE_BUSY_RX;
00772 
00773     hsmartcard->pRxBuffPtr = pData;
00774     hsmartcard->RxXferSize = Size;
00775 
00776     /* Set the SMARTCARD DMA transfer complete callback */
00777     hsmartcard->hdmarx->XferCpltCallback = SMARTCARD_DMAReceiveCplt;
00778 
00779     /* Set the SMARTCARD DMA error callback */
00780     hsmartcard->hdmarx->XferErrorCallback = SMARTCARD_DMAError;
00781 
00782     /* Enable the DMA channel */
00783     tmp = (uint32_t*)&pData;
00784     HAL_DMA_Start_IT(hsmartcard->hdmarx, (uint32_t)&hsmartcard->Instance->RDR, *(uint32_t*)tmp, Size);
00785 
00786     /* Enable the DMA transfer for the receiver request by setting the DMAR bit
00787        in the SMARTCARD associated USART CR3 register */
00788     SET_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
00789 
00790     /* Process Unlocked */
00791     __HAL_UNLOCK(hsmartcard);
00792 
00793     return HAL_OK;
00794   }
00795   else
00796   {
00797     return HAL_BUSY;
00798   }
00799 }
00800 
00801 /**
00802   * @brief Handle SMARTCARD interrupt requests.
00803   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00804   *                    the configuration information for the specified SMARTCARD module.
00805   * @retval None
00806   */
00807 void HAL_SMARTCARD_IRQHandler(SMARTCARD_HandleTypeDef *hsmartcard)
00808 {
00809   /* SMARTCARD parity error interrupt occurred -------------------------------------*/
00810   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_PE) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_PE) != RESET))
00811   {
00812     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_PEF);
00813     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_PE;
00814     /* Set the SMARTCARD states ready to be able to start again the process */
00815     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00816     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00817   }
00818 
00819   /* SMARTCARD frame error interrupt occurred --------------------------------------*/
00820   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_FE) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_ERR) != RESET))
00821   {
00822     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_FEF);
00823     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_FE;
00824     /* Set the SMARTCARD states ready to be able to start again the process */
00825     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00826     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00827   }
00828 
00829   /* SMARTCARD noise error interrupt occurred --------------------------------------*/
00830   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_NE) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_ERR) != RESET))
00831   {
00832     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_NEF);
00833     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_NE;
00834     /* Set the SMARTCARD states ready to be able to start again the process */
00835     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00836     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00837   }
00838 
00839   /* SMARTCARD Over-Run interrupt occurred -----------------------------------------*/
00840   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_ORE) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_ERR) != RESET))
00841   {
00842     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_OREF);
00843     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_ORE;
00844     /* Set the SMARTCARD states ready to be able to start again the process */
00845     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00846     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00847   }
00848 
00849   /* SMARTCARD receiver timeout interrupt occurred -----------------------------------------*/
00850   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_RTO) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_RTO) != RESET))
00851   {
00852     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_RTOF);
00853     hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_RTO;
00854     /* Set the SMARTCARD states ready to be able to start again the process */
00855     hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
00856     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00857   }
00858 
00859   /* Call SMARTCARD Error Call back function if need be --------------------------*/
00860   if(hsmartcard->ErrorCode != HAL_SMARTCARD_ERROR_NONE)
00861   {
00862     HAL_SMARTCARD_ErrorCallback(hsmartcard);
00863   }
00864 
00865   /* SMARTCARD in mode Receiver ---------------------------------------------------*/
00866   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_RXNE) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_RXNE) != RESET))
00867   {
00868     SMARTCARD_Receive_IT(hsmartcard);
00869     /* Clear RXNE interrupt flag done by reading RDR in SMARTCARD_Receive_IT() */
00870   }
00871 
00872   /* SMARTCARD in mode Receiver, end of block interruption ------------------------*/
00873   if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_EOB) != RESET) && (__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_EOB) != RESET))
00874   {
00875     hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
00876     __HAL_UNLOCK(hsmartcard);
00877     HAL_SMARTCARD_RxCpltCallback(hsmartcard);
00878     /* Clear EOBF interrupt after HAL_SMARTCARD_RxCpltCallback() call for the End of Block information
00879      * to be available during HAL_SMARTCARD_RxCpltCallback() processing */
00880     __HAL_SMARTCARD_CLEAR_IT(hsmartcard, SMARTCARD_CLEAR_EOBF);
00881   }
00882 
00883   /* SMARTCARD in mode Transmitter ------------------------------------------------*/
00884  if((__HAL_SMARTCARD_GET_IT(hsmartcard, SMARTCARD_IT_TXE) != RESET) &&(__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, SMARTCARD_IT_TXE) != RESET))
00885   {
00886     SMARTCARD_Transmit_IT(hsmartcard);
00887   }
00888 
00889   /* SMARTCARD in mode Transmitter (transmission end) ------------------------*/
00890  if((__HAL_SMARTCARD_GET_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication) != RESET) &&(__HAL_SMARTCARD_GET_IT_SOURCE(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication) != RESET))
00891   {
00892     SMARTCARD_EndTransmit_IT(hsmartcard);
00893   }
00894 }
00895 
00896 /**
00897   * @brief Tx Transfer completed callback.
00898   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00899   *                    the configuration information for the specified SMARTCARD module.
00900   * @retval None
00901   */
00902 __weak void HAL_SMARTCARD_TxCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
00903 {
00904   /* Prevent unused argument(s) compilation warning */
00905   UNUSED(hsmartcard);
00906 
00907   /* NOTE : This function should not be modified, when the callback is needed,
00908             the HAL_SMARTCARD_TxCpltCallback can be implemented in the user file.
00909    */
00910 }
00911 
00912 /**
00913   * @brief Rx Transfer completed callback.
00914   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00915   *                    the configuration information for the specified SMARTCARD module.
00916   * @retval None
00917   */
00918 __weak void HAL_SMARTCARD_RxCpltCallback(SMARTCARD_HandleTypeDef *hsmartcard)
00919 {
00920   /* Prevent unused argument(s) compilation warning */
00921   UNUSED(hsmartcard);
00922 
00923   /* NOTE : This function should not be modified, when the callback is needed,
00924             the HAL_SMARTCARD_RxCpltCallback can be implemented in the user file.
00925    */
00926 }
00927 
00928 /**
00929   * @brief SMARTCARD error callback.
00930   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00931   *                    the configuration information for the specified SMARTCARD module.
00932   * @retval None
00933   */
00934 __weak void HAL_SMARTCARD_ErrorCallback(SMARTCARD_HandleTypeDef *hsmartcard)
00935 {
00936   /* Prevent unused argument(s) compilation warning */
00937   UNUSED(hsmartcard);
00938 
00939   /* NOTE : This function should not be modified, when the callback is needed,
00940             the HAL_SMARTCARD_ErrorCallback can be implemented in the user file.
00941    */
00942 }
00943 
00944 /**
00945   * @}
00946   */
00947 
00948 /** @defgroup SMARTCARD_Exported_Functions_Group4 Peripheral State and Errors functions
00949   *  @brief   SMARTCARD State and Errors functions
00950   *
00951 @verbatim
00952   ==============================================================================
00953                   ##### Peripheral State and Errors functions #####
00954   ==============================================================================
00955   [..]
00956     This subsection provides a set of functions allowing to return the State of SmartCard
00957     handle and also return Peripheral Errors occurred during communication process
00958      (+) HAL_SMARTCARD_GetState() API can be helpful to check in run-time the state
00959          of the SMARTCARD peripheral.
00960      (+) HAL_SMARTCARD_GetError() checks in run-time errors that could occur during
00961          communication.
00962 
00963 @endverbatim
00964   * @{
00965   */
00966 
00967 
00968 /**
00969   * @brief  Return the SMARTCARD handle state.
00970   * @param  hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00971   *                     the configuration information for the specified SMARTCARD module.
00972   * @retval SMARTCARD handle state
00973   */
00974 HAL_SMARTCARD_StateTypeDef HAL_SMARTCARD_GetState(SMARTCARD_HandleTypeDef *hsmartcard)
00975 {
00976   uint32_t temp1= 0x00, temp2 = 0x00;
00977   temp1 = hsmartcard->gState;
00978   temp2 = hsmartcard->RxState;
00979   
00980   return (HAL_SMARTCARD_StateTypeDef)(temp1 | temp2);
00981 }
00982 
00983 /**
00984   * @brief  Return the SMARTCARD handle error code.
00985   * @param  hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
00986   *                     the configuration information for the specified SMARTCARD module.
00987   * @retval SMARTCARD handle Error Code
00988 */
00989 uint32_t HAL_SMARTCARD_GetError(SMARTCARD_HandleTypeDef *hsmartcard)
00990 {
00991   return hsmartcard->ErrorCode;
00992 }
00993 
00994 /**
00995   * @}
00996   */
00997 
00998 /**
00999   * @}
01000   */
01001 
01002 /** @defgroup SMARTCARD_Private_Functions   SMARTCARD Private Functions
01003   * @{
01004   */
01005 
01006 /**
01007   * @brief Send an amount of data in non-blocking mode.
01008   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01009   *                the configuration information for the specified SMARTCARD module.
01010   *         Function called under interruption only, once
01011   *         interruptions have been enabled by HAL_SMARTCARD_Transmit_IT()
01012   * @retval HAL status
01013   */
01014 static HAL_StatusTypeDef SMARTCARD_Transmit_IT(SMARTCARD_HandleTypeDef *hsmartcard)
01015 {
01016   /* Check that a Tx process is ongoing */
01017   if (hsmartcard->gState == HAL_SMARTCARD_STATE_BUSY_TX)
01018   {
01019 
01020     if(hsmartcard->TxXferCount == 0)
01021     {
01022       /* Disable the SMARTCARD Transmit Data Register Empty Interrupt */
01023       __HAL_SMARTCARD_DISABLE_IT(hsmartcard, SMARTCARD_IT_TXE);
01024 
01025       /* Enable the SMARTCARD Transmit Complete Interrupt */
01026       __HAL_SMARTCARD_ENABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
01027 
01028       return HAL_OK;
01029     }
01030     else
01031     {
01032       hsmartcard->Instance->TDR = (*hsmartcard->pTxBuffPtr++ & (uint8_t)0xFF);
01033       hsmartcard->TxXferCount--;
01034 
01035       return HAL_OK;
01036     }
01037   }
01038   else
01039   {
01040     return HAL_BUSY;
01041   }
01042 }
01043 
01044 /**
01045   * @brief  Wrap up transmission in non-blocking mode.
01046   * @param  hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01047   *                     the configuration information for the specified SMARTCARD module.
01048   * @retval HAL status
01049   */
01050 static HAL_StatusTypeDef SMARTCARD_EndTransmit_IT(SMARTCARD_HandleTypeDef *hsmartcard)
01051 {
01052   /* Disable the SMARTCARD Transmit Complete Interrupt */
01053   __HAL_SMARTCARD_DISABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
01054 
01055   /* Check if a receive process is ongoing or not. If not disable ERR IT */
01056   if(hsmartcard->RxState == HAL_SMARTCARD_STATE_READY)
01057   {
01058     /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
01059     __HAL_SMARTCARD_DISABLE_IT(hsmartcard, SMARTCARD_IT_ERR);
01060   }
01061   else
01062   {
01063     /* Re-enable Rx at end of transmission if initial mode is Rx/Tx */
01064     if(hsmartcard->Init.Mode == SMARTCARD_MODE_TX_RX)
01065     {
01066       /* Disable the Peripheral first to update modes */
01067       CLEAR_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
01068       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_RE);
01069       /* Enable the Peripheral */
01070       SET_BIT(hsmartcard->Instance->CR1, USART_CR1_UE);
01071     }
01072   }
01073 
01074   /* Tx process is ended, restore hsmartcard->gState to Ready */
01075   hsmartcard->gState = HAL_SMARTCARD_STATE_READY;
01076 
01077   HAL_SMARTCARD_TxCpltCallback(hsmartcard);
01078 
01079   return HAL_OK;
01080 }
01081 
01082 
01083 /**
01084   * @brief Receive an amount of data in non-blocking mode.
01085   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01086   *                the configuration information for the specified SMARTCARD module.
01087   *         Function called under interruption only, once
01088   *         interruptions have been enabled by HAL_SMARTCARD_Receive_IT().
01089   * @retval HAL status
01090   */
01091 static HAL_StatusTypeDef SMARTCARD_Receive_IT(SMARTCARD_HandleTypeDef *hsmartcard)
01092 {
01093   /* Check that a Rx process is ongoing */
01094   if (hsmartcard->RxState == HAL_SMARTCARD_STATE_BUSY_RX)
01095   {
01096     *hsmartcard->pRxBuffPtr++ = (uint8_t)(hsmartcard->Instance->RDR & (uint8_t)0xFF);
01097 
01098     if(--hsmartcard->RxXferCount == 0)
01099     {
01100       __HAL_SMARTCARD_DISABLE_IT(hsmartcard, SMARTCARD_IT_RXNE);
01101 
01102       /* Check if a transmit process is ongoing or not. If not disable ERR IT */
01103       if(hsmartcard->gState == HAL_SMARTCARD_STATE_READY)
01104       {
01105         /* Disable the SMARTCARD Error Interrupt: (Frame error, noise error, overrun error) */
01106         __HAL_SMARTCARD_DISABLE_IT(hsmartcard, SMARTCARD_IT_ERR);
01107       }
01108 
01109       /* Disable the SMARTCARD Parity Error Interrupt */
01110       __HAL_SMARTCARD_DISABLE_IT(hsmartcard, SMARTCARD_IT_PE);
01111 
01112       hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
01113 
01114       HAL_SMARTCARD_RxCpltCallback(hsmartcard);
01115 
01116       return HAL_OK;
01117     }
01118 
01119     return HAL_OK;
01120   }
01121   else
01122   {
01123     return HAL_BUSY;
01124   }
01125 }
01126 
01127 /**
01128   * @brief  Handle SMARTCARD Communication Timeout.
01129   * @param  hsmartcard Pointer to a SMARTCARD_HandleTypeDef structure that contains
01130   *                    the configuration information for the specified SMARTCARD module.
01131   * @param  Flag Specifies the SMARTCARD flag to check.
01132   * @param  Status The new Flag status (SET or RESET).
01133   * @param  Tickstart Tick start value
01134   * @param  Timeout Timeout duration.
01135   * @retval HAL status
01136   */
01137 static HAL_StatusTypeDef SMARTCARD_WaitOnFlagUntilTimeout(SMARTCARD_HandleTypeDef *hsmartcard, uint32_t Flag, FlagStatus Status, uint32_t Tickstart, uint32_t Timeout)
01138 {
01139   /* Wait until flag is set */
01140   while((__HAL_SMARTCARD_GET_FLAG(hsmartcard, Flag) ? SET : RESET) == Status)
01141   {
01142     /* Check for the Timeout */
01143     if(Timeout != HAL_MAX_DELAY)
01144     {
01145       if((Timeout == 0) || ((HAL_GetTick()-Tickstart) > Timeout))
01146       {
01147         /* Disable TXE, RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts for the interrupt process */
01148         CLEAR_BIT(hsmartcard->Instance->CR1, (USART_CR1_RXNEIE | USART_CR1_PEIE | USART_CR1_TXEIE));
01149         CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_EIE);
01150 
01151         hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
01152         hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
01153 
01154         /* Process Unlocked */
01155         __HAL_UNLOCK(hsmartcard);
01156 
01157         return HAL_TIMEOUT;
01158       }
01159     }
01160   }
01161   return HAL_OK;
01162 }
01163 
01164 /**
01165   * @brief DMA SMARTCARD transmit process complete callback.
01166   * @param  hdma: Pointer to a DMA_HandleTypeDef structure that contains
01167   *               the configuration information for the specified DMA module.
01168   * @retval None
01169   */
01170 static void SMARTCARD_DMATransmitCplt(DMA_HandleTypeDef *hdma)
01171 {
01172   SMARTCARD_HandleTypeDef* hsmartcard = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
01173   hsmartcard->TxXferCount = 0;
01174 
01175   /* Disable the DMA transfer for transmit request by resetting the DMAT bit
01176   in the SMARTCARD associated USART CR3 register */
01177   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAT);
01178 
01179   /* Enable the SMARTCARD Transmit Complete Interrupt */
01180   __HAL_SMARTCARD_ENABLE_IT(hsmartcard, hsmartcard->AdvancedInit.TxCompletionIndication);
01181 }
01182 
01183 /**
01184   * @brief DMA SMARTCARD receive process complete callback.
01185   * @param  hdma: Pointer to a DMA_HandleTypeDef structure that contains
01186   *               the configuration information for the specified DMA module.
01187   * @retval None
01188   */
01189 static void SMARTCARD_DMAReceiveCplt(DMA_HandleTypeDef *hdma)
01190 {
01191   SMARTCARD_HandleTypeDef* hsmartcard = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
01192   hsmartcard->RxXferCount = 0;
01193 
01194   /* Disable the DMA transfer for the receiver request by resetting the DMAR bit
01195      in the SMARTCARD associated USART CR3 register */
01196   CLEAR_BIT(hsmartcard->Instance->CR3, USART_CR3_DMAR);
01197 
01198   /* At end of Rx process, restore hsmartcard->RxState to Ready */
01199   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
01200 
01201   HAL_SMARTCARD_RxCpltCallback(hsmartcard);
01202 }
01203 
01204 /**
01205   * @brief DMA SMARTCARD communication error callback.
01206   * @param  hdma: Pointer to a DMA_HandleTypeDef structure that contains
01207   *               the configuration information for the specified DMA module.
01208   * @retval None
01209   */
01210 static void SMARTCARD_DMAError(DMA_HandleTypeDef *hdma)
01211 {
01212   SMARTCARD_HandleTypeDef* hsmartcard = ( SMARTCARD_HandleTypeDef* )((DMA_HandleTypeDef* )hdma)->Parent;
01213   hsmartcard->RxXferCount = 0;
01214   hsmartcard->TxXferCount = 0;
01215   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
01216   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
01217   hsmartcard->ErrorCode |= HAL_SMARTCARD_ERROR_DMA;
01218   HAL_SMARTCARD_ErrorCallback(hsmartcard);
01219 }
01220 
01221 /**
01222   * @brief Configure the SMARTCARD associated USART peripheral.
01223   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01224   *                    the configuration information for the specified SMARTCARD module.
01225   * @retval None
01226   */
01227 static HAL_StatusTypeDef SMARTCARD_SetConfig(SMARTCARD_HandleTypeDef *hsmartcard)
01228 {
01229   uint32_t tmpreg                          = 0x00000000;
01230   SMARTCARD_ClockSourceTypeDef clocksource = SMARTCARD_CLOCKSOURCE_UNDEFINED;
01231   HAL_StatusTypeDef ret                    = HAL_OK;
01232 
01233   /* Check the parameters */
01234   assert_param(IS_SMARTCARD_INSTANCE(hsmartcard->Instance));
01235   assert_param(IS_SMARTCARD_BAUDRATE(hsmartcard->Init.BaudRate));
01236   assert_param(IS_SMARTCARD_WORD_LENGTH(hsmartcard->Init.WordLength));
01237   assert_param(IS_SMARTCARD_STOPBITS(hsmartcard->Init.StopBits));
01238   assert_param(IS_SMARTCARD_PARITY(hsmartcard->Init.Parity));
01239   assert_param(IS_SMARTCARD_MODE(hsmartcard->Init.Mode));
01240   assert_param(IS_SMARTCARD_POLARITY(hsmartcard->Init.CLKPolarity));
01241   assert_param(IS_SMARTCARD_PHASE(hsmartcard->Init.CLKPhase));
01242   assert_param(IS_SMARTCARD_LASTBIT(hsmartcard->Init.CLKLastBit));
01243   assert_param(IS_SMARTCARD_ONE_BIT_SAMPLE(hsmartcard->Init.OneBitSampling));
01244   assert_param(IS_SMARTCARD_NACK(hsmartcard->Init.NACKEnable));
01245   assert_param(IS_SMARTCARD_TIMEOUT(hsmartcard->Init.TimeOutEnable));
01246   assert_param(IS_SMARTCARD_AUTORETRY_COUNT(hsmartcard->Init.AutoRetryCount));
01247 
01248   /*-------------------------- USART CR1 Configuration -----------------------*/
01249   /* In SmartCard mode, M and PCE are forced to 1 (8 bits + parity).
01250    * Oversampling is forced to 16 (OVER8 = 0).
01251    * Configure the Parity and Mode:
01252    *  set PS bit according to hsmartcard->Init.Parity value
01253    *  set TE and RE bits according to hsmartcard->Init.Mode value */
01254   tmpreg = (uint32_t) hsmartcard->Init.Parity | hsmartcard->Init.Mode;
01255   tmpreg |= (uint32_t) hsmartcard->Init.WordLength;
01256   MODIFY_REG(hsmartcard->Instance->CR1, USART_CR1_FIELDS, tmpreg);
01257 
01258   /*-------------------------- USART CR2 Configuration -----------------------*/
01259   tmpreg = hsmartcard->Init.StopBits;
01260   /* Synchronous mode is activated by default */
01261   tmpreg |= (uint32_t) USART_CR2_CLKEN | hsmartcard->Init.CLKPolarity;
01262   tmpreg |= (uint32_t) hsmartcard->Init.CLKPhase | hsmartcard->Init.CLKLastBit;
01263   tmpreg |= (uint32_t) hsmartcard->Init.TimeOutEnable;
01264   MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_FIELDS, tmpreg);
01265 
01266   /*-------------------------- USART CR3 Configuration -----------------------*/
01267   /* Configure
01268    * - one-bit sampling method versus three samples' majority rule
01269    *   according to hsmartcard->Init.OneBitSampling
01270    * - NACK transmission in case of parity error according
01271    *   to hsmartcard->Init.NACKEnable
01272    * - autoretry counter according to hsmartcard->Init.AutoRetryCount     */
01273   tmpreg =  (uint32_t) hsmartcard->Init.OneBitSampling | hsmartcard->Init.NACKEnable;
01274   tmpreg |= ((uint32_t)hsmartcard->Init.AutoRetryCount << SMARTCARD_CR3_SCARCNT_LSB_POS);
01275   MODIFY_REG(hsmartcard->Instance-> CR3,USART_CR3_FIELDS, tmpreg);
01276 
01277   /*-------------------------- USART GTPR Configuration ----------------------*/
01278   tmpreg = (hsmartcard->Init.Prescaler | ((uint32_t)hsmartcard->Init.GuardTime << SMARTCARD_GTPR_GT_LSB_POS));
01279   MODIFY_REG(hsmartcard->Instance->GTPR, (USART_GTPR_GT|USART_GTPR_PSC), tmpreg);
01280 
01281   /*-------------------------- USART RTOR Configuration ----------------------*/
01282   tmpreg =   ((uint32_t)hsmartcard->Init.BlockLength << SMARTCARD_RTOR_BLEN_LSB_POS);
01283   if (hsmartcard->Init.TimeOutEnable == SMARTCARD_TIMEOUT_ENABLE)
01284   {
01285     assert_param(IS_SMARTCARD_TIMEOUT_VALUE(hsmartcard->Init.TimeOutValue));
01286     tmpreg |=  (uint32_t) hsmartcard->Init.TimeOutValue;
01287   }
01288   MODIFY_REG(hsmartcard->Instance->RTOR, (USART_RTOR_RTO|USART_RTOR_BLEN), tmpreg);
01289 
01290   /*-------------------------- USART BRR Configuration -----------------------*/
01291   SMARTCARD_GETCLOCKSOURCE(hsmartcard, clocksource);
01292   switch (clocksource)
01293   {
01294     case SMARTCARD_CLOCKSOURCE_PCLK1:
01295       hsmartcard->Instance->BRR = (uint16_t)((HAL_RCC_GetPCLK1Freq() + (hsmartcard->Init.BaudRate/2)) / hsmartcard->Init.BaudRate);
01296       break;
01297     case SMARTCARD_CLOCKSOURCE_PCLK2:
01298       hsmartcard->Instance->BRR = (uint16_t)((HAL_RCC_GetPCLK2Freq() + (hsmartcard->Init.BaudRate/2)) / hsmartcard->Init.BaudRate);
01299       break;
01300     case SMARTCARD_CLOCKSOURCE_HSI:
01301       hsmartcard->Instance->BRR = (uint16_t)((HSI_VALUE + (hsmartcard->Init.BaudRate/2)) / hsmartcard->Init.BaudRate);
01302       break;
01303     case SMARTCARD_CLOCKSOURCE_SYSCLK:
01304       hsmartcard->Instance->BRR = (uint16_t)((HAL_RCC_GetSysClockFreq() + (hsmartcard->Init.BaudRate/2)) / hsmartcard->Init.BaudRate);
01305       break;
01306     case SMARTCARD_CLOCKSOURCE_LSE:
01307       hsmartcard->Instance->BRR = (uint16_t)((LSE_VALUE + (hsmartcard->Init.BaudRate/2)) / hsmartcard->Init.BaudRate);
01308       break;
01309     case SMARTCARD_CLOCKSOURCE_UNDEFINED:
01310     default:
01311       ret = HAL_ERROR;
01312       break;
01313   }
01314 
01315   return ret;
01316 }
01317 
01318 
01319 /**
01320   * @brief Configure the SMARTCARD associated USART peripheral advanced features.
01321   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01322   *                    the configuration information for the specified SMARTCARD module.
01323   * @retval None
01324   */
01325 static void SMARTCARD_AdvFeatureConfig(SMARTCARD_HandleTypeDef *hsmartcard)
01326 {
01327   /* Check whether the set of advanced features to configure is properly set */
01328   assert_param(IS_SMARTCARD_ADVFEATURE_INIT(hsmartcard->AdvancedInit.AdvFeatureInit));
01329 
01330   /* if required, configure TX pin active level inversion */
01331   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_TXINVERT_INIT))
01332   {
01333     assert_param(IS_SMARTCARD_ADVFEATURE_TXINV(hsmartcard->AdvancedInit.TxPinLevelInvert));
01334     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_TXINV, hsmartcard->AdvancedInit.TxPinLevelInvert);
01335   }
01336 
01337   /* if required, configure RX pin active level inversion */
01338   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_RXINVERT_INIT))
01339   {
01340     assert_param(IS_SMARTCARD_ADVFEATURE_RXINV(hsmartcard->AdvancedInit.RxPinLevelInvert));
01341     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_RXINV, hsmartcard->AdvancedInit.RxPinLevelInvert);
01342   }
01343 
01344   /* if required, configure data inversion */
01345   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_DATAINVERT_INIT))
01346   {
01347     assert_param(IS_SMARTCARD_ADVFEATURE_DATAINV(hsmartcard->AdvancedInit.DataInvert));
01348     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_DATAINV, hsmartcard->AdvancedInit.DataInvert);
01349   }
01350 
01351   /* if required, configure RX/TX pins swap */
01352   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_SWAP_INIT))
01353   {
01354     assert_param(IS_SMARTCARD_ADVFEATURE_SWAP(hsmartcard->AdvancedInit.Swap));
01355     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_SWAP, hsmartcard->AdvancedInit.Swap);
01356   }
01357 
01358   /* if required, configure RX overrun detection disabling */
01359   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_RXOVERRUNDISABLE_INIT))
01360   {
01361     assert_param(IS_SMARTCARD_OVERRUN(hsmartcard->AdvancedInit.OverrunDisable));
01362     MODIFY_REG(hsmartcard->Instance->CR3, USART_CR3_OVRDIS, hsmartcard->AdvancedInit.OverrunDisable);
01363   }
01364 
01365   /* if required, configure DMA disabling on reception error */
01366   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_DMADISABLEONERROR_INIT))
01367   {
01368     assert_param(IS_SMARTCARD_ADVFEATURE_DMAONRXERROR(hsmartcard->AdvancedInit.DMADisableonRxError));
01369     MODIFY_REG(hsmartcard->Instance->CR3, USART_CR3_DDRE, hsmartcard->AdvancedInit.DMADisableonRxError);
01370   }
01371 
01372   /* if required, configure MSB first on communication line */
01373   if (HAL_IS_BIT_SET(hsmartcard->AdvancedInit.AdvFeatureInit, SMARTCARD_ADVFEATURE_MSBFIRST_INIT))
01374   {
01375     assert_param(IS_SMARTCARD_ADVFEATURE_MSBFIRST(hsmartcard->AdvancedInit.MSBFirst));
01376     MODIFY_REG(hsmartcard->Instance->CR2, USART_CR2_MSBFIRST, hsmartcard->AdvancedInit.MSBFirst);
01377   }
01378 
01379 }
01380 
01381 /**
01382   * @brief Check the SMARTCARD Idle State.
01383   * @param hsmartcard: Pointer to a SMARTCARD_HandleTypeDef structure that contains
01384   *                    the configuration information for the specified SMARTCARD module.
01385   * @retval HAL status
01386   */
01387 static HAL_StatusTypeDef SMARTCARD_CheckIdleState(SMARTCARD_HandleTypeDef *hsmartcard)
01388 {
01389   uint32_t tickstart = 0;
01390 
01391   /* Initialize the SMARTCARD ErrorCode */
01392   hsmartcard->ErrorCode = HAL_SMARTCARD_ERROR_NONE;
01393 
01394   /* Init tickstart for timeout managment*/
01395   tickstart = HAL_GetTick();
01396 
01397   /* Check if the Transmitter is enabled */
01398   if((hsmartcard->Instance->CR1 & USART_CR1_TE) == USART_CR1_TE)
01399   {
01400     /* Wait until TEACK flag is set */
01401     if(SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, USART_ISR_TEACK, RESET, tickstart, SMARTCARD_TEACK_REACK_TIMEOUT) != HAL_OK)
01402     {
01403       return HAL_TIMEOUT;
01404     }
01405   }
01406   /* Check if the Receiver is enabled */
01407   if((hsmartcard->Instance->CR1 & USART_CR1_RE) == USART_CR1_RE)
01408   {
01409     /* Wait until REACK flag is set */
01410     if(SMARTCARD_WaitOnFlagUntilTimeout(hsmartcard, USART_ISR_REACK, RESET, tickstart, SMARTCARD_TEACK_REACK_TIMEOUT) != HAL_OK)
01411     {
01412       return HAL_TIMEOUT;
01413     }
01414   }
01415 
01416   /* Initialize the SMARTCARD states */
01417   hsmartcard->gState  = HAL_SMARTCARD_STATE_READY;
01418   hsmartcard->RxState = HAL_SMARTCARD_STATE_READY;
01419 
01420   /* Process Unlocked */
01421   __HAL_UNLOCK(hsmartcard);
01422 
01423   return HAL_OK;
01424 }
01425 
01426 /**
01427   * @}
01428   */
01429 
01430 #endif /* HAL_SMARTCARD_MODULE_ENABLED */
01431 /**
01432   * @}
01433   */
01434 
01435 /**
01436   * @}
01437   */
01438 
01439 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/