1 /**
2   ******************************************************************************
3   * @file    stm32l5xx_hal_uart.c
4   * @author  MCD Application Team
5   * @brief   UART HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the Universal Asynchronous Receiver Transmitter Peripheral (UART).
8   *           + Initialization and de-initialization functions
9   *           + IO operation functions
10   *           + Peripheral Control functions
11   *
12   *
13   ******************************************************************************
14   * @attention
15   *
16   * Copyright (c) 2019 STMicroelectronics.
17   * All rights reserved.
18   *
19   * This software is licensed under terms that can be found in the LICENSE file
20   * in the root directory of this software component.
21   * If no LICENSE file comes with this software, it is provided AS-IS.
22   *
23   ******************************************************************************
24   @verbatim
25  ===============================================================================
26                         ##### How to use this driver #####
27  ===============================================================================
28   [..]
29     The UART HAL driver can be used as follows:
30 
31     (#) Declare a UART_HandleTypeDef handle structure (eg. UART_HandleTypeDef huart).
32     (#) Initialize the UART low level resources by implementing the HAL_UART_MspInit() API:
33         (++) Enable the USARTx interface clock.
34         (++) UART pins configuration:
35             (+++) Enable the clock for the UART GPIOs.
36             (+++) Configure these UART pins as alternate function pull-up.
37         (++) NVIC configuration if you need to use interrupt process (HAL_UART_Transmit_IT()
38              and HAL_UART_Receive_IT() APIs):
39             (+++) Configure the USARTx interrupt priority.
40             (+++) Enable the NVIC USART IRQ handle.
41         (++) UART interrupts handling:
42               -@@-  The specific UART interrupts (Transmission complete interrupt,
43                 RXNE interrupt, RX/TX FIFOs related interrupts and Error Interrupts)
44                 are managed using the macros __HAL_UART_ENABLE_IT() and __HAL_UART_DISABLE_IT()
45                 inside the transmit and receive processes.
46         (++) DMA Configuration if you need to use DMA process (HAL_UART_Transmit_DMA()
47              and HAL_UART_Receive_DMA() APIs):
48             (+++) Declare a DMA handle structure for the Tx/Rx channel.
49             (+++) Enable the DMAx interface clock.
50             (+++) Configure the declared DMA handle structure with the required Tx/Rx parameters.
51             (+++) Configure the DMA Tx/Rx channel.
52             (+++) Associate the initialized DMA handle to the UART DMA Tx/Rx handle.
53             (+++) Configure the priority and enable the NVIC for the transfer complete
54                   interrupt on the DMA Tx/Rx channel.
55 
56     (#) Program the Baud Rate, Word Length, Stop Bit, Parity, Prescaler value , Hardware
57         flow control and Mode (Receiver/Transmitter) in the huart handle Init structure.
58 
59     (#) If required, program UART advanced features (TX/RX pins swap, auto Baud rate detection,...)
60         in the huart handle AdvancedInit structure.
61 
62     (#) For the UART asynchronous mode, initialize the UART registers by calling
63         the HAL_UART_Init() API.
64 
65     (#) For the UART Half duplex mode, initialize the UART registers by calling
66         the HAL_HalfDuplex_Init() API.
67 
68     (#) For the UART LIN (Local Interconnection Network) mode, initialize the UART registers
69         by calling the HAL_LIN_Init() API.
70 
71     (#) For the UART Multiprocessor mode, initialize the UART registers
72         by calling the HAL_MultiProcessor_Init() API.
73 
74     (#) For the UART RS485 Driver Enabled mode, initialize the UART registers
75         by calling the HAL_RS485Ex_Init() API.
76 
77     [..]
78     (@) These API's (HAL_UART_Init(), HAL_HalfDuplex_Init(), HAL_LIN_Init(), HAL_MultiProcessor_Init(),
79         also configure the low level Hardware GPIO, CLOCK, CORTEX...etc) by
80         calling the customized HAL_UART_MspInit() API.
81 
82     ##### Callback registration #####
83     ==================================
84 
85     [..]
86     The compilation define USE_HAL_UART_REGISTER_CALLBACKS when set to 1
87     allows the user to configure dynamically the driver callbacks.
88 
89     [..]
90     Use Function HAL_UART_RegisterCallback() to register a user callback.
91     Function HAL_UART_RegisterCallback() allows to register following callbacks:
92     (+) TxHalfCpltCallback        : Tx Half Complete Callback.
93     (+) TxCpltCallback            : Tx Complete Callback.
94     (+) RxHalfCpltCallback        : Rx Half Complete Callback.
95     (+) RxCpltCallback            : Rx Complete Callback.
96     (+) ErrorCallback             : Error Callback.
97     (+) AbortCpltCallback         : Abort Complete Callback.
98     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
99     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
100     (+) WakeupCallback            : Wakeup Callback.
101     (+) RxFifoFullCallback        : Rx Fifo Full Callback.
102     (+) TxFifoEmptyCallback       : Tx Fifo Empty Callback.
103     (+) MspInitCallback           : UART MspInit.
104     (+) MspDeInitCallback         : UART MspDeInit.
105     This function takes as parameters the HAL peripheral handle, the Callback ID
106     and a pointer to the user callback function.
107 
108     [..]
109     Use function HAL_UART_UnRegisterCallback() to reset a callback to the default
110     weak (surcharged) function.
111     HAL_UART_UnRegisterCallback() takes as parameters the HAL peripheral handle,
112     and the Callback ID.
113     This function allows to reset following callbacks:
114     (+) TxHalfCpltCallback        : Tx Half Complete Callback.
115     (+) TxCpltCallback            : Tx Complete Callback.
116     (+) RxHalfCpltCallback        : Rx Half Complete Callback.
117     (+) RxCpltCallback            : Rx Complete Callback.
118     (+) ErrorCallback             : Error Callback.
119     (+) AbortCpltCallback         : Abort Complete Callback.
120     (+) AbortTransmitCpltCallback : Abort Transmit Complete Callback.
121     (+) AbortReceiveCpltCallback  : Abort Receive Complete Callback.
122     (+) WakeupCallback            : Wakeup Callback.
123     (+) RxFifoFullCallback        : Rx Fifo Full Callback.
124     (+) TxFifoEmptyCallback       : Tx Fifo Empty Callback.
125     (+) MspInitCallback           : UART MspInit.
126     (+) MspDeInitCallback         : UART MspDeInit.
127 
128     [..]
129     For specific callback RxEventCallback, use dedicated registration/reset functions:
130     respectively HAL_UART_RegisterRxEventCallback() , HAL_UART_UnRegisterRxEventCallback().
131 
132     [..]
133     By default, after the HAL_UART_Init() and when the state is HAL_UART_STATE_RESET
134     all callbacks are set to the corresponding weak (surcharged) functions:
135     examples HAL_UART_TxCpltCallback(), HAL_UART_RxHalfCpltCallback().
136     Exception done for MspInit and MspDeInit functions that are respectively
137     reset to the legacy weak (surcharged) functions in the HAL_UART_Init()
138     and HAL_UART_DeInit() only when these callbacks are null (not registered beforehand).
139     If not, MspInit or MspDeInit are not null, the HAL_UART_Init() and HAL_UART_DeInit()
140     keep and use the user MspInit/MspDeInit callbacks (registered beforehand).
141 
142     [..]
143     Callbacks can be registered/unregistered in HAL_UART_STATE_READY state only.
144     Exception done MspInit/MspDeInit that can be registered/unregistered
145     in HAL_UART_STATE_READY or HAL_UART_STATE_RESET state, thus registered (user)
146     MspInit/DeInit callbacks can be used during the Init/DeInit.
147     In that case first register the MspInit/MspDeInit user callbacks
148     using HAL_UART_RegisterCallback() before calling HAL_UART_DeInit()
149     or HAL_UART_Init() function.
150 
151     [..]
152     When The compilation define USE_HAL_UART_REGISTER_CALLBACKS is set to 0 or
153     not defined, the callback registration feature is not available
154     and weak (surcharged) callbacks are used.
155 
156 
157   @endverbatim
158   ******************************************************************************
159   */
160 
161 /* Includes ------------------------------------------------------------------*/
162 #include "stm32l5xx_hal.h"
163 
164 /** @addtogroup STM32L5xx_HAL_Driver
165   * @{
166   */
167 
168 /** @defgroup UART UART
169   * @brief HAL UART module driver
170   * @{
171   */
172 
173 #ifdef HAL_UART_MODULE_ENABLED
174 
175 /* Private typedef -----------------------------------------------------------*/
176 /* Private define ------------------------------------------------------------*/
177 /** @defgroup UART_Private_Constants UART Private Constants
178   * @{
179   */
180 #define USART_CR1_FIELDS  ((uint32_t)(USART_CR1_M | USART_CR1_PCE | USART_CR1_PS | USART_CR1_TE | USART_CR1_RE | \
181                                       USART_CR1_OVER8 | USART_CR1_FIFOEN)) /*!< UART or USART CR1 fields of parameters set by UART_SetConfig API */
182 
183 #define USART_CR3_FIELDS  ((uint32_t)(USART_CR3_RTSE | USART_CR3_CTSE | USART_CR3_ONEBIT | USART_CR3_TXFTCFG | \
184                                       USART_CR3_RXFTCFG)) /*!< UART or USART CR3 fields of parameters set by UART_SetConfig API */
185 
186 #define LPUART_BRR_MIN  0x00000300U  /* LPUART BRR minimum authorized value */
187 #define LPUART_BRR_MAX  0x000FFFFFU  /* LPUART BRR maximum authorized value */
188 
189 #define UART_BRR_MIN    0x10U        /* UART BRR minimum authorized value */
190 #define UART_BRR_MAX    0x0000FFFFU  /* UART BRR maximum authorized value */
191 /**
192   * @}
193   */
194 
195 /* Private macros ------------------------------------------------------------*/
196 /* Private function prototypes -----------------------------------------------*/
197 /** @addtogroup UART_Private_Functions
198   * @{
199   */
200 static void UART_EndTxTransfer(UART_HandleTypeDef *huart);
201 static void UART_EndRxTransfer(UART_HandleTypeDef *huart);
202 static void UART_DMATransmitCplt(DMA_HandleTypeDef *hdma);
203 static void UART_DMAReceiveCplt(DMA_HandleTypeDef *hdma);
204 static void UART_DMARxHalfCplt(DMA_HandleTypeDef *hdma);
205 static void UART_DMATxHalfCplt(DMA_HandleTypeDef *hdma);
206 static void UART_DMAError(DMA_HandleTypeDef *hdma);
207 static void UART_DMAAbortOnError(DMA_HandleTypeDef *hdma);
208 static void UART_DMATxAbortCallback(DMA_HandleTypeDef *hdma);
209 static void UART_DMARxAbortCallback(DMA_HandleTypeDef *hdma);
210 static void UART_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
211 static void UART_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma);
212 static void UART_TxISR_8BIT(UART_HandleTypeDef *huart);
213 static void UART_TxISR_16BIT(UART_HandleTypeDef *huart);
214 static void UART_TxISR_8BIT_FIFOEN(UART_HandleTypeDef *huart);
215 static void UART_TxISR_16BIT_FIFOEN(UART_HandleTypeDef *huart);
216 static void UART_EndTransmit_IT(UART_HandleTypeDef *huart);
217 static void UART_RxISR_8BIT(UART_HandleTypeDef *huart);
218 static void UART_RxISR_16BIT(UART_HandleTypeDef *huart);
219 static void UART_RxISR_8BIT_FIFOEN(UART_HandleTypeDef *huart);
220 static void UART_RxISR_16BIT_FIFOEN(UART_HandleTypeDef *huart);
221 /**
222   * @}
223   */
224 
225 /* Private variables ---------------------------------------------------------*/
226 /** @addtogroup UART_Private_variables
227   * @{
228   */
229 const uint16_t UARTPrescTable[12] = {1U, 2U, 4U, 6U, 8U, 10U, 12U, 16U, 32U, 64U, 128U, 256U};
230 /**
231   * @}
232   */
233 
234 /* Exported Constants --------------------------------------------------------*/
235 /* Exported functions --------------------------------------------------------*/
236 
237 /** @defgroup UART_Exported_Functions UART Exported Functions
238   * @{
239   */
240 
241 /** @defgroup UART_Exported_Functions_Group1 Initialization and de-initialization functions
242   *  @brief    Initialization and Configuration functions
243   *
244 @verbatim
245 ===============================================================================
246             ##### Initialization and Configuration functions #####
247  ===============================================================================
248     [..]
249     This subsection provides a set of functions allowing to initialize the USARTx or the UARTy
250     in asynchronous mode.
251       (+) For the asynchronous mode the parameters below can be configured:
252         (++) Baud Rate
253         (++) Word Length
254         (++) Stop Bit
255         (++) Parity: If the parity is enabled, then the MSB bit of the data written
256              in the data register is transmitted but is changed by the parity bit.
257         (++) Hardware flow control
258         (++) Receiver/transmitter modes
259         (++) Over Sampling Method
260         (++) One-Bit Sampling Method
261       (+) For the asynchronous mode, the following advanced features can be configured as well:
262         (++) TX and/or RX pin level inversion
263         (++) data logical level inversion
264         (++) RX and TX pins swap
265         (++) RX overrun detection disabling
266         (++) DMA disabling on RX error
267         (++) MSB first on communication line
268         (++) auto Baud rate detection
269     [..]
270     The HAL_UART_Init(), HAL_HalfDuplex_Init(), HAL_LIN_Init()and HAL_MultiProcessor_Init()API
271     follow respectively the UART asynchronous, UART Half duplex, UART LIN mode
272     and UART multiprocessor mode configuration procedures (details for the procedures
273     are available in reference manual).
274 
275 @endverbatim
276 
277   Depending on the frame length defined by the M1 and M0 bits (7-bit,
278   8-bit or 9-bit), the possible UART formats are listed in the
279   following table.
280 
281   Table 1. UART frame format.
282     +-----------------------------------------------------------------------+
283     |  M1 bit |  M0 bit |  PCE bit  |             UART frame                |
284     |---------|---------|-----------|---------------------------------------|
285     |    0    |    0    |    0      |    | SB |    8 bit data   | STB |     |
286     |---------|---------|-----------|---------------------------------------|
287     |    0    |    0    |    1      |    | SB | 7 bit data | PB | STB |     |
288     |---------|---------|-----------|---------------------------------------|
289     |    0    |    1    |    0      |    | SB |    9 bit data   | STB |     |
290     |---------|---------|-----------|---------------------------------------|
291     |    0    |    1    |    1      |    | SB | 8 bit data | PB | STB |     |
292     |---------|---------|-----------|---------------------------------------|
293     |    1    |    0    |    0      |    | SB |    7 bit data   | STB |     |
294     |---------|---------|-----------|---------------------------------------|
295     |    1    |    0    |    1      |    | SB | 6 bit data | PB | STB |     |
296     +-----------------------------------------------------------------------+
297 
298   * @{
299   */
300 
301 /**
302   * @brief Initialize the UART mode according to the specified
303   *        parameters in the UART_InitTypeDef and initialize the associated handle.
304   * @param huart UART handle.
305   * @retval HAL status
306   */
HAL_UART_Init(UART_HandleTypeDef * huart)307 HAL_StatusTypeDef HAL_UART_Init(UART_HandleTypeDef *huart)
308 {
309   /* Check the UART handle allocation */
310   if (huart == NULL)
311   {
312     return HAL_ERROR;
313   }
314 
315   if (huart->Init.HwFlowCtl != UART_HWCONTROL_NONE)
316   {
317     /* Check the parameters */
318     assert_param(IS_UART_HWFLOW_INSTANCE(huart->Instance));
319   }
320   else
321   {
322     /* Check the parameters */
323     assert_param((IS_UART_INSTANCE(huart->Instance)) || (IS_LPUART_INSTANCE(huart->Instance)));
324   }
325 
326   if (huart->gState == HAL_UART_STATE_RESET)
327   {
328     /* Allocate lock resource and initialize it */
329     huart->Lock = HAL_UNLOCKED;
330 
331 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
332     UART_InitCallbacksToDefault(huart);
333 
334     if (huart->MspInitCallback == NULL)
335     {
336       huart->MspInitCallback = HAL_UART_MspInit;
337     }
338 
339     /* Init the low level hardware */
340     huart->MspInitCallback(huart);
341 #else
342     /* Init the low level hardware : GPIO, CLOCK */
343     HAL_UART_MspInit(huart);
344 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
345   }
346 
347   huart->gState = HAL_UART_STATE_BUSY;
348 
349   __HAL_UART_DISABLE(huart);
350 
351   /* Set the UART Communication parameters */
352   if (UART_SetConfig(huart) == HAL_ERROR)
353   {
354     return HAL_ERROR;
355   }
356 
357   if (huart->AdvancedInit.AdvFeatureInit != UART_ADVFEATURE_NO_INIT)
358   {
359     UART_AdvFeatureConfig(huart);
360   }
361 
362   /* In asynchronous mode, the following bits must be kept cleared:
363   - LINEN and CLKEN bits in the USART_CR2 register,
364   - SCEN, HDSEL and IREN  bits in the USART_CR3 register.*/
365   CLEAR_BIT(huart->Instance->CR2, (USART_CR2_LINEN | USART_CR2_CLKEN));
366   CLEAR_BIT(huart->Instance->CR3, (USART_CR3_SCEN | USART_CR3_HDSEL | USART_CR3_IREN));
367 
368   __HAL_UART_ENABLE(huart);
369 
370   /* TEACK and/or REACK to check before moving huart->gState and huart->RxState to Ready */
371   return (UART_CheckIdleState(huart));
372 }
373 
374 /**
375   * @brief Initialize the half-duplex mode according to the specified
376   *        parameters in the UART_InitTypeDef and creates the associated handle.
377   * @param huart UART handle.
378   * @retval HAL status
379   */
HAL_HalfDuplex_Init(UART_HandleTypeDef * huart)380 HAL_StatusTypeDef HAL_HalfDuplex_Init(UART_HandleTypeDef *huart)
381 {
382   /* Check the UART handle allocation */
383   if (huart == NULL)
384   {
385     return HAL_ERROR;
386   }
387 
388   /* Check UART instance */
389   assert_param(IS_UART_HALFDUPLEX_INSTANCE(huart->Instance));
390 
391   if (huart->gState == HAL_UART_STATE_RESET)
392   {
393     /* Allocate lock resource and initialize it */
394     huart->Lock = HAL_UNLOCKED;
395 
396 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
397     UART_InitCallbacksToDefault(huart);
398 
399     if (huart->MspInitCallback == NULL)
400     {
401       huart->MspInitCallback = HAL_UART_MspInit;
402     }
403 
404     /* Init the low level hardware */
405     huart->MspInitCallback(huart);
406 #else
407     /* Init the low level hardware : GPIO, CLOCK */
408     HAL_UART_MspInit(huart);
409 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
410   }
411 
412   huart->gState = HAL_UART_STATE_BUSY;
413 
414   __HAL_UART_DISABLE(huart);
415 
416   /* Set the UART Communication parameters */
417   if (UART_SetConfig(huart) == HAL_ERROR)
418   {
419     return HAL_ERROR;
420   }
421 
422   if (huart->AdvancedInit.AdvFeatureInit != UART_ADVFEATURE_NO_INIT)
423   {
424     UART_AdvFeatureConfig(huart);
425   }
426 
427   /* In half-duplex mode, the following bits must be kept cleared:
428   - LINEN and CLKEN bits in the USART_CR2 register,
429   - SCEN and IREN bits in the USART_CR3 register.*/
430   CLEAR_BIT(huart->Instance->CR2, (USART_CR2_LINEN | USART_CR2_CLKEN));
431   CLEAR_BIT(huart->Instance->CR3, (USART_CR3_IREN | USART_CR3_SCEN));
432 
433   /* Enable the Half-Duplex mode by setting the HDSEL bit in the CR3 register */
434   SET_BIT(huart->Instance->CR3, USART_CR3_HDSEL);
435 
436   __HAL_UART_ENABLE(huart);
437 
438   /* TEACK and/or REACK to check before moving huart->gState and huart->RxState to Ready */
439   return (UART_CheckIdleState(huart));
440 }
441 
442 
443 /**
444   * @brief Initialize the LIN mode according to the specified
445   *        parameters in the UART_InitTypeDef and creates the associated handle.
446   * @param huart             UART handle.
447   * @param BreakDetectLength Specifies the LIN break detection length.
448   *        This parameter can be one of the following values:
449   *          @arg @ref UART_LINBREAKDETECTLENGTH_10B 10-bit break detection
450   *          @arg @ref UART_LINBREAKDETECTLENGTH_11B 11-bit break detection
451   * @retval HAL status
452   */
HAL_LIN_Init(UART_HandleTypeDef * huart,uint32_t BreakDetectLength)453 HAL_StatusTypeDef HAL_LIN_Init(UART_HandleTypeDef *huart, uint32_t BreakDetectLength)
454 {
455   /* Check the UART handle allocation */
456   if (huart == NULL)
457   {
458     return HAL_ERROR;
459   }
460 
461   /* Check the LIN UART instance */
462   assert_param(IS_UART_LIN_INSTANCE(huart->Instance));
463   /* Check the Break detection length parameter */
464   assert_param(IS_UART_LIN_BREAK_DETECT_LENGTH(BreakDetectLength));
465 
466   /* LIN mode limited to 16-bit oversampling only */
467   if (huart->Init.OverSampling == UART_OVERSAMPLING_8)
468   {
469     return HAL_ERROR;
470   }
471   /* LIN mode limited to 8-bit data length */
472   if (huart->Init.WordLength != UART_WORDLENGTH_8B)
473   {
474     return HAL_ERROR;
475   }
476 
477   if (huart->gState == HAL_UART_STATE_RESET)
478   {
479     /* Allocate lock resource and initialize it */
480     huart->Lock = HAL_UNLOCKED;
481 
482 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
483     UART_InitCallbacksToDefault(huart);
484 
485     if (huart->MspInitCallback == NULL)
486     {
487       huart->MspInitCallback = HAL_UART_MspInit;
488     }
489 
490     /* Init the low level hardware */
491     huart->MspInitCallback(huart);
492 #else
493     /* Init the low level hardware : GPIO, CLOCK */
494     HAL_UART_MspInit(huart);
495 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
496   }
497 
498   huart->gState = HAL_UART_STATE_BUSY;
499 
500   __HAL_UART_DISABLE(huart);
501 
502   /* Set the UART Communication parameters */
503   if (UART_SetConfig(huart) == HAL_ERROR)
504   {
505     return HAL_ERROR;
506   }
507 
508   if (huart->AdvancedInit.AdvFeatureInit != UART_ADVFEATURE_NO_INIT)
509   {
510     UART_AdvFeatureConfig(huart);
511   }
512 
513   /* In LIN mode, the following bits must be kept cleared:
514   - LINEN and CLKEN bits in the USART_CR2 register,
515   - SCEN and IREN bits in the USART_CR3 register.*/
516   CLEAR_BIT(huart->Instance->CR2, USART_CR2_CLKEN);
517   CLEAR_BIT(huart->Instance->CR3, (USART_CR3_HDSEL | USART_CR3_IREN | USART_CR3_SCEN));
518 
519   /* Enable the LIN mode by setting the LINEN bit in the CR2 register */
520   SET_BIT(huart->Instance->CR2, USART_CR2_LINEN);
521 
522   /* Set the USART LIN Break detection length. */
523   MODIFY_REG(huart->Instance->CR2, USART_CR2_LBDL, BreakDetectLength);
524 
525   __HAL_UART_ENABLE(huart);
526 
527   /* TEACK and/or REACK to check before moving huart->gState and huart->RxState to Ready */
528   return (UART_CheckIdleState(huart));
529 }
530 
531 
532 /**
533   * @brief Initialize the multiprocessor mode according to the specified
534   *        parameters in the UART_InitTypeDef and initialize the associated handle.
535   * @param huart        UART handle.
536   * @param Address      UART node address (4-, 6-, 7- or 8-bit long).
537   * @param WakeUpMethod Specifies the UART wakeup method.
538   *        This parameter can be one of the following values:
539   *          @arg @ref UART_WAKEUPMETHOD_IDLELINE WakeUp by an idle line detection
540   *          @arg @ref UART_WAKEUPMETHOD_ADDRESSMARK WakeUp by an address mark
541   * @note  If the user resorts to idle line detection wake up, the Address parameter
542   *        is useless and ignored by the initialization function.
543   * @note  If the user resorts to address mark wake up, the address length detection
544   *        is configured by default to 4 bits only. For the UART to be able to
545   *        manage 6-, 7- or 8-bit long addresses detection, the API
546   *        HAL_MultiProcessorEx_AddressLength_Set() must be called after
547   *        HAL_MultiProcessor_Init().
548   * @retval HAL status
549   */
HAL_MultiProcessor_Init(UART_HandleTypeDef * huart,uint8_t Address,uint32_t WakeUpMethod)550 HAL_StatusTypeDef HAL_MultiProcessor_Init(UART_HandleTypeDef *huart, uint8_t Address, uint32_t WakeUpMethod)
551 {
552   /* Check the UART handle allocation */
553   if (huart == NULL)
554   {
555     return HAL_ERROR;
556   }
557 
558   /* Check the wake up method parameter */
559   assert_param(IS_UART_WAKEUPMETHOD(WakeUpMethod));
560 
561   if (huart->gState == HAL_UART_STATE_RESET)
562   {
563     /* Allocate lock resource and initialize it */
564     huart->Lock = HAL_UNLOCKED;
565 
566 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
567     UART_InitCallbacksToDefault(huart);
568 
569     if (huart->MspInitCallback == NULL)
570     {
571       huart->MspInitCallback = HAL_UART_MspInit;
572     }
573 
574     /* Init the low level hardware */
575     huart->MspInitCallback(huart);
576 #else
577     /* Init the low level hardware : GPIO, CLOCK */
578     HAL_UART_MspInit(huart);
579 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
580   }
581 
582   huart->gState = HAL_UART_STATE_BUSY;
583 
584   __HAL_UART_DISABLE(huart);
585 
586   /* Set the UART Communication parameters */
587   if (UART_SetConfig(huart) == HAL_ERROR)
588   {
589     return HAL_ERROR;
590   }
591 
592   if (huart->AdvancedInit.AdvFeatureInit != UART_ADVFEATURE_NO_INIT)
593   {
594     UART_AdvFeatureConfig(huart);
595   }
596 
597   /* In multiprocessor mode, the following bits must be kept cleared:
598   - LINEN and CLKEN bits in the USART_CR2 register,
599   - SCEN, HDSEL and IREN  bits in the USART_CR3 register. */
600   CLEAR_BIT(huart->Instance->CR2, (USART_CR2_LINEN | USART_CR2_CLKEN));
601   CLEAR_BIT(huart->Instance->CR3, (USART_CR3_SCEN | USART_CR3_HDSEL | USART_CR3_IREN));
602 
603   if (WakeUpMethod == UART_WAKEUPMETHOD_ADDRESSMARK)
604   {
605     /* If address mark wake up method is chosen, set the USART address node */
606     MODIFY_REG(huart->Instance->CR2, USART_CR2_ADD, ((uint32_t)Address << UART_CR2_ADDRESS_LSB_POS));
607   }
608 
609   /* Set the wake up method by setting the WAKE bit in the CR1 register */
610   MODIFY_REG(huart->Instance->CR1, USART_CR1_WAKE, WakeUpMethod);
611 
612   __HAL_UART_ENABLE(huart);
613 
614   /* TEACK and/or REACK to check before moving huart->gState and huart->RxState to Ready */
615   return (UART_CheckIdleState(huart));
616 }
617 
618 
619 /**
620   * @brief DeInitialize the UART peripheral.
621   * @param huart UART handle.
622   * @retval HAL status
623   */
HAL_UART_DeInit(UART_HandleTypeDef * huart)624 HAL_StatusTypeDef HAL_UART_DeInit(UART_HandleTypeDef *huart)
625 {
626   /* Check the UART handle allocation */
627   if (huart == NULL)
628   {
629     return HAL_ERROR;
630   }
631 
632   /* Check the parameters */
633   assert_param((IS_UART_INSTANCE(huart->Instance)) || (IS_LPUART_INSTANCE(huart->Instance)));
634 
635   huart->gState = HAL_UART_STATE_BUSY;
636 
637   __HAL_UART_DISABLE(huart);
638 
639   huart->Instance->CR1 = 0x0U;
640   huart->Instance->CR2 = 0x0U;
641   huart->Instance->CR3 = 0x0U;
642 
643 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
644   if (huart->MspDeInitCallback == NULL)
645   {
646     huart->MspDeInitCallback = HAL_UART_MspDeInit;
647   }
648   /* DeInit the low level hardware */
649   huart->MspDeInitCallback(huart);
650 #else
651   /* DeInit the low level hardware */
652   HAL_UART_MspDeInit(huart);
653 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
654 
655   huart->ErrorCode = HAL_UART_ERROR_NONE;
656   huart->gState = HAL_UART_STATE_RESET;
657   huart->RxState = HAL_UART_STATE_RESET;
658   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
659   huart->RxEventType = HAL_UART_RXEVENT_TC;
660 
661   __HAL_UNLOCK(huart);
662 
663   return HAL_OK;
664 }
665 
666 /**
667   * @brief Initialize the UART MSP.
668   * @param huart UART handle.
669   * @retval None
670   */
HAL_UART_MspInit(UART_HandleTypeDef * huart)671 __weak void HAL_UART_MspInit(UART_HandleTypeDef *huart)
672 {
673   /* Prevent unused argument(s) compilation warning */
674   UNUSED(huart);
675 
676   /* NOTE : This function should not be modified, when the callback is needed,
677             the HAL_UART_MspInit can be implemented in the user file
678    */
679 }
680 
681 /**
682   * @brief DeInitialize the UART MSP.
683   * @param huart UART handle.
684   * @retval None
685   */
HAL_UART_MspDeInit(UART_HandleTypeDef * huart)686 __weak void HAL_UART_MspDeInit(UART_HandleTypeDef *huart)
687 {
688   /* Prevent unused argument(s) compilation warning */
689   UNUSED(huart);
690 
691   /* NOTE : This function should not be modified, when the callback is needed,
692             the HAL_UART_MspDeInit can be implemented in the user file
693    */
694 }
695 
696 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
697 /**
698   * @brief  Register a User UART Callback
699   *         To be used instead of the weak predefined callback
700   * @note   The HAL_UART_RegisterCallback() may be called before HAL_UART_Init(), HAL_HalfDuplex_Init(),
701   *         HAL_LIN_Init(), HAL_MultiProcessor_Init() or HAL_RS485Ex_Init() in HAL_UART_STATE_RESET to register
702   *         callbacks for HAL_UART_MSPINIT_CB_ID and HAL_UART_MSPDEINIT_CB_ID
703   * @param  huart uart handle
704   * @param  CallbackID ID of the callback to be registered
705   *         This parameter can be one of the following values:
706   *           @arg @ref HAL_UART_TX_HALFCOMPLETE_CB_ID Tx Half Complete Callback ID
707   *           @arg @ref HAL_UART_TX_COMPLETE_CB_ID Tx Complete Callback ID
708   *           @arg @ref HAL_UART_RX_HALFCOMPLETE_CB_ID Rx Half Complete Callback ID
709   *           @arg @ref HAL_UART_RX_COMPLETE_CB_ID Rx Complete Callback ID
710   *           @arg @ref HAL_UART_ERROR_CB_ID Error Callback ID
711   *           @arg @ref HAL_UART_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
712   *           @arg @ref HAL_UART_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
713   *           @arg @ref HAL_UART_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
714   *           @arg @ref HAL_UART_WAKEUP_CB_ID Wakeup Callback ID
715   *           @arg @ref HAL_UART_RX_FIFO_FULL_CB_ID Rx Fifo Full Callback ID
716   *           @arg @ref HAL_UART_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty Callback ID
717   *           @arg @ref HAL_UART_MSPINIT_CB_ID MspInit Callback ID
718   *           @arg @ref HAL_UART_MSPDEINIT_CB_ID MspDeInit Callback ID
719   * @param  pCallback pointer to the Callback function
720   * @retval HAL status
721   */
HAL_UART_RegisterCallback(UART_HandleTypeDef * huart,HAL_UART_CallbackIDTypeDef CallbackID,pUART_CallbackTypeDef pCallback)722 HAL_StatusTypeDef HAL_UART_RegisterCallback(UART_HandleTypeDef *huart, HAL_UART_CallbackIDTypeDef CallbackID,
723                                             pUART_CallbackTypeDef pCallback)
724 {
725   HAL_StatusTypeDef status = HAL_OK;
726 
727   if (pCallback == NULL)
728   {
729     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
730 
731     return HAL_ERROR;
732   }
733 
734   if (huart->gState == HAL_UART_STATE_READY)
735   {
736     switch (CallbackID)
737     {
738       case HAL_UART_TX_HALFCOMPLETE_CB_ID :
739         huart->TxHalfCpltCallback = pCallback;
740         break;
741 
742       case HAL_UART_TX_COMPLETE_CB_ID :
743         huart->TxCpltCallback = pCallback;
744         break;
745 
746       case HAL_UART_RX_HALFCOMPLETE_CB_ID :
747         huart->RxHalfCpltCallback = pCallback;
748         break;
749 
750       case HAL_UART_RX_COMPLETE_CB_ID :
751         huart->RxCpltCallback = pCallback;
752         break;
753 
754       case HAL_UART_ERROR_CB_ID :
755         huart->ErrorCallback = pCallback;
756         break;
757 
758       case HAL_UART_ABORT_COMPLETE_CB_ID :
759         huart->AbortCpltCallback = pCallback;
760         break;
761 
762       case HAL_UART_ABORT_TRANSMIT_COMPLETE_CB_ID :
763         huart->AbortTransmitCpltCallback = pCallback;
764         break;
765 
766       case HAL_UART_ABORT_RECEIVE_COMPLETE_CB_ID :
767         huart->AbortReceiveCpltCallback = pCallback;
768         break;
769 
770       case HAL_UART_WAKEUP_CB_ID :
771         huart->WakeupCallback = pCallback;
772         break;
773 
774       case HAL_UART_RX_FIFO_FULL_CB_ID :
775         huart->RxFifoFullCallback = pCallback;
776         break;
777 
778       case HAL_UART_TX_FIFO_EMPTY_CB_ID :
779         huart->TxFifoEmptyCallback = pCallback;
780         break;
781 
782       case HAL_UART_MSPINIT_CB_ID :
783         huart->MspInitCallback = pCallback;
784         break;
785 
786       case HAL_UART_MSPDEINIT_CB_ID :
787         huart->MspDeInitCallback = pCallback;
788         break;
789 
790       default :
791         huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
792 
793         status =  HAL_ERROR;
794         break;
795     }
796   }
797   else if (huart->gState == HAL_UART_STATE_RESET)
798   {
799     switch (CallbackID)
800     {
801       case HAL_UART_MSPINIT_CB_ID :
802         huart->MspInitCallback = pCallback;
803         break;
804 
805       case HAL_UART_MSPDEINIT_CB_ID :
806         huart->MspDeInitCallback = pCallback;
807         break;
808 
809       default :
810         huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
811 
812         status =  HAL_ERROR;
813         break;
814     }
815   }
816   else
817   {
818     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
819 
820     status =  HAL_ERROR;
821   }
822 
823   return status;
824 }
825 
826 /**
827   * @brief  Unregister an UART Callback
828   *         UART callaback is redirected to the weak predefined callback
829   * @note   The HAL_UART_UnRegisterCallback() may be called before HAL_UART_Init(), HAL_HalfDuplex_Init(),
830   *         HAL_LIN_Init(), HAL_MultiProcessor_Init() or HAL_RS485Ex_Init() in HAL_UART_STATE_RESET to un-register
831   *         callbacks for HAL_UART_MSPINIT_CB_ID and HAL_UART_MSPDEINIT_CB_ID
832   * @param  huart uart handle
833   * @param  CallbackID ID of the callback to be unregistered
834   *         This parameter can be one of the following values:
835   *           @arg @ref HAL_UART_TX_HALFCOMPLETE_CB_ID Tx Half Complete Callback ID
836   *           @arg @ref HAL_UART_TX_COMPLETE_CB_ID Tx Complete Callback ID
837   *           @arg @ref HAL_UART_RX_HALFCOMPLETE_CB_ID Rx Half Complete Callback ID
838   *           @arg @ref HAL_UART_RX_COMPLETE_CB_ID Rx Complete Callback ID
839   *           @arg @ref HAL_UART_ERROR_CB_ID Error Callback ID
840   *           @arg @ref HAL_UART_ABORT_COMPLETE_CB_ID Abort Complete Callback ID
841   *           @arg @ref HAL_UART_ABORT_TRANSMIT_COMPLETE_CB_ID Abort Transmit Complete Callback ID
842   *           @arg @ref HAL_UART_ABORT_RECEIVE_COMPLETE_CB_ID Abort Receive Complete Callback ID
843   *           @arg @ref HAL_UART_WAKEUP_CB_ID Wakeup Callback ID
844   *           @arg @ref HAL_UART_RX_FIFO_FULL_CB_ID Rx Fifo Full Callback ID
845   *           @arg @ref HAL_UART_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty Callback ID
846   *           @arg @ref HAL_UART_MSPINIT_CB_ID MspInit Callback ID
847   *           @arg @ref HAL_UART_MSPDEINIT_CB_ID MspDeInit Callback ID
848   * @retval HAL status
849   */
HAL_UART_UnRegisterCallback(UART_HandleTypeDef * huart,HAL_UART_CallbackIDTypeDef CallbackID)850 HAL_StatusTypeDef HAL_UART_UnRegisterCallback(UART_HandleTypeDef *huart, HAL_UART_CallbackIDTypeDef CallbackID)
851 {
852   HAL_StatusTypeDef status = HAL_OK;
853 
854   if (HAL_UART_STATE_READY == huart->gState)
855   {
856     switch (CallbackID)
857     {
858       case HAL_UART_TX_HALFCOMPLETE_CB_ID :
859         huart->TxHalfCpltCallback = HAL_UART_TxHalfCpltCallback;               /* Legacy weak  TxHalfCpltCallback    */
860         break;
861 
862       case HAL_UART_TX_COMPLETE_CB_ID :
863         huart->TxCpltCallback = HAL_UART_TxCpltCallback;                       /* Legacy weak TxCpltCallback         */
864         break;
865 
866       case HAL_UART_RX_HALFCOMPLETE_CB_ID :
867         huart->RxHalfCpltCallback = HAL_UART_RxHalfCpltCallback;               /* Legacy weak RxHalfCpltCallback     */
868         break;
869 
870       case HAL_UART_RX_COMPLETE_CB_ID :
871         huart->RxCpltCallback = HAL_UART_RxCpltCallback;                       /* Legacy weak RxCpltCallback         */
872         break;
873 
874       case HAL_UART_ERROR_CB_ID :
875         huart->ErrorCallback = HAL_UART_ErrorCallback;                         /* Legacy weak ErrorCallback          */
876         break;
877 
878       case HAL_UART_ABORT_COMPLETE_CB_ID :
879         huart->AbortCpltCallback = HAL_UART_AbortCpltCallback;                 /* Legacy weak AbortCpltCallback      */
880         break;
881 
882       case HAL_UART_ABORT_TRANSMIT_COMPLETE_CB_ID :
883         huart->AbortTransmitCpltCallback = HAL_UART_AbortTransmitCpltCallback; /* Legacy weak
884                                                                                   AbortTransmitCpltCallback          */
885         break;
886 
887       case HAL_UART_ABORT_RECEIVE_COMPLETE_CB_ID :
888         huart->AbortReceiveCpltCallback = HAL_UART_AbortReceiveCpltCallback;   /* Legacy weak
889                                                                                   AbortReceiveCpltCallback           */
890         break;
891 
892       case HAL_UART_WAKEUP_CB_ID :
893         huart->WakeupCallback = HAL_UARTEx_WakeupCallback;                     /* Legacy weak WakeupCallback         */
894         break;
895 
896       case HAL_UART_RX_FIFO_FULL_CB_ID :
897         huart->RxFifoFullCallback = HAL_UARTEx_RxFifoFullCallback;             /* Legacy weak RxFifoFullCallback     */
898         break;
899 
900       case HAL_UART_TX_FIFO_EMPTY_CB_ID :
901         huart->TxFifoEmptyCallback = HAL_UARTEx_TxFifoEmptyCallback;           /* Legacy weak TxFifoEmptyCallback    */
902         break;
903 
904       case HAL_UART_MSPINIT_CB_ID :
905         huart->MspInitCallback = HAL_UART_MspInit;                             /* Legacy weak MspInitCallback        */
906         break;
907 
908       case HAL_UART_MSPDEINIT_CB_ID :
909         huart->MspDeInitCallback = HAL_UART_MspDeInit;                         /* Legacy weak MspDeInitCallback      */
910         break;
911 
912       default :
913         huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
914 
915         status =  HAL_ERROR;
916         break;
917     }
918   }
919   else if (HAL_UART_STATE_RESET == huart->gState)
920   {
921     switch (CallbackID)
922     {
923       case HAL_UART_MSPINIT_CB_ID :
924         huart->MspInitCallback = HAL_UART_MspInit;
925         break;
926 
927       case HAL_UART_MSPDEINIT_CB_ID :
928         huart->MspDeInitCallback = HAL_UART_MspDeInit;
929         break;
930 
931       default :
932         huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
933 
934         status =  HAL_ERROR;
935         break;
936     }
937   }
938   else
939   {
940     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
941 
942     status =  HAL_ERROR;
943   }
944 
945   return status;
946 }
947 
948 /**
949   * @brief  Register a User UART Rx Event Callback
950   *         To be used instead of the weak predefined callback
951   * @param  huart     Uart handle
952   * @param  pCallback Pointer to the Rx Event Callback function
953   * @retval HAL status
954   */
HAL_UART_RegisterRxEventCallback(UART_HandleTypeDef * huart,pUART_RxEventCallbackTypeDef pCallback)955 HAL_StatusTypeDef HAL_UART_RegisterRxEventCallback(UART_HandleTypeDef *huart, pUART_RxEventCallbackTypeDef pCallback)
956 {
957   HAL_StatusTypeDef status = HAL_OK;
958 
959   if (pCallback == NULL)
960   {
961     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
962 
963     return HAL_ERROR;
964   }
965 
966   /* Process locked */
967   __HAL_LOCK(huart);
968 
969   if (huart->gState == HAL_UART_STATE_READY)
970   {
971     huart->RxEventCallback = pCallback;
972   }
973   else
974   {
975     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
976 
977     status =  HAL_ERROR;
978   }
979 
980   /* Release Lock */
981   __HAL_UNLOCK(huart);
982 
983   return status;
984 }
985 
986 /**
987   * @brief  UnRegister the UART Rx Event Callback
988   *         UART Rx Event Callback is redirected to the weak HAL_UARTEx_RxEventCallback() predefined callback
989   * @param  huart     Uart handle
990   * @retval HAL status
991   */
HAL_UART_UnRegisterRxEventCallback(UART_HandleTypeDef * huart)992 HAL_StatusTypeDef HAL_UART_UnRegisterRxEventCallback(UART_HandleTypeDef *huart)
993 {
994   HAL_StatusTypeDef status = HAL_OK;
995 
996   /* Process locked */
997   __HAL_LOCK(huart);
998 
999   if (huart->gState == HAL_UART_STATE_READY)
1000   {
1001     huart->RxEventCallback = HAL_UARTEx_RxEventCallback; /* Legacy weak UART Rx Event Callback  */
1002   }
1003   else
1004   {
1005     huart->ErrorCode |= HAL_UART_ERROR_INVALID_CALLBACK;
1006 
1007     status =  HAL_ERROR;
1008   }
1009 
1010   /* Release Lock */
1011   __HAL_UNLOCK(huart);
1012   return status;
1013 }
1014 
1015 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
1016 
1017 /**
1018   * @}
1019   */
1020 
1021 /** @defgroup UART_Exported_Functions_Group2 IO operation functions
1022   * @brief UART Transmit/Receive functions
1023   *
1024 @verbatim
1025  ===============================================================================
1026                       ##### IO operation functions #####
1027  ===============================================================================
1028     This subsection provides a set of functions allowing to manage the UART asynchronous
1029     and Half duplex data transfers.
1030 
1031     (#) There are two mode of transfer:
1032        (+) Blocking mode: The communication is performed in polling mode.
1033            The HAL status of all data processing is returned by the same function
1034            after finishing transfer.
1035        (+) Non-Blocking mode: The communication is performed using Interrupts
1036            or DMA, These API's return the HAL status.
1037            The end of the data processing will be indicated through the
1038            dedicated UART IRQ when using Interrupt mode or the DMA IRQ when
1039            using DMA mode.
1040            The HAL_UART_TxCpltCallback(), HAL_UART_RxCpltCallback() user callbacks
1041            will be executed respectively at the end of the transmit or Receive process
1042            The HAL_UART_ErrorCallback()user callback will be executed when a communication error is detected
1043 
1044     (#) Blocking mode API's are :
1045         (+) HAL_UART_Transmit()
1046         (+) HAL_UART_Receive()
1047 
1048     (#) Non-Blocking mode API's with Interrupt are :
1049         (+) HAL_UART_Transmit_IT()
1050         (+) HAL_UART_Receive_IT()
1051         (+) HAL_UART_IRQHandler()
1052 
1053     (#) Non-Blocking mode API's with DMA are :
1054         (+) HAL_UART_Transmit_DMA()
1055         (+) HAL_UART_Receive_DMA()
1056         (+) HAL_UART_DMAPause()
1057         (+) HAL_UART_DMAResume()
1058         (+) HAL_UART_DMAStop()
1059 
1060     (#) A set of Transfer Complete Callbacks are provided in Non_Blocking mode:
1061         (+) HAL_UART_TxHalfCpltCallback()
1062         (+) HAL_UART_TxCpltCallback()
1063         (+) HAL_UART_RxHalfCpltCallback()
1064         (+) HAL_UART_RxCpltCallback()
1065         (+) HAL_UART_ErrorCallback()
1066 
1067     (#) Non-Blocking mode transfers could be aborted using Abort API's :
1068         (+) HAL_UART_Abort()
1069         (+) HAL_UART_AbortTransmit()
1070         (+) HAL_UART_AbortReceive()
1071         (+) HAL_UART_Abort_IT()
1072         (+) HAL_UART_AbortTransmit_IT()
1073         (+) HAL_UART_AbortReceive_IT()
1074 
1075     (#) For Abort services based on interrupts (HAL_UART_Abortxxx_IT), a set of Abort Complete Callbacks are provided:
1076         (+) HAL_UART_AbortCpltCallback()
1077         (+) HAL_UART_AbortTransmitCpltCallback()
1078         (+) HAL_UART_AbortReceiveCpltCallback()
1079 
1080     (#) A Rx Event Reception Callback (Rx event notification) is available for Non_Blocking modes of enhanced
1081         reception services:
1082         (+) HAL_UARTEx_RxEventCallback()
1083 
1084     (#) In Non-Blocking mode transfers, possible errors are split into 2 categories.
1085         Errors are handled as follows :
1086        (+) Error is considered as Recoverable and non blocking : Transfer could go till end, but error severity is
1087            to be evaluated by user : this concerns Frame Error, Parity Error or Noise Error
1088            in Interrupt mode reception .
1089            Received character is then retrieved and stored in Rx buffer, Error code is set to allow user
1090            to identify error type, and HAL_UART_ErrorCallback() user callback is executed.
1091            Transfer is kept ongoing on UART side.
1092            If user wants to abort it, Abort services should be called by user.
1093        (+) Error is considered as Blocking : Transfer could not be completed properly and is aborted.
1094            This concerns Overrun Error In Interrupt mode reception and all errors in DMA mode.
1095            Error code is set to allow user to identify error type, and HAL_UART_ErrorCallback()
1096            user callback is executed.
1097 
1098     -@- In the Half duplex communication, it is forbidden to run the transmit
1099         and receive process in parallel, the UART state HAL_UART_STATE_BUSY_TX_RX can't be useful.
1100 
1101 @endverbatim
1102   * @{
1103   */
1104 
1105 /**
1106   * @brief Send an amount of data in blocking mode.
1107   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1108   *         the sent data is handled as a set of u16. In this case, Size must indicate the number
1109   *         of u16 provided through pData.
1110   * @note When FIFO mode is enabled, writing a data in the TDR register adds one
1111   *       data to the TXFIFO. Write operations to the TDR register are performed
1112   *       when TXFNF flag is set. From hardware perspective, TXFNF flag and
1113   *       TXE are mapped on the same bit-field.
1114   * @param huart   UART handle.
1115   * @param pData   Pointer to data buffer (u8 or u16 data elements).
1116   * @param Size    Amount of data elements (u8 or u16) to be sent.
1117   * @param Timeout Timeout duration.
1118   * @retval HAL status
1119   */
HAL_UART_Transmit(UART_HandleTypeDef * huart,const uint8_t * pData,uint16_t Size,uint32_t Timeout)1120 HAL_StatusTypeDef HAL_UART_Transmit(UART_HandleTypeDef *huart, const uint8_t *pData, uint16_t Size, uint32_t Timeout)
1121 {
1122   const uint8_t  *pdata8bits;
1123   const uint16_t *pdata16bits;
1124   uint32_t tickstart;
1125 
1126   /* Check that a Tx process is not already ongoing */
1127   if (huart->gState == HAL_UART_STATE_READY)
1128   {
1129     if ((pData == NULL) || (Size == 0U))
1130     {
1131       return  HAL_ERROR;
1132     }
1133 
1134     huart->ErrorCode = HAL_UART_ERROR_NONE;
1135     huart->gState = HAL_UART_STATE_BUSY_TX;
1136 
1137     /* Init tickstart for timeout management */
1138     tickstart = HAL_GetTick();
1139 
1140     huart->TxXferSize  = Size;
1141     huart->TxXferCount = Size;
1142 
1143     /* In case of 9bits/No Parity transfer, pData needs to be handled as a uint16_t pointer */
1144     if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
1145     {
1146       pdata8bits  = NULL;
1147       pdata16bits = (const uint16_t *) pData;
1148     }
1149     else
1150     {
1151       pdata8bits  = pData;
1152       pdata16bits = NULL;
1153     }
1154 
1155     while (huart->TxXferCount > 0U)
1156     {
1157       if (UART_WaitOnFlagUntilTimeout(huart, UART_FLAG_TXE, RESET, tickstart, Timeout) != HAL_OK)
1158       {
1159 
1160         huart->gState = HAL_UART_STATE_READY;
1161 
1162         return HAL_TIMEOUT;
1163       }
1164       if (pdata8bits == NULL)
1165       {
1166         huart->Instance->TDR = (uint16_t)(*pdata16bits & 0x01FFU);
1167         pdata16bits++;
1168       }
1169       else
1170       {
1171         huart->Instance->TDR = (uint8_t)(*pdata8bits & 0xFFU);
1172         pdata8bits++;
1173       }
1174       huart->TxXferCount--;
1175     }
1176 
1177     if (UART_WaitOnFlagUntilTimeout(huart, UART_FLAG_TC, RESET, tickstart, Timeout) != HAL_OK)
1178     {
1179       huart->gState = HAL_UART_STATE_READY;
1180 
1181       return HAL_TIMEOUT;
1182     }
1183 
1184     /* At end of Tx process, restore huart->gState to Ready */
1185     huart->gState = HAL_UART_STATE_READY;
1186 
1187     return HAL_OK;
1188   }
1189   else
1190   {
1191     return HAL_BUSY;
1192   }
1193 }
1194 
1195 /**
1196   * @brief Receive an amount of data in blocking mode.
1197   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1198   *         the received data is handled as a set of u16. In this case, Size must indicate the number
1199   *         of u16 available through pData.
1200   * @note When FIFO mode is enabled, the RXFNE flag is set as long as the RXFIFO
1201   *       is not empty. Read operations from the RDR register are performed when
1202   *       RXFNE flag is set. From hardware perspective, RXFNE flag and
1203   *       RXNE are mapped on the same bit-field.
1204   * @param huart   UART handle.
1205   * @param pData   Pointer to data buffer (u8 or u16 data elements).
1206   * @param Size    Amount of data elements (u8 or u16) to be received.
1207   * @param Timeout Timeout duration.
1208   * @retval HAL status
1209   */
HAL_UART_Receive(UART_HandleTypeDef * huart,uint8_t * pData,uint16_t Size,uint32_t Timeout)1210 HAL_StatusTypeDef HAL_UART_Receive(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size, uint32_t Timeout)
1211 {
1212   uint8_t  *pdata8bits;
1213   uint16_t *pdata16bits;
1214   uint16_t uhMask;
1215   uint32_t tickstart;
1216 
1217   /* Check that a Rx process is not already ongoing */
1218   if (huart->RxState == HAL_UART_STATE_READY)
1219   {
1220     if ((pData == NULL) || (Size == 0U))
1221     {
1222       return  HAL_ERROR;
1223     }
1224 
1225     huart->ErrorCode = HAL_UART_ERROR_NONE;
1226     huart->RxState = HAL_UART_STATE_BUSY_RX;
1227     huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
1228 
1229     /* Init tickstart for timeout management */
1230     tickstart = HAL_GetTick();
1231 
1232     huart->RxXferSize  = Size;
1233     huart->RxXferCount = Size;
1234 
1235     /* Computation of UART mask to apply to RDR register */
1236     UART_MASK_COMPUTATION(huart);
1237     uhMask = huart->Mask;
1238 
1239     /* In case of 9bits/No Parity transfer, pRxData needs to be handled as a uint16_t pointer */
1240     if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
1241     {
1242       pdata8bits  = NULL;
1243       pdata16bits = (uint16_t *) pData;
1244     }
1245     else
1246     {
1247       pdata8bits  = pData;
1248       pdata16bits = NULL;
1249     }
1250 
1251     /* as long as data have to be received */
1252     while (huart->RxXferCount > 0U)
1253     {
1254       if (UART_WaitOnFlagUntilTimeout(huart, UART_FLAG_RXNE, RESET, tickstart, Timeout) != HAL_OK)
1255       {
1256         huart->RxState = HAL_UART_STATE_READY;
1257 
1258         return HAL_TIMEOUT;
1259       }
1260       if (pdata8bits == NULL)
1261       {
1262         *pdata16bits = (uint16_t)(huart->Instance->RDR & uhMask);
1263         pdata16bits++;
1264       }
1265       else
1266       {
1267         *pdata8bits = (uint8_t)(huart->Instance->RDR & (uint8_t)uhMask);
1268         pdata8bits++;
1269       }
1270       huart->RxXferCount--;
1271     }
1272 
1273     /* At end of Rx process, restore huart->RxState to Ready */
1274     huart->RxState = HAL_UART_STATE_READY;
1275 
1276     return HAL_OK;
1277   }
1278   else
1279   {
1280     return HAL_BUSY;
1281   }
1282 }
1283 
1284 /**
1285   * @brief Send an amount of data in interrupt mode.
1286   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1287   *         the sent data is handled as a set of u16. In this case, Size must indicate the number
1288   *         of u16 provided through pData.
1289   * @param huart UART handle.
1290   * @param pData Pointer to data buffer (u8 or u16 data elements).
1291   * @param Size  Amount of data elements (u8 or u16) to be sent.
1292   * @retval HAL status
1293   */
HAL_UART_Transmit_IT(UART_HandleTypeDef * huart,const uint8_t * pData,uint16_t Size)1294 HAL_StatusTypeDef HAL_UART_Transmit_IT(UART_HandleTypeDef *huart, const uint8_t *pData, uint16_t Size)
1295 {
1296   /* Check that a Tx process is not already ongoing */
1297   if (huart->gState == HAL_UART_STATE_READY)
1298   {
1299     if ((pData == NULL) || (Size == 0U))
1300     {
1301       return HAL_ERROR;
1302     }
1303 
1304     huart->pTxBuffPtr  = pData;
1305     huart->TxXferSize  = Size;
1306     huart->TxXferCount = Size;
1307     huart->TxISR       = NULL;
1308 
1309     huart->ErrorCode = HAL_UART_ERROR_NONE;
1310     huart->gState = HAL_UART_STATE_BUSY_TX;
1311 
1312     /* Configure Tx interrupt processing */
1313     if (huart->FifoMode == UART_FIFOMODE_ENABLE)
1314     {
1315       /* Set the Tx ISR function pointer according to the data word length */
1316       if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
1317       {
1318         huart->TxISR = UART_TxISR_16BIT_FIFOEN;
1319       }
1320       else
1321       {
1322         huart->TxISR = UART_TxISR_8BIT_FIFOEN;
1323       }
1324 
1325       /* Enable the TX FIFO threshold interrupt */
1326       ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_TXFTIE);
1327     }
1328     else
1329     {
1330       /* Set the Tx ISR function pointer according to the data word length */
1331       if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
1332       {
1333         huart->TxISR = UART_TxISR_16BIT;
1334       }
1335       else
1336       {
1337         huart->TxISR = UART_TxISR_8BIT;
1338       }
1339 
1340       /* Enable the Transmit Data Register Empty interrupt */
1341       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
1342     }
1343 
1344     return HAL_OK;
1345   }
1346   else
1347   {
1348     return HAL_BUSY;
1349   }
1350 }
1351 
1352 /**
1353   * @brief Receive an amount of data in interrupt mode.
1354   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1355   *         the received data is handled as a set of u16. In this case, Size must indicate the number
1356   *         of u16 available through pData.
1357   * @param huart UART handle.
1358   * @param pData Pointer to data buffer (u8 or u16 data elements).
1359   * @param Size  Amount of data elements (u8 or u16) to be received.
1360   * @retval HAL status
1361   */
HAL_UART_Receive_IT(UART_HandleTypeDef * huart,uint8_t * pData,uint16_t Size)1362 HAL_StatusTypeDef HAL_UART_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
1363 {
1364   /* Check that a Rx process is not already ongoing */
1365   if (huart->RxState == HAL_UART_STATE_READY)
1366   {
1367     if ((pData == NULL) || (Size == 0U))
1368     {
1369       return HAL_ERROR;
1370     }
1371 
1372     /* Set Reception type to Standard reception */
1373     huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
1374 
1375     if (!(IS_LPUART_INSTANCE(huart->Instance)))
1376     {
1377       /* Check that USART RTOEN bit is set */
1378       if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
1379       {
1380         /* Enable the UART Receiver Timeout Interrupt */
1381         ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
1382       }
1383     }
1384 
1385     return (UART_Start_Receive_IT(huart, pData, Size));
1386   }
1387   else
1388   {
1389     return HAL_BUSY;
1390   }
1391 }
1392 
1393 /**
1394   * @brief Send an amount of data in DMA mode.
1395   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1396   *         the sent data is handled as a set of u16. In this case, Size must indicate the number
1397   *         of u16 provided through pData.
1398   * @param huart UART handle.
1399   * @param pData Pointer to data buffer (u8 or u16 data elements).
1400   * @param Size  Amount of data elements (u8 or u16) to be sent.
1401   * @retval HAL status
1402   */
HAL_UART_Transmit_DMA(UART_HandleTypeDef * huart,const uint8_t * pData,uint16_t Size)1403 HAL_StatusTypeDef HAL_UART_Transmit_DMA(UART_HandleTypeDef *huart, const uint8_t *pData, uint16_t Size)
1404 {
1405   /* Check that a Tx process is not already ongoing */
1406   if (huart->gState == HAL_UART_STATE_READY)
1407   {
1408     if ((pData == NULL) || (Size == 0U))
1409     {
1410       return HAL_ERROR;
1411     }
1412 
1413     huart->pTxBuffPtr  = pData;
1414     huart->TxXferSize  = Size;
1415     huart->TxXferCount = Size;
1416 
1417     huart->ErrorCode = HAL_UART_ERROR_NONE;
1418     huart->gState = HAL_UART_STATE_BUSY_TX;
1419 
1420     if (huart->hdmatx != NULL)
1421     {
1422       /* Set the UART DMA transfer complete callback */
1423       huart->hdmatx->XferCpltCallback = UART_DMATransmitCplt;
1424 
1425       /* Set the UART DMA Half transfer complete callback */
1426       huart->hdmatx->XferHalfCpltCallback = UART_DMATxHalfCplt;
1427 
1428       /* Set the DMA error callback */
1429       huart->hdmatx->XferErrorCallback = UART_DMAError;
1430 
1431       /* Set the DMA abort callback */
1432       huart->hdmatx->XferAbortCallback = NULL;
1433 
1434       /* Enable the UART transmit DMA channel */
1435       if (HAL_DMA_Start_IT(huart->hdmatx, (uint32_t)huart->pTxBuffPtr, (uint32_t)&huart->Instance->TDR, Size) != HAL_OK)
1436       {
1437         /* Set error code to DMA */
1438         huart->ErrorCode = HAL_UART_ERROR_DMA;
1439 
1440         /* Restore huart->gState to ready */
1441         huart->gState = HAL_UART_STATE_READY;
1442 
1443         return HAL_ERROR;
1444       }
1445     }
1446     /* Clear the TC flag in the ICR register */
1447     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_TCF);
1448 
1449     /* Enable the DMA transfer for transmit request by setting the DMAT bit
1450     in the UART CR3 register */
1451     ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1452 
1453     return HAL_OK;
1454   }
1455   else
1456   {
1457     return HAL_BUSY;
1458   }
1459 }
1460 
1461 /**
1462   * @brief Receive an amount of data in DMA mode.
1463   * @note   When the UART parity is enabled (PCE = 1), the received data contain
1464   *         the parity bit (MSB position).
1465   * @note   When UART parity is not enabled (PCE = 0), and Word Length is configured to 9 bits (M1-M0 = 01),
1466   *         the received data is handled as a set of u16. In this case, Size must indicate the number
1467   *         of u16 available through pData.
1468   * @param huart UART handle.
1469   * @param pData Pointer to data buffer (u8 or u16 data elements).
1470   * @param Size  Amount of data elements (u8 or u16) to be received.
1471   * @retval HAL status
1472   */
HAL_UART_Receive_DMA(UART_HandleTypeDef * huart,uint8_t * pData,uint16_t Size)1473 HAL_StatusTypeDef HAL_UART_Receive_DMA(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
1474 {
1475   /* Check that a Rx process is not already ongoing */
1476   if (huart->RxState == HAL_UART_STATE_READY)
1477   {
1478     if ((pData == NULL) || (Size == 0U))
1479     {
1480       return HAL_ERROR;
1481     }
1482 
1483     /* Set Reception type to Standard reception */
1484     huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
1485 
1486     if (!(IS_LPUART_INSTANCE(huart->Instance)))
1487     {
1488       /* Check that USART RTOEN bit is set */
1489       if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
1490       {
1491         /* Enable the UART Receiver Timeout Interrupt */
1492         ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
1493       }
1494     }
1495 
1496     return (UART_Start_Receive_DMA(huart, pData, Size));
1497   }
1498   else
1499   {
1500     return HAL_BUSY;
1501   }
1502 }
1503 
1504 /**
1505   * @brief Pause the DMA Transfer.
1506   * @param huart UART handle.
1507   * @retval HAL status
1508   */
HAL_UART_DMAPause(UART_HandleTypeDef * huart)1509 HAL_StatusTypeDef HAL_UART_DMAPause(UART_HandleTypeDef *huart)
1510 {
1511   const HAL_UART_StateTypeDef gstate = huart->gState;
1512   const HAL_UART_StateTypeDef rxstate = huart->RxState;
1513 
1514   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT)) &&
1515       (gstate == HAL_UART_STATE_BUSY_TX))
1516   {
1517     /* Disable the UART DMA Tx request */
1518     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1519   }
1520   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR)) &&
1521       (rxstate == HAL_UART_STATE_BUSY_RX))
1522   {
1523     /* Disable PE and ERR (Frame error, noise error, overrun error) interrupts */
1524     ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_PEIE);
1525     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
1526 
1527     /* Disable the UART DMA Rx request */
1528     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1529   }
1530 
1531   return HAL_OK;
1532 }
1533 
1534 /**
1535   * @brief Resume the DMA Transfer.
1536   * @param huart UART handle.
1537   * @retval HAL status
1538   */
HAL_UART_DMAResume(UART_HandleTypeDef * huart)1539 HAL_StatusTypeDef HAL_UART_DMAResume(UART_HandleTypeDef *huart)
1540 {
1541   if (huart->gState == HAL_UART_STATE_BUSY_TX)
1542   {
1543     /* Enable the UART DMA Tx request */
1544     ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1545   }
1546   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
1547   {
1548     /* Clear the Overrun flag before resuming the Rx transfer */
1549     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF);
1550 
1551     /* Re-enable PE and ERR (Frame error, noise error, overrun error) interrupts */
1552     if (huart->Init.Parity != UART_PARITY_NONE)
1553     {
1554       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_PEIE);
1555     }
1556     ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_EIE);
1557 
1558     /* Enable the UART DMA Rx request */
1559     ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1560   }
1561 
1562   return HAL_OK;
1563 }
1564 
1565 /**
1566   * @brief Stop the DMA Transfer.
1567   * @param huart UART handle.
1568   * @retval HAL status
1569   */
HAL_UART_DMAStop(UART_HandleTypeDef * huart)1570 HAL_StatusTypeDef HAL_UART_DMAStop(UART_HandleTypeDef *huart)
1571 {
1572   /* The Lock is not implemented on this API to allow the user application
1573      to call the HAL UART API under callbacks HAL_UART_TxCpltCallback() / HAL_UART_RxCpltCallback() /
1574      HAL_UART_TxHalfCpltCallback / HAL_UART_RxHalfCpltCallback:
1575      indeed, when HAL_DMA_Abort() API is called, the DMA TX/RX Transfer or Half Transfer complete
1576      interrupt is generated if the DMA transfer interruption occurs at the middle or at the end of
1577      the stream and the corresponding call back is executed. */
1578 
1579   const HAL_UART_StateTypeDef gstate = huart->gState;
1580   const HAL_UART_StateTypeDef rxstate = huart->RxState;
1581 
1582   /* Stop UART DMA Tx request if ongoing */
1583   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT)) &&
1584       (gstate == HAL_UART_STATE_BUSY_TX))
1585   {
1586     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1587 
1588     /* Abort the UART DMA Tx channel */
1589     if (huart->hdmatx != NULL)
1590     {
1591       if (HAL_DMA_Abort(huart->hdmatx) != HAL_OK)
1592       {
1593         if (HAL_DMA_GetError(huart->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
1594         {
1595           /* Set error code to DMA */
1596           huart->ErrorCode = HAL_UART_ERROR_DMA;
1597 
1598           return HAL_TIMEOUT;
1599         }
1600       }
1601     }
1602 
1603     UART_EndTxTransfer(huart);
1604   }
1605 
1606   /* Stop UART DMA Rx request if ongoing */
1607   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR)) &&
1608       (rxstate == HAL_UART_STATE_BUSY_RX))
1609   {
1610     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1611 
1612     /* Abort the UART DMA Rx channel */
1613     if (huart->hdmarx != NULL)
1614     {
1615       if (HAL_DMA_Abort(huart->hdmarx) != HAL_OK)
1616       {
1617         if (HAL_DMA_GetError(huart->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
1618         {
1619           /* Set error code to DMA */
1620           huart->ErrorCode = HAL_UART_ERROR_DMA;
1621 
1622           return HAL_TIMEOUT;
1623         }
1624       }
1625     }
1626 
1627     UART_EndRxTransfer(huart);
1628   }
1629 
1630   return HAL_OK;
1631 }
1632 
1633 /**
1634   * @brief  Abort ongoing transfers (blocking mode).
1635   * @param  huart UART handle.
1636   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1637   *         This procedure performs following operations :
1638   *           - Disable UART Interrupts (Tx and Rx)
1639   *           - Disable the DMA transfer in the peripheral register (if enabled)
1640   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1641   *           - Set handle State to READY
1642   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1643   * @retval HAL status
1644   */
HAL_UART_Abort(UART_HandleTypeDef * huart)1645 HAL_StatusTypeDef HAL_UART_Abort(UART_HandleTypeDef *huart)
1646 {
1647   /* Disable TXE, TC, RXNE, PE, RXFT, TXFT and ERR (Frame error, noise error, overrun error) interrupts */
1648   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE |
1649                                           USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE));
1650   ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE | USART_CR3_RXFTIE | USART_CR3_TXFTIE);
1651 
1652   /* If Reception till IDLE event was ongoing, disable IDLEIE interrupt */
1653   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
1654   {
1655     ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_IDLEIE));
1656   }
1657 
1658   /* Abort the UART DMA Tx channel if enabled */
1659   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT))
1660   {
1661     /* Disable the UART DMA Tx request if enabled */
1662     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1663 
1664     /* Abort the UART DMA Tx channel : use blocking DMA Abort API (no callback) */
1665     if (huart->hdmatx != NULL)
1666     {
1667       /* Set the UART DMA Abort callback to Null.
1668          No call back execution at end of DMA abort procedure */
1669       huart->hdmatx->XferAbortCallback = NULL;
1670 
1671       if (HAL_DMA_Abort(huart->hdmatx) != HAL_OK)
1672       {
1673         if (HAL_DMA_GetError(huart->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
1674         {
1675           /* Set error code to DMA */
1676           huart->ErrorCode = HAL_UART_ERROR_DMA;
1677 
1678           return HAL_TIMEOUT;
1679         }
1680       }
1681     }
1682   }
1683 
1684   /* Abort the UART DMA Rx channel if enabled */
1685   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
1686   {
1687     /* Disable the UART DMA Rx request if enabled */
1688     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1689 
1690     /* Abort the UART DMA Rx channel : use blocking DMA Abort API (no callback) */
1691     if (huart->hdmarx != NULL)
1692     {
1693       /* Set the UART DMA Abort callback to Null.
1694          No call back execution at end of DMA abort procedure */
1695       huart->hdmarx->XferAbortCallback = NULL;
1696 
1697       if (HAL_DMA_Abort(huart->hdmarx) != HAL_OK)
1698       {
1699         if (HAL_DMA_GetError(huart->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
1700         {
1701           /* Set error code to DMA */
1702           huart->ErrorCode = HAL_UART_ERROR_DMA;
1703 
1704           return HAL_TIMEOUT;
1705         }
1706       }
1707     }
1708   }
1709 
1710   /* Reset Tx and Rx transfer counters */
1711   huart->TxXferCount = 0U;
1712   huart->RxXferCount = 0U;
1713 
1714   /* Clear the Error flags in the ICR register */
1715   __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
1716 
1717   /* Flush the whole TX FIFO (if needed) */
1718   if (huart->FifoMode == UART_FIFOMODE_ENABLE)
1719   {
1720     __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
1721   }
1722 
1723   /* Discard the received data */
1724   __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
1725 
1726   /* Restore huart->gState and huart->RxState to Ready */
1727   huart->gState  = HAL_UART_STATE_READY;
1728   huart->RxState = HAL_UART_STATE_READY;
1729   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
1730 
1731   huart->ErrorCode = HAL_UART_ERROR_NONE;
1732 
1733   return HAL_OK;
1734 }
1735 
1736 /**
1737   * @brief  Abort ongoing Transmit transfer (blocking mode).
1738   * @param  huart UART handle.
1739   * @note   This procedure could be used for aborting any ongoing Tx transfer started in Interrupt or DMA mode.
1740   *         This procedure performs following operations :
1741   *           - Disable UART Interrupts (Tx)
1742   *           - Disable the DMA transfer in the peripheral register (if enabled)
1743   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1744   *           - Set handle State to READY
1745   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1746   * @retval HAL status
1747   */
HAL_UART_AbortTransmit(UART_HandleTypeDef * huart)1748 HAL_StatusTypeDef HAL_UART_AbortTransmit(UART_HandleTypeDef *huart)
1749 {
1750   /* Disable TCIE, TXEIE and TXFTIE interrupts */
1751   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TCIE | USART_CR1_TXEIE_TXFNFIE));
1752   ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_TXFTIE);
1753 
1754   /* Abort the UART DMA Tx channel if enabled */
1755   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT))
1756   {
1757     /* Disable the UART DMA Tx request if enabled */
1758     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1759 
1760     /* Abort the UART DMA Tx channel : use blocking DMA Abort API (no callback) */
1761     if (huart->hdmatx != NULL)
1762     {
1763       /* Set the UART DMA Abort callback to Null.
1764          No call back execution at end of DMA abort procedure */
1765       huart->hdmatx->XferAbortCallback = NULL;
1766 
1767       if (HAL_DMA_Abort(huart->hdmatx) != HAL_OK)
1768       {
1769         if (HAL_DMA_GetError(huart->hdmatx) == HAL_DMA_ERROR_TIMEOUT)
1770         {
1771           /* Set error code to DMA */
1772           huart->ErrorCode = HAL_UART_ERROR_DMA;
1773 
1774           return HAL_TIMEOUT;
1775         }
1776       }
1777     }
1778   }
1779 
1780   /* Reset Tx transfer counter */
1781   huart->TxXferCount = 0U;
1782 
1783   /* Flush the whole TX FIFO (if needed) */
1784   if (huart->FifoMode == UART_FIFOMODE_ENABLE)
1785   {
1786     __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
1787   }
1788 
1789   /* Restore huart->gState to Ready */
1790   huart->gState = HAL_UART_STATE_READY;
1791 
1792   return HAL_OK;
1793 }
1794 
1795 /**
1796   * @brief  Abort ongoing Receive transfer (blocking mode).
1797   * @param  huart UART handle.
1798   * @note   This procedure could be used for aborting any ongoing Rx transfer started in Interrupt or DMA mode.
1799   *         This procedure performs following operations :
1800   *           - Disable UART Interrupts (Rx)
1801   *           - Disable the DMA transfer in the peripheral register (if enabled)
1802   *           - Abort DMA transfer by calling HAL_DMA_Abort (in case of transfer in DMA mode)
1803   *           - Set handle State to READY
1804   * @note   This procedure is executed in blocking mode : when exiting function, Abort is considered as completed.
1805   * @retval HAL status
1806   */
HAL_UART_AbortReceive(UART_HandleTypeDef * huart)1807 HAL_StatusTypeDef HAL_UART_AbortReceive(UART_HandleTypeDef *huart)
1808 {
1809   /* Disable PEIE, EIE, RXNEIE and RXFTIE interrupts */
1810   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_PEIE | USART_CR1_RXNEIE_RXFNEIE));
1811   ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE | USART_CR3_RXFTIE);
1812 
1813   /* If Reception till IDLE event was ongoing, disable IDLEIE interrupt */
1814   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
1815   {
1816     ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_IDLEIE));
1817   }
1818 
1819   /* Abort the UART DMA Rx channel if enabled */
1820   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
1821   {
1822     /* Disable the UART DMA Rx request if enabled */
1823     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1824 
1825     /* Abort the UART DMA Rx channel : use blocking DMA Abort API (no callback) */
1826     if (huart->hdmarx != NULL)
1827     {
1828       /* Set the UART DMA Abort callback to Null.
1829          No call back execution at end of DMA abort procedure */
1830       huart->hdmarx->XferAbortCallback = NULL;
1831 
1832       if (HAL_DMA_Abort(huart->hdmarx) != HAL_OK)
1833       {
1834         if (HAL_DMA_GetError(huart->hdmarx) == HAL_DMA_ERROR_TIMEOUT)
1835         {
1836           /* Set error code to DMA */
1837           huart->ErrorCode = HAL_UART_ERROR_DMA;
1838 
1839           return HAL_TIMEOUT;
1840         }
1841       }
1842     }
1843   }
1844 
1845   /* Reset Rx transfer counter */
1846   huart->RxXferCount = 0U;
1847 
1848   /* Clear the Error flags in the ICR register */
1849   __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
1850 
1851   /* Discard the received data */
1852   __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
1853 
1854   /* Restore huart->RxState to Ready */
1855   huart->RxState = HAL_UART_STATE_READY;
1856   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
1857 
1858   return HAL_OK;
1859 }
1860 
1861 /**
1862   * @brief  Abort ongoing transfers (Interrupt mode).
1863   * @param  huart UART handle.
1864   * @note   This procedure could be used for aborting any ongoing transfer started in Interrupt or DMA mode.
1865   *         This procedure performs following operations :
1866   *           - Disable UART Interrupts (Tx and Rx)
1867   *           - Disable the DMA transfer in the peripheral register (if enabled)
1868   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
1869   *           - Set handle State to READY
1870   *           - At abort completion, call user abort complete callback
1871   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
1872   *         considered as completed only when user abort complete callback is executed (not when exiting function).
1873   * @retval HAL status
1874   */
HAL_UART_Abort_IT(UART_HandleTypeDef * huart)1875 HAL_StatusTypeDef HAL_UART_Abort_IT(UART_HandleTypeDef *huart)
1876 {
1877   uint32_t abortcplt = 1U;
1878 
1879   /* Disable interrupts */
1880   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_PEIE | USART_CR1_TCIE | USART_CR1_RXNEIE_RXFNEIE |
1881                                           USART_CR1_TXEIE_TXFNFIE));
1882   ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE | USART_CR3_TXFTIE));
1883 
1884   /* If Reception till IDLE event was ongoing, disable IDLEIE interrupt */
1885   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
1886   {
1887     ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_IDLEIE));
1888   }
1889 
1890   /* If DMA Tx and/or DMA Rx Handles are associated to UART Handle, DMA Abort complete callbacks should be initialised
1891      before any call to DMA Abort functions */
1892   /* DMA Tx Handle is valid */
1893   if (huart->hdmatx != NULL)
1894   {
1895     /* Set DMA Abort Complete callback if UART DMA Tx request if enabled.
1896        Otherwise, set it to NULL */
1897     if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT))
1898     {
1899       huart->hdmatx->XferAbortCallback = UART_DMATxAbortCallback;
1900     }
1901     else
1902     {
1903       huart->hdmatx->XferAbortCallback = NULL;
1904     }
1905   }
1906   /* DMA Rx Handle is valid */
1907   if (huart->hdmarx != NULL)
1908   {
1909     /* Set DMA Abort Complete callback if UART DMA Rx request if enabled.
1910        Otherwise, set it to NULL */
1911     if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
1912     {
1913       huart->hdmarx->XferAbortCallback = UART_DMARxAbortCallback;
1914     }
1915     else
1916     {
1917       huart->hdmarx->XferAbortCallback = NULL;
1918     }
1919   }
1920 
1921   /* Abort the UART DMA Tx channel if enabled */
1922   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT))
1923   {
1924     /* Disable DMA Tx at UART level */
1925     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
1926 
1927     /* Abort the UART DMA Tx channel : use non blocking DMA Abort API (callback) */
1928     if (huart->hdmatx != NULL)
1929     {
1930       /* UART Tx DMA Abort callback has already been initialised :
1931          will lead to call HAL_UART_AbortCpltCallback() at end of DMA abort procedure */
1932 
1933       /* Abort DMA TX */
1934       if (HAL_DMA_Abort_IT(huart->hdmatx) != HAL_OK)
1935       {
1936         huart->hdmatx->XferAbortCallback = NULL;
1937       }
1938       else
1939       {
1940         abortcplt = 0U;
1941       }
1942     }
1943   }
1944 
1945   /* Abort the UART DMA Rx channel if enabled */
1946   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
1947   {
1948     /* Disable the UART DMA Rx request if enabled */
1949     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
1950 
1951     /* Abort the UART DMA Rx channel : use non blocking DMA Abort API (callback) */
1952     if (huart->hdmarx != NULL)
1953     {
1954       /* UART Rx DMA Abort callback has already been initialised :
1955          will lead to call HAL_UART_AbortCpltCallback() at end of DMA abort procedure */
1956 
1957       /* Abort DMA RX */
1958       if (HAL_DMA_Abort_IT(huart->hdmarx) != HAL_OK)
1959       {
1960         huart->hdmarx->XferAbortCallback = NULL;
1961         abortcplt = 1U;
1962       }
1963       else
1964       {
1965         abortcplt = 0U;
1966       }
1967     }
1968   }
1969 
1970   /* if no DMA abort complete callback execution is required => call user Abort Complete callback */
1971   if (abortcplt == 1U)
1972   {
1973     /* Reset Tx and Rx transfer counters */
1974     huart->TxXferCount = 0U;
1975     huart->RxXferCount = 0U;
1976 
1977     /* Clear ISR function pointers */
1978     huart->RxISR = NULL;
1979     huart->TxISR = NULL;
1980 
1981     /* Reset errorCode */
1982     huart->ErrorCode = HAL_UART_ERROR_NONE;
1983 
1984     /* Clear the Error flags in the ICR register */
1985     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
1986 
1987     /* Flush the whole TX FIFO (if needed) */
1988     if (huart->FifoMode == UART_FIFOMODE_ENABLE)
1989     {
1990       __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
1991     }
1992 
1993     /* Discard the received data */
1994     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
1995 
1996     /* Restore huart->gState and huart->RxState to Ready */
1997     huart->gState  = HAL_UART_STATE_READY;
1998     huart->RxState = HAL_UART_STATE_READY;
1999     huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
2000 
2001     /* As no DMA to be aborted, call directly user Abort complete callback */
2002 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2003     /* Call registered Abort complete callback */
2004     huart->AbortCpltCallback(huart);
2005 #else
2006     /* Call legacy weak Abort complete callback */
2007     HAL_UART_AbortCpltCallback(huart);
2008 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2009   }
2010 
2011   return HAL_OK;
2012 }
2013 
2014 /**
2015   * @brief  Abort ongoing Transmit transfer (Interrupt mode).
2016   * @param  huart UART handle.
2017   * @note   This procedure could be used for aborting any ongoing Tx transfer started in Interrupt or DMA mode.
2018   *         This procedure performs following operations :
2019   *           - Disable UART Interrupts (Tx)
2020   *           - Disable the DMA transfer in the peripheral register (if enabled)
2021   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
2022   *           - Set handle State to READY
2023   *           - At abort completion, call user abort complete callback
2024   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
2025   *         considered as completed only when user abort complete callback is executed (not when exiting function).
2026   * @retval HAL status
2027   */
HAL_UART_AbortTransmit_IT(UART_HandleTypeDef * huart)2028 HAL_StatusTypeDef HAL_UART_AbortTransmit_IT(UART_HandleTypeDef *huart)
2029 {
2030   /* Disable interrupts */
2031   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TCIE | USART_CR1_TXEIE_TXFNFIE));
2032   ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_TXFTIE);
2033 
2034   /* Abort the UART DMA Tx channel if enabled */
2035   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT))
2036   {
2037     /* Disable the UART DMA Tx request if enabled */
2038     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
2039 
2040     /* Abort the UART DMA Tx channel : use non blocking DMA Abort API (callback) */
2041     if (huart->hdmatx != NULL)
2042     {
2043       /* Set the UART DMA Abort callback :
2044          will lead to call HAL_UART_AbortCpltCallback() at end of DMA abort procedure */
2045       huart->hdmatx->XferAbortCallback = UART_DMATxOnlyAbortCallback;
2046 
2047       /* Abort DMA TX */
2048       if (HAL_DMA_Abort_IT(huart->hdmatx) != HAL_OK)
2049       {
2050         /* Call Directly huart->hdmatx->XferAbortCallback function in case of error */
2051         huart->hdmatx->XferAbortCallback(huart->hdmatx);
2052       }
2053     }
2054     else
2055     {
2056       /* Reset Tx transfer counter */
2057       huart->TxXferCount = 0U;
2058 
2059       /* Clear TxISR function pointers */
2060       huart->TxISR = NULL;
2061 
2062       /* Restore huart->gState to Ready */
2063       huart->gState = HAL_UART_STATE_READY;
2064 
2065       /* As no DMA to be aborted, call directly user Abort complete callback */
2066 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2067       /* Call registered Abort Transmit Complete Callback */
2068       huart->AbortTransmitCpltCallback(huart);
2069 #else
2070       /* Call legacy weak Abort Transmit Complete Callback */
2071       HAL_UART_AbortTransmitCpltCallback(huart);
2072 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2073     }
2074   }
2075   else
2076   {
2077     /* Reset Tx transfer counter */
2078     huart->TxXferCount = 0U;
2079 
2080     /* Clear TxISR function pointers */
2081     huart->TxISR = NULL;
2082 
2083     /* Flush the whole TX FIFO (if needed) */
2084     if (huart->FifoMode == UART_FIFOMODE_ENABLE)
2085     {
2086       __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
2087     }
2088 
2089     /* Restore huart->gState to Ready */
2090     huart->gState = HAL_UART_STATE_READY;
2091 
2092     /* As no DMA to be aborted, call directly user Abort complete callback */
2093 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2094     /* Call registered Abort Transmit Complete Callback */
2095     huart->AbortTransmitCpltCallback(huart);
2096 #else
2097     /* Call legacy weak Abort Transmit Complete Callback */
2098     HAL_UART_AbortTransmitCpltCallback(huart);
2099 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2100   }
2101 
2102   return HAL_OK;
2103 }
2104 
2105 /**
2106   * @brief  Abort ongoing Receive transfer (Interrupt mode).
2107   * @param  huart UART handle.
2108   * @note   This procedure could be used for aborting any ongoing Rx transfer started in Interrupt or DMA mode.
2109   *         This procedure performs following operations :
2110   *           - Disable UART Interrupts (Rx)
2111   *           - Disable the DMA transfer in the peripheral register (if enabled)
2112   *           - Abort DMA transfer by calling HAL_DMA_Abort_IT (in case of transfer in DMA mode)
2113   *           - Set handle State to READY
2114   *           - At abort completion, call user abort complete callback
2115   * @note   This procedure is executed in Interrupt mode, meaning that abort procedure could be
2116   *         considered as completed only when user abort complete callback is executed (not when exiting function).
2117   * @retval HAL status
2118   */
HAL_UART_AbortReceive_IT(UART_HandleTypeDef * huart)2119 HAL_StatusTypeDef HAL_UART_AbortReceive_IT(UART_HandleTypeDef *huart)
2120 {
2121   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
2122   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_PEIE | USART_CR1_RXNEIE_RXFNEIE));
2123   ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
2124 
2125   /* If Reception till IDLE event was ongoing, disable IDLEIE interrupt */
2126   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
2127   {
2128     ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_IDLEIE));
2129   }
2130 
2131   /* Abort the UART DMA Rx channel if enabled */
2132   if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
2133   {
2134     /* Disable the UART DMA Rx request if enabled */
2135     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
2136 
2137     /* Abort the UART DMA Rx channel : use non blocking DMA Abort API (callback) */
2138     if (huart->hdmarx != NULL)
2139     {
2140       /* Set the UART DMA Abort callback :
2141          will lead to call HAL_UART_AbortCpltCallback() at end of DMA abort procedure */
2142       huart->hdmarx->XferAbortCallback = UART_DMARxOnlyAbortCallback;
2143 
2144       /* Abort DMA RX */
2145       if (HAL_DMA_Abort_IT(huart->hdmarx) != HAL_OK)
2146       {
2147         /* Call Directly huart->hdmarx->XferAbortCallback function in case of error */
2148         huart->hdmarx->XferAbortCallback(huart->hdmarx);
2149       }
2150     }
2151     else
2152     {
2153       /* Reset Rx transfer counter */
2154       huart->RxXferCount = 0U;
2155 
2156       /* Clear RxISR function pointer */
2157       huart->pRxBuffPtr = NULL;
2158 
2159       /* Clear the Error flags in the ICR register */
2160       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
2161 
2162       /* Discard the received data */
2163       __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
2164 
2165       /* Restore huart->RxState to Ready */
2166       huart->RxState = HAL_UART_STATE_READY;
2167       huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
2168 
2169       /* As no DMA to be aborted, call directly user Abort complete callback */
2170 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2171       /* Call registered Abort Receive Complete Callback */
2172       huart->AbortReceiveCpltCallback(huart);
2173 #else
2174       /* Call legacy weak Abort Receive Complete Callback */
2175       HAL_UART_AbortReceiveCpltCallback(huart);
2176 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2177     }
2178   }
2179   else
2180   {
2181     /* Reset Rx transfer counter */
2182     huart->RxXferCount = 0U;
2183 
2184     /* Clear RxISR function pointer */
2185     huart->pRxBuffPtr = NULL;
2186 
2187     /* Clear the Error flags in the ICR register */
2188     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
2189 
2190     /* Restore huart->RxState to Ready */
2191     huart->RxState = HAL_UART_STATE_READY;
2192     huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
2193 
2194     /* As no DMA to be aborted, call directly user Abort complete callback */
2195 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2196     /* Call registered Abort Receive Complete Callback */
2197     huart->AbortReceiveCpltCallback(huart);
2198 #else
2199     /* Call legacy weak Abort Receive Complete Callback */
2200     HAL_UART_AbortReceiveCpltCallback(huart);
2201 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2202   }
2203 
2204   return HAL_OK;
2205 }
2206 
2207 /**
2208   * @brief Handle UART interrupt request.
2209   * @param huart UART handle.
2210   * @retval None
2211   */
HAL_UART_IRQHandler(UART_HandleTypeDef * huart)2212 void HAL_UART_IRQHandler(UART_HandleTypeDef *huart)
2213 {
2214   uint32_t isrflags   = READ_REG(huart->Instance->ISR);
2215   uint32_t cr1its     = READ_REG(huart->Instance->CR1);
2216   uint32_t cr3its     = READ_REG(huart->Instance->CR3);
2217 
2218   uint32_t errorflags;
2219   uint32_t errorcode;
2220 
2221   /* If no error occurs */
2222   errorflags = (isrflags & (uint32_t)(USART_ISR_PE | USART_ISR_FE | USART_ISR_ORE | USART_ISR_NE | USART_ISR_RTOF));
2223   if (errorflags == 0U)
2224   {
2225     /* UART in mode Receiver ---------------------------------------------------*/
2226     if (((isrflags & USART_ISR_RXNE_RXFNE) != 0U)
2227         && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U)
2228             || ((cr3its & USART_CR3_RXFTIE) != 0U)))
2229     {
2230       if (huart->RxISR != NULL)
2231       {
2232         huart->RxISR(huart);
2233       }
2234       return;
2235     }
2236   }
2237 
2238   /* If some errors occur */
2239   if ((errorflags != 0U)
2240       && ((((cr3its & (USART_CR3_RXFTIE | USART_CR3_EIE)) != 0U)
2241            || ((cr1its & (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE | USART_CR1_RTOIE)) != 0U))))
2242   {
2243     /* UART parity error interrupt occurred -------------------------------------*/
2244     if (((isrflags & USART_ISR_PE) != 0U) && ((cr1its & USART_CR1_PEIE) != 0U))
2245     {
2246       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_PEF);
2247 
2248       huart->ErrorCode |= HAL_UART_ERROR_PE;
2249     }
2250 
2251     /* UART frame error interrupt occurred --------------------------------------*/
2252     if (((isrflags & USART_ISR_FE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
2253     {
2254       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_FEF);
2255 
2256       huart->ErrorCode |= HAL_UART_ERROR_FE;
2257     }
2258 
2259     /* UART noise error interrupt occurred --------------------------------------*/
2260     if (((isrflags & USART_ISR_NE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
2261     {
2262       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_NEF);
2263 
2264       huart->ErrorCode |= HAL_UART_ERROR_NE;
2265     }
2266 
2267     /* UART Over-Run interrupt occurred -----------------------------------------*/
2268     if (((isrflags & USART_ISR_ORE) != 0U)
2269         && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U) ||
2270             ((cr3its & (USART_CR3_RXFTIE | USART_CR3_EIE)) != 0U)))
2271     {
2272       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF);
2273 
2274       huart->ErrorCode |= HAL_UART_ERROR_ORE;
2275     }
2276 
2277     /* UART Receiver Timeout interrupt occurred ---------------------------------*/
2278     if (((isrflags & USART_ISR_RTOF) != 0U) && ((cr1its & USART_CR1_RTOIE) != 0U))
2279     {
2280       __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_RTOF);
2281 
2282       huart->ErrorCode |= HAL_UART_ERROR_RTO;
2283     }
2284 
2285     /* Call UART Error Call back function if need be ----------------------------*/
2286     if (huart->ErrorCode != HAL_UART_ERROR_NONE)
2287     {
2288       /* UART in mode Receiver --------------------------------------------------*/
2289       if (((isrflags & USART_ISR_RXNE_RXFNE) != 0U)
2290           && (((cr1its & USART_CR1_RXNEIE_RXFNEIE) != 0U)
2291               || ((cr3its & USART_CR3_RXFTIE) != 0U)))
2292       {
2293         if (huart->RxISR != NULL)
2294         {
2295           huart->RxISR(huart);
2296         }
2297       }
2298 
2299       /* If Error is to be considered as blocking :
2300           - Receiver Timeout error in Reception
2301           - Overrun error in Reception
2302           - any error occurs in DMA mode reception
2303       */
2304       errorcode = huart->ErrorCode;
2305       if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR)) ||
2306           ((errorcode & (HAL_UART_ERROR_RTO | HAL_UART_ERROR_ORE)) != 0U))
2307       {
2308         /* Blocking error : transfer is aborted
2309            Set the UART state ready to be able to start again the process,
2310            Disable Rx Interrupts, and disable Rx DMA request, if ongoing */
2311         UART_EndRxTransfer(huart);
2312 
2313         /* Abort the UART DMA Rx channel if enabled */
2314         if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
2315         {
2316           /* Disable the UART DMA Rx request if enabled */
2317           ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
2318 
2319           /* Abort the UART DMA Rx channel */
2320           if (huart->hdmarx != NULL)
2321           {
2322             /* Set the UART DMA Abort callback :
2323                will lead to call HAL_UART_ErrorCallback() at end of DMA abort procedure */
2324             huart->hdmarx->XferAbortCallback = UART_DMAAbortOnError;
2325 
2326             /* Abort DMA RX */
2327             if (HAL_DMA_Abort_IT(huart->hdmarx) != HAL_OK)
2328             {
2329               /* Call Directly huart->hdmarx->XferAbortCallback function in case of error */
2330               huart->hdmarx->XferAbortCallback(huart->hdmarx);
2331             }
2332           }
2333           else
2334           {
2335             /* Call user error callback */
2336 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2337             /*Call registered error callback*/
2338             huart->ErrorCallback(huart);
2339 #else
2340             /*Call legacy weak error callback*/
2341             HAL_UART_ErrorCallback(huart);
2342 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2343 
2344           }
2345         }
2346         else
2347         {
2348           /* Call user error callback */
2349 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2350           /*Call registered error callback*/
2351           huart->ErrorCallback(huart);
2352 #else
2353           /*Call legacy weak error callback*/
2354           HAL_UART_ErrorCallback(huart);
2355 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2356         }
2357       }
2358       else
2359       {
2360         /* Non Blocking error : transfer could go on.
2361            Error is notified to user through user error callback */
2362 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2363         /*Call registered error callback*/
2364         huart->ErrorCallback(huart);
2365 #else
2366         /*Call legacy weak error callback*/
2367         HAL_UART_ErrorCallback(huart);
2368 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2369         huart->ErrorCode = HAL_UART_ERROR_NONE;
2370       }
2371     }
2372     return;
2373 
2374   } /* End if some error occurs */
2375 
2376   /* Check current reception Mode :
2377      If Reception till IDLE event has been selected : */
2378   if ((huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
2379       && ((isrflags & USART_ISR_IDLE) != 0U)
2380       && ((cr1its & USART_ISR_IDLE) != 0U))
2381   {
2382     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_IDLEF);
2383 
2384     /* Check if DMA mode is enabled in UART */
2385     if (HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR))
2386     {
2387       /* DMA mode enabled */
2388       /* Check received length : If all expected data are received, do nothing,
2389          (DMA cplt callback will be called).
2390          Otherwise, if at least one data has already been received, IDLE event is to be notified to user */
2391       uint16_t nb_remaining_rx_data = (uint16_t) __HAL_DMA_GET_COUNTER(huart->hdmarx);
2392       if ((nb_remaining_rx_data > 0U)
2393           && (nb_remaining_rx_data < huart->RxXferSize))
2394       {
2395         /* Reception is not complete */
2396         huart->RxXferCount = nb_remaining_rx_data;
2397 
2398         /* In Normal mode, end DMA xfer and HAL UART Rx process*/
2399         if (HAL_IS_BIT_CLR(huart->hdmarx->Instance->CCR, DMA_CCR_CIRC))
2400         {
2401           /* Disable PE and ERR (Frame error, noise error, overrun error) interrupts */
2402           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_PEIE);
2403           ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
2404 
2405           /* Disable the DMA transfer for the receiver request by resetting the DMAR bit
2406              in the UART CR3 register */
2407           ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
2408 
2409           /* At end of Rx process, restore huart->RxState to Ready */
2410           huart->RxState = HAL_UART_STATE_READY;
2411           huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
2412 
2413           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
2414 
2415           /* Last bytes received, so no need as the abort is immediate */
2416           (void)HAL_DMA_Abort(huart->hdmarx);
2417         }
2418 
2419         /* Initialize type of RxEvent that correspond to RxEvent callback execution;
2420            In this case, Rx Event type is Idle Event */
2421         huart->RxEventType = HAL_UART_RXEVENT_IDLE;
2422 
2423 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2424         /*Call registered Rx Event callback*/
2425         huart->RxEventCallback(huart, (huart->RxXferSize - huart->RxXferCount));
2426 #else
2427         /*Call legacy weak Rx Event callback*/
2428         HAL_UARTEx_RxEventCallback(huart, (huart->RxXferSize - huart->RxXferCount));
2429 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
2430       }
2431       return;
2432     }
2433     else
2434     {
2435       /* DMA mode not enabled */
2436       /* Check received length : If all expected data are received, do nothing.
2437          Otherwise, if at least one data has already been received, IDLE event is to be notified to user */
2438       uint16_t nb_rx_data = huart->RxXferSize - huart->RxXferCount;
2439       if ((huart->RxXferCount > 0U)
2440           && (nb_rx_data > 0U))
2441       {
2442         /* Disable the UART Parity Error Interrupt and RXNE interrupts */
2443         ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
2444 
2445         /* Disable the UART Error Interrupt:(Frame error, noise error, overrun error) and RX FIFO Threshold interrupt */
2446         ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
2447 
2448         /* Rx process is completed, restore huart->RxState to Ready */
2449         huart->RxState = HAL_UART_STATE_READY;
2450         huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
2451 
2452         /* Clear RxISR function pointer */
2453         huart->RxISR = NULL;
2454 
2455         ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
2456 
2457         /* Initialize type of RxEvent that correspond to RxEvent callback execution;
2458            In this case, Rx Event type is Idle Event */
2459         huart->RxEventType = HAL_UART_RXEVENT_IDLE;
2460 
2461 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2462         /*Call registered Rx complete callback*/
2463         huart->RxEventCallback(huart, nb_rx_data);
2464 #else
2465         /*Call legacy weak Rx Event callback*/
2466         HAL_UARTEx_RxEventCallback(huart, nb_rx_data);
2467 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
2468       }
2469       return;
2470     }
2471   }
2472 
2473   /* UART wakeup from Stop mode interrupt occurred ---------------------------*/
2474   if (((isrflags & USART_ISR_WUF) != 0U) && ((cr3its & USART_CR3_WUFIE) != 0U))
2475   {
2476     __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_WUF);
2477 
2478     /* UART Rx state is not reset as a reception process might be ongoing.
2479        If UART handle state fields need to be reset to READY, this could be done in Wakeup callback */
2480 
2481 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2482     /* Call registered Wakeup Callback */
2483     huart->WakeupCallback(huart);
2484 #else
2485     /* Call legacy weak Wakeup Callback */
2486     HAL_UARTEx_WakeupCallback(huart);
2487 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2488     return;
2489   }
2490 
2491   /* UART in mode Transmitter ------------------------------------------------*/
2492   if (((isrflags & USART_ISR_TXE_TXFNF) != 0U)
2493       && (((cr1its & USART_CR1_TXEIE_TXFNFIE) != 0U)
2494           || ((cr3its & USART_CR3_TXFTIE) != 0U)))
2495   {
2496     if (huart->TxISR != NULL)
2497     {
2498       huart->TxISR(huart);
2499     }
2500     return;
2501   }
2502 
2503   /* UART in mode Transmitter (transmission end) -----------------------------*/
2504   if (((isrflags & USART_ISR_TC) != 0U) && ((cr1its & USART_CR1_TCIE) != 0U))
2505   {
2506     UART_EndTransmit_IT(huart);
2507     return;
2508   }
2509 
2510   /* UART TX Fifo Empty occurred ----------------------------------------------*/
2511   if (((isrflags & USART_ISR_TXFE) != 0U) && ((cr1its & USART_CR1_TXFEIE) != 0U))
2512   {
2513 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2514     /* Call registered Tx Fifo Empty Callback */
2515     huart->TxFifoEmptyCallback(huart);
2516 #else
2517     /* Call legacy weak Tx Fifo Empty Callback */
2518     HAL_UARTEx_TxFifoEmptyCallback(huart);
2519 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2520     return;
2521   }
2522 
2523   /* UART RX Fifo Full occurred ----------------------------------------------*/
2524   if (((isrflags & USART_ISR_RXFF) != 0U) && ((cr1its & USART_CR1_RXFFIE) != 0U))
2525   {
2526 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
2527     /* Call registered Rx Fifo Full Callback */
2528     huart->RxFifoFullCallback(huart);
2529 #else
2530     /* Call legacy weak Rx Fifo Full Callback */
2531     HAL_UARTEx_RxFifoFullCallback(huart);
2532 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
2533     return;
2534   }
2535 }
2536 
2537 /**
2538   * @brief Tx Transfer completed callback.
2539   * @param huart UART handle.
2540   * @retval None
2541   */
HAL_UART_TxCpltCallback(UART_HandleTypeDef * huart)2542 __weak void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart)
2543 {
2544   /* Prevent unused argument(s) compilation warning */
2545   UNUSED(huart);
2546 
2547   /* NOTE : This function should not be modified, when the callback is needed,
2548             the HAL_UART_TxCpltCallback can be implemented in the user file.
2549    */
2550 }
2551 
2552 /**
2553   * @brief  Tx Half Transfer completed callback.
2554   * @param  huart UART handle.
2555   * @retval None
2556   */
HAL_UART_TxHalfCpltCallback(UART_HandleTypeDef * huart)2557 __weak void HAL_UART_TxHalfCpltCallback(UART_HandleTypeDef *huart)
2558 {
2559   /* Prevent unused argument(s) compilation warning */
2560   UNUSED(huart);
2561 
2562   /* NOTE: This function should not be modified, when the callback is needed,
2563            the HAL_UART_TxHalfCpltCallback can be implemented in the user file.
2564    */
2565 }
2566 
2567 /**
2568   * @brief  Rx Transfer completed callback.
2569   * @param  huart UART handle.
2570   * @retval None
2571   */
HAL_UART_RxCpltCallback(UART_HandleTypeDef * huart)2572 __weak void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
2573 {
2574   /* Prevent unused argument(s) compilation warning */
2575   UNUSED(huart);
2576 
2577   /* NOTE : This function should not be modified, when the callback is needed,
2578             the HAL_UART_RxCpltCallback can be implemented in the user file.
2579    */
2580 }
2581 
2582 /**
2583   * @brief  Rx Half Transfer completed callback.
2584   * @param  huart UART handle.
2585   * @retval None
2586   */
HAL_UART_RxHalfCpltCallback(UART_HandleTypeDef * huart)2587 __weak void HAL_UART_RxHalfCpltCallback(UART_HandleTypeDef *huart)
2588 {
2589   /* Prevent unused argument(s) compilation warning */
2590   UNUSED(huart);
2591 
2592   /* NOTE: This function should not be modified, when the callback is needed,
2593            the HAL_UART_RxHalfCpltCallback can be implemented in the user file.
2594    */
2595 }
2596 
2597 /**
2598   * @brief  UART error callback.
2599   * @param  huart UART handle.
2600   * @retval None
2601   */
HAL_UART_ErrorCallback(UART_HandleTypeDef * huart)2602 __weak void HAL_UART_ErrorCallback(UART_HandleTypeDef *huart)
2603 {
2604   /* Prevent unused argument(s) compilation warning */
2605   UNUSED(huart);
2606 
2607   /* NOTE : This function should not be modified, when the callback is needed,
2608             the HAL_UART_ErrorCallback can be implemented in the user file.
2609    */
2610 }
2611 
2612 /**
2613   * @brief  UART Abort Complete callback.
2614   * @param  huart UART handle.
2615   * @retval None
2616   */
HAL_UART_AbortCpltCallback(UART_HandleTypeDef * huart)2617 __weak void HAL_UART_AbortCpltCallback(UART_HandleTypeDef *huart)
2618 {
2619   /* Prevent unused argument(s) compilation warning */
2620   UNUSED(huart);
2621 
2622   /* NOTE : This function should not be modified, when the callback is needed,
2623             the HAL_UART_AbortCpltCallback can be implemented in the user file.
2624    */
2625 }
2626 
2627 /**
2628   * @brief  UART Abort Complete callback.
2629   * @param  huart UART handle.
2630   * @retval None
2631   */
HAL_UART_AbortTransmitCpltCallback(UART_HandleTypeDef * huart)2632 __weak void HAL_UART_AbortTransmitCpltCallback(UART_HandleTypeDef *huart)
2633 {
2634   /* Prevent unused argument(s) compilation warning */
2635   UNUSED(huart);
2636 
2637   /* NOTE : This function should not be modified, when the callback is needed,
2638             the HAL_UART_AbortTransmitCpltCallback can be implemented in the user file.
2639    */
2640 }
2641 
2642 /**
2643   * @brief  UART Abort Receive Complete callback.
2644   * @param  huart UART handle.
2645   * @retval None
2646   */
HAL_UART_AbortReceiveCpltCallback(UART_HandleTypeDef * huart)2647 __weak void HAL_UART_AbortReceiveCpltCallback(UART_HandleTypeDef *huart)
2648 {
2649   /* Prevent unused argument(s) compilation warning */
2650   UNUSED(huart);
2651 
2652   /* NOTE : This function should not be modified, when the callback is needed,
2653             the HAL_UART_AbortReceiveCpltCallback can be implemented in the user file.
2654    */
2655 }
2656 
2657 /**
2658   * @brief  Reception Event Callback (Rx event notification called after use of advanced reception service).
2659   * @param  huart UART handle
2660   * @param  Size  Number of data available in application reception buffer (indicates a position in
2661   *               reception buffer until which, data are available)
2662   * @retval None
2663   */
HAL_UARTEx_RxEventCallback(UART_HandleTypeDef * huart,uint16_t Size)2664 __weak void HAL_UARTEx_RxEventCallback(UART_HandleTypeDef *huart, uint16_t Size)
2665 {
2666   /* Prevent unused argument(s) compilation warning */
2667   UNUSED(huart);
2668   UNUSED(Size);
2669 
2670   /* NOTE : This function should not be modified, when the callback is needed,
2671             the HAL_UARTEx_RxEventCallback can be implemented in the user file.
2672    */
2673 }
2674 
2675 /**
2676   * @}
2677   */
2678 
2679 /** @defgroup UART_Exported_Functions_Group3 Peripheral Control functions
2680   *  @brief   UART control functions
2681   *
2682 @verbatim
2683  ===============================================================================
2684                       ##### Peripheral Control functions #####
2685  ===============================================================================
2686     [..]
2687     This subsection provides a set of functions allowing to control the UART.
2688      (+) HAL_UART_ReceiverTimeout_Config() API allows to configure the receiver timeout value on the fly
2689      (+) HAL_UART_EnableReceiverTimeout() API enables the receiver timeout feature
2690      (+) HAL_UART_DisableReceiverTimeout() API disables the receiver timeout feature
2691      (+) HAL_MultiProcessor_EnableMuteMode() API enables mute mode
2692      (+) HAL_MultiProcessor_DisableMuteMode() API disables mute mode
2693      (+) HAL_MultiProcessor_EnterMuteMode() API enters mute mode
2694      (+) UART_SetConfig() API configures the UART peripheral
2695      (+) UART_AdvFeatureConfig() API optionally configures the UART advanced features
2696      (+) UART_CheckIdleState() API ensures that TEACK and/or REACK are set after initialization
2697      (+) HAL_HalfDuplex_EnableTransmitter() API disables receiver and enables transmitter
2698      (+) HAL_HalfDuplex_EnableReceiver() API disables transmitter and enables receiver
2699      (+) HAL_LIN_SendBreak() API transmits the break characters
2700 @endverbatim
2701   * @{
2702   */
2703 
2704 /**
2705   * @brief  Update on the fly the receiver timeout value in RTOR register.
2706   * @param  huart Pointer to a UART_HandleTypeDef structure that contains
2707   *                    the configuration information for the specified UART module.
2708   * @param  TimeoutValue receiver timeout value in number of baud blocks. The timeout
2709   *                     value must be less or equal to 0x0FFFFFFFF.
2710   * @retval None
2711   */
HAL_UART_ReceiverTimeout_Config(UART_HandleTypeDef * huart,uint32_t TimeoutValue)2712 void HAL_UART_ReceiverTimeout_Config(UART_HandleTypeDef *huart, uint32_t TimeoutValue)
2713 {
2714   if (!(IS_LPUART_INSTANCE(huart->Instance)))
2715   {
2716     assert_param(IS_UART_RECEIVER_TIMEOUT_VALUE(TimeoutValue));
2717     MODIFY_REG(huart->Instance->RTOR, USART_RTOR_RTO, TimeoutValue);
2718   }
2719 }
2720 
2721 /**
2722   * @brief  Enable the UART receiver timeout feature.
2723   * @param  huart Pointer to a UART_HandleTypeDef structure that contains
2724   *                    the configuration information for the specified UART module.
2725   * @retval HAL status
2726   */
HAL_UART_EnableReceiverTimeout(UART_HandleTypeDef * huart)2727 HAL_StatusTypeDef HAL_UART_EnableReceiverTimeout(UART_HandleTypeDef *huart)
2728 {
2729   if (!(IS_LPUART_INSTANCE(huart->Instance)))
2730   {
2731     if (huart->gState == HAL_UART_STATE_READY)
2732     {
2733       /* Process Locked */
2734       __HAL_LOCK(huart);
2735 
2736       huart->gState = HAL_UART_STATE_BUSY;
2737 
2738       /* Set the USART RTOEN bit */
2739       SET_BIT(huart->Instance->CR2, USART_CR2_RTOEN);
2740 
2741       huart->gState = HAL_UART_STATE_READY;
2742 
2743       /* Process Unlocked */
2744       __HAL_UNLOCK(huart);
2745 
2746       return HAL_OK;
2747     }
2748     else
2749     {
2750       return HAL_BUSY;
2751     }
2752   }
2753   else
2754   {
2755     return HAL_ERROR;
2756   }
2757 }
2758 
2759 /**
2760   * @brief  Disable the UART receiver timeout feature.
2761   * @param  huart Pointer to a UART_HandleTypeDef structure that contains
2762   *                    the configuration information for the specified UART module.
2763   * @retval HAL status
2764   */
HAL_UART_DisableReceiverTimeout(UART_HandleTypeDef * huart)2765 HAL_StatusTypeDef HAL_UART_DisableReceiverTimeout(UART_HandleTypeDef *huart)
2766 {
2767   if (!(IS_LPUART_INSTANCE(huart->Instance)))
2768   {
2769     if (huart->gState == HAL_UART_STATE_READY)
2770     {
2771       /* Process Locked */
2772       __HAL_LOCK(huart);
2773 
2774       huart->gState = HAL_UART_STATE_BUSY;
2775 
2776       /* Clear the USART RTOEN bit */
2777       CLEAR_BIT(huart->Instance->CR2, USART_CR2_RTOEN);
2778 
2779       huart->gState = HAL_UART_STATE_READY;
2780 
2781       /* Process Unlocked */
2782       __HAL_UNLOCK(huart);
2783 
2784       return HAL_OK;
2785     }
2786     else
2787     {
2788       return HAL_BUSY;
2789     }
2790   }
2791   else
2792   {
2793     return HAL_ERROR;
2794   }
2795 }
2796 
2797 /**
2798   * @brief  Enable UART in mute mode (does not mean UART enters mute mode;
2799   *         to enter mute mode, HAL_MultiProcessor_EnterMuteMode() API must be called).
2800   * @param  huart UART handle.
2801   * @retval HAL status
2802   */
HAL_MultiProcessor_EnableMuteMode(UART_HandleTypeDef * huart)2803 HAL_StatusTypeDef HAL_MultiProcessor_EnableMuteMode(UART_HandleTypeDef *huart)
2804 {
2805   __HAL_LOCK(huart);
2806 
2807   huart->gState = HAL_UART_STATE_BUSY;
2808 
2809   /* Enable USART mute mode by setting the MME bit in the CR1 register */
2810   ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_MME);
2811 
2812   huart->gState = HAL_UART_STATE_READY;
2813 
2814   return (UART_CheckIdleState(huart));
2815 }
2816 
2817 /**
2818   * @brief  Disable UART mute mode (does not mean the UART actually exits mute mode
2819   *         as it may not have been in mute mode at this very moment).
2820   * @param  huart UART handle.
2821   * @retval HAL status
2822   */
HAL_MultiProcessor_DisableMuteMode(UART_HandleTypeDef * huart)2823 HAL_StatusTypeDef HAL_MultiProcessor_DisableMuteMode(UART_HandleTypeDef *huart)
2824 {
2825   __HAL_LOCK(huart);
2826 
2827   huart->gState = HAL_UART_STATE_BUSY;
2828 
2829   /* Disable USART mute mode by clearing the MME bit in the CR1 register */
2830   ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_MME);
2831 
2832   huart->gState = HAL_UART_STATE_READY;
2833 
2834   return (UART_CheckIdleState(huart));
2835 }
2836 
2837 /**
2838   * @brief Enter UART mute mode (means UART actually enters mute mode).
2839   * @note  To exit from mute mode, HAL_MultiProcessor_DisableMuteMode() API must be called.
2840   * @param huart UART handle.
2841   * @retval None
2842   */
HAL_MultiProcessor_EnterMuteMode(UART_HandleTypeDef * huart)2843 void HAL_MultiProcessor_EnterMuteMode(UART_HandleTypeDef *huart)
2844 {
2845   __HAL_UART_SEND_REQ(huart, UART_MUTE_MODE_REQUEST);
2846 }
2847 
2848 /**
2849   * @brief  Enable the UART transmitter and disable the UART receiver.
2850   * @param  huart UART handle.
2851   * @retval HAL status
2852   */
HAL_HalfDuplex_EnableTransmitter(UART_HandleTypeDef * huart)2853 HAL_StatusTypeDef HAL_HalfDuplex_EnableTransmitter(UART_HandleTypeDef *huart)
2854 {
2855   __HAL_LOCK(huart);
2856   huart->gState = HAL_UART_STATE_BUSY;
2857 
2858   /* Clear TE and RE bits */
2859   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TE | USART_CR1_RE));
2860 
2861   /* Enable the USART's transmit interface by setting the TE bit in the USART CR1 register */
2862   ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TE);
2863 
2864   huart->gState = HAL_UART_STATE_READY;
2865 
2866   __HAL_UNLOCK(huart);
2867 
2868   return HAL_OK;
2869 }
2870 
2871 /**
2872   * @brief  Enable the UART receiver and disable the UART transmitter.
2873   * @param  huart UART handle.
2874   * @retval HAL status.
2875   */
HAL_HalfDuplex_EnableReceiver(UART_HandleTypeDef * huart)2876 HAL_StatusTypeDef HAL_HalfDuplex_EnableReceiver(UART_HandleTypeDef *huart)
2877 {
2878   __HAL_LOCK(huart);
2879   huart->gState = HAL_UART_STATE_BUSY;
2880 
2881   /* Clear TE and RE bits */
2882   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TE | USART_CR1_RE));
2883 
2884   /* Enable the USART's receive interface by setting the RE bit in the USART CR1 register */
2885   ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RE);
2886 
2887   huart->gState = HAL_UART_STATE_READY;
2888 
2889   __HAL_UNLOCK(huart);
2890 
2891   return HAL_OK;
2892 }
2893 
2894 
2895 /**
2896   * @brief  Transmit break characters.
2897   * @param  huart UART handle.
2898   * @retval HAL status
2899   */
HAL_LIN_SendBreak(UART_HandleTypeDef * huart)2900 HAL_StatusTypeDef HAL_LIN_SendBreak(UART_HandleTypeDef *huart)
2901 {
2902   /* Check the parameters */
2903   assert_param(IS_UART_LIN_INSTANCE(huart->Instance));
2904 
2905   __HAL_LOCK(huart);
2906 
2907   huart->gState = HAL_UART_STATE_BUSY;
2908 
2909   /* Send break characters */
2910   __HAL_UART_SEND_REQ(huart, UART_SENDBREAK_REQUEST);
2911 
2912   huart->gState = HAL_UART_STATE_READY;
2913 
2914   __HAL_UNLOCK(huart);
2915 
2916   return HAL_OK;
2917 }
2918 
2919 /**
2920   * @}
2921   */
2922 
2923 /** @defgroup UART_Exported_Functions_Group4 Peripheral State and Error functions
2924   *  @brief   UART Peripheral State functions
2925   *
2926 @verbatim
2927   ==============================================================================
2928             ##### Peripheral State and Error functions #####
2929   ==============================================================================
2930     [..]
2931     This subsection provides functions allowing to :
2932       (+) Return the UART handle state.
2933       (+) Return the UART handle error code
2934 
2935 @endverbatim
2936   * @{
2937   */
2938 
2939 /**
2940   * @brief Return the UART handle state.
2941   * @param  huart Pointer to a UART_HandleTypeDef structure that contains
2942   *               the configuration information for the specified UART.
2943   * @retval HAL state
2944   */
HAL_UART_GetState(const UART_HandleTypeDef * huart)2945 HAL_UART_StateTypeDef HAL_UART_GetState(const UART_HandleTypeDef *huart)
2946 {
2947   uint32_t temp1;
2948   uint32_t temp2;
2949   temp1 = huart->gState;
2950   temp2 = huart->RxState;
2951 
2952   return (HAL_UART_StateTypeDef)(temp1 | temp2);
2953 }
2954 
2955 /**
2956   * @brief  Return the UART handle error code.
2957   * @param  huart Pointer to a UART_HandleTypeDef structure that contains
2958   *               the configuration information for the specified UART.
2959   * @retval UART Error Code
2960   */
HAL_UART_GetError(const UART_HandleTypeDef * huart)2961 uint32_t HAL_UART_GetError(const UART_HandleTypeDef *huart)
2962 {
2963   return huart->ErrorCode;
2964 }
2965 /**
2966   * @}
2967   */
2968 
2969 /**
2970   * @}
2971   */
2972 
2973 /** @defgroup UART_Private_Functions UART Private Functions
2974   * @{
2975   */
2976 
2977 /**
2978   * @brief  Initialize the callbacks to their default values.
2979   * @param  huart UART handle.
2980   * @retval none
2981   */
2982 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
UART_InitCallbacksToDefault(UART_HandleTypeDef * huart)2983 void UART_InitCallbacksToDefault(UART_HandleTypeDef *huart)
2984 {
2985   /* Init the UART Callback settings */
2986   huart->TxHalfCpltCallback        = HAL_UART_TxHalfCpltCallback;        /* Legacy weak TxHalfCpltCallback        */
2987   huart->TxCpltCallback            = HAL_UART_TxCpltCallback;            /* Legacy weak TxCpltCallback            */
2988   huart->RxHalfCpltCallback        = HAL_UART_RxHalfCpltCallback;        /* Legacy weak RxHalfCpltCallback        */
2989   huart->RxCpltCallback            = HAL_UART_RxCpltCallback;            /* Legacy weak RxCpltCallback            */
2990   huart->ErrorCallback             = HAL_UART_ErrorCallback;             /* Legacy weak ErrorCallback             */
2991   huart->AbortCpltCallback         = HAL_UART_AbortCpltCallback;         /* Legacy weak AbortCpltCallback         */
2992   huart->AbortTransmitCpltCallback = HAL_UART_AbortTransmitCpltCallback; /* Legacy weak AbortTransmitCpltCallback */
2993   huart->AbortReceiveCpltCallback  = HAL_UART_AbortReceiveCpltCallback;  /* Legacy weak AbortReceiveCpltCallback  */
2994   huart->WakeupCallback            = HAL_UARTEx_WakeupCallback;          /* Legacy weak WakeupCallback            */
2995   huart->RxFifoFullCallback        = HAL_UARTEx_RxFifoFullCallback;      /* Legacy weak RxFifoFullCallback        */
2996   huart->TxFifoEmptyCallback       = HAL_UARTEx_TxFifoEmptyCallback;     /* Legacy weak TxFifoEmptyCallback       */
2997   huart->RxEventCallback           = HAL_UARTEx_RxEventCallback;         /* Legacy weak RxEventCallback           */
2998 
2999 }
3000 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3001 
3002 /**
3003   * @brief Configure the UART peripheral.
3004   * @param huart UART handle.
3005   * @retval HAL status
3006   */
UART_SetConfig(UART_HandleTypeDef * huart)3007 HAL_StatusTypeDef UART_SetConfig(UART_HandleTypeDef *huart)
3008 {
3009   uint32_t tmpreg;
3010   uint16_t brrtemp;
3011   UART_ClockSourceTypeDef clocksource;
3012   uint32_t usartdiv;
3013   HAL_StatusTypeDef ret               = HAL_OK;
3014   uint32_t lpuart_ker_ck_pres;
3015   uint32_t pclk;
3016 
3017   /* Check the parameters */
3018   assert_param(IS_UART_BAUDRATE(huart->Init.BaudRate));
3019   assert_param(IS_UART_WORD_LENGTH(huart->Init.WordLength));
3020   if (UART_INSTANCE_LOWPOWER(huart))
3021   {
3022     assert_param(IS_LPUART_STOPBITS(huart->Init.StopBits));
3023   }
3024   else
3025   {
3026     assert_param(IS_UART_STOPBITS(huart->Init.StopBits));
3027     assert_param(IS_UART_ONE_BIT_SAMPLE(huart->Init.OneBitSampling));
3028   }
3029 
3030   assert_param(IS_UART_PARITY(huart->Init.Parity));
3031   assert_param(IS_UART_MODE(huart->Init.Mode));
3032   assert_param(IS_UART_HARDWARE_FLOW_CONTROL(huart->Init.HwFlowCtl));
3033   assert_param(IS_UART_OVERSAMPLING(huart->Init.OverSampling));
3034   assert_param(IS_UART_PRESCALER(huart->Init.ClockPrescaler));
3035 
3036   /*-------------------------- USART CR1 Configuration -----------------------*/
3037   /* Clear M, PCE, PS, TE, RE and OVER8 bits and configure
3038   *  the UART Word Length, Parity, Mode and oversampling:
3039   *  set the M bits according to huart->Init.WordLength value
3040   *  set PCE and PS bits according to huart->Init.Parity value
3041   *  set TE and RE bits according to huart->Init.Mode value
3042   *  set OVER8 bit according to huart->Init.OverSampling value */
3043   tmpreg = (uint32_t)huart->Init.WordLength | huart->Init.Parity | huart->Init.Mode | huart->Init.OverSampling ;
3044   MODIFY_REG(huart->Instance->CR1, USART_CR1_FIELDS, tmpreg);
3045 
3046   /*-------------------------- USART CR2 Configuration -----------------------*/
3047   /* Configure the UART Stop Bits: Set STOP[13:12] bits according
3048   * to huart->Init.StopBits value */
3049   MODIFY_REG(huart->Instance->CR2, USART_CR2_STOP, huart->Init.StopBits);
3050 
3051   /*-------------------------- USART CR3 Configuration -----------------------*/
3052   /* Configure
3053   * - UART HardWare Flow Control: set CTSE and RTSE bits according
3054   *   to huart->Init.HwFlowCtl value
3055   * - one-bit sampling method versus three samples' majority rule according
3056   *   to huart->Init.OneBitSampling (not applicable to LPUART) */
3057   tmpreg = (uint32_t)huart->Init.HwFlowCtl;
3058 
3059   if (!(UART_INSTANCE_LOWPOWER(huart)))
3060   {
3061     tmpreg |= huart->Init.OneBitSampling;
3062   }
3063   MODIFY_REG(huart->Instance->CR3, USART_CR3_FIELDS, tmpreg);
3064 
3065   /*-------------------------- USART PRESC Configuration -----------------------*/
3066   /* Configure
3067   * - UART Clock Prescaler : set PRESCALER according to huart->Init.ClockPrescaler value */
3068   MODIFY_REG(huart->Instance->PRESC, USART_PRESC_PRESCALER, huart->Init.ClockPrescaler);
3069 
3070   /*-------------------------- USART BRR Configuration -----------------------*/
3071   UART_GETCLOCKSOURCE(huart, clocksource);
3072 
3073   /* Check LPUART instance */
3074   if (UART_INSTANCE_LOWPOWER(huart))
3075   {
3076     /* Retrieve frequency clock */
3077     switch (clocksource)
3078     {
3079       case UART_CLOCKSOURCE_PCLK1:
3080         pclk = HAL_RCC_GetPCLK1Freq();
3081         break;
3082       case UART_CLOCKSOURCE_PCLK2:
3083         pclk = HAL_RCC_GetPCLK2Freq();
3084         break;
3085       case UART_CLOCKSOURCE_HSI:
3086         pclk = (uint32_t) HSI_VALUE;
3087         break;
3088       case UART_CLOCKSOURCE_SYSCLK:
3089         pclk = HAL_RCC_GetSysClockFreq();
3090         break;
3091       case UART_CLOCKSOURCE_LSE:
3092         pclk = (uint32_t) LSE_VALUE;
3093         break;
3094       default:
3095         pclk = 0U;
3096         ret = HAL_ERROR;
3097         break;
3098     }
3099 
3100     /* If proper clock source reported */
3101     if (pclk != 0U)
3102     {
3103       /* Compute clock after Prescaler */
3104       lpuart_ker_ck_pres = (pclk / UARTPrescTable[huart->Init.ClockPrescaler]);
3105 
3106       /* Ensure that Frequency clock is in the range [3 * baudrate, 4096 * baudrate] */
3107       if ((lpuart_ker_ck_pres < (3U * huart->Init.BaudRate)) ||
3108           (lpuart_ker_ck_pres > (4096U * huart->Init.BaudRate)))
3109       {
3110         ret = HAL_ERROR;
3111       }
3112       else
3113       {
3114         /* Check computed UsartDiv value is in allocated range
3115            (it is forbidden to write values lower than 0x300 in the LPUART_BRR register) */
3116         usartdiv = (uint32_t)(UART_DIV_LPUART(pclk, huart->Init.BaudRate, huart->Init.ClockPrescaler));
3117         if ((usartdiv >= LPUART_BRR_MIN) && (usartdiv <= LPUART_BRR_MAX))
3118         {
3119           huart->Instance->BRR = usartdiv;
3120         }
3121         else
3122         {
3123           ret = HAL_ERROR;
3124         }
3125       } /* if ( (lpuart_ker_ck_pres < (3 * huart->Init.BaudRate) ) ||
3126                 (lpuart_ker_ck_pres > (4096 * huart->Init.BaudRate) )) */
3127     } /* if (pclk != 0) */
3128   }
3129   /* Check UART Over Sampling to set Baud Rate Register */
3130   else if (huart->Init.OverSampling == UART_OVERSAMPLING_8)
3131   {
3132     switch (clocksource)
3133     {
3134       case UART_CLOCKSOURCE_PCLK1:
3135         pclk = HAL_RCC_GetPCLK1Freq();
3136         break;
3137       case UART_CLOCKSOURCE_PCLK2:
3138         pclk = HAL_RCC_GetPCLK2Freq();
3139         break;
3140       case UART_CLOCKSOURCE_HSI:
3141         pclk = (uint32_t) HSI_VALUE;
3142         break;
3143       case UART_CLOCKSOURCE_SYSCLK:
3144         pclk = HAL_RCC_GetSysClockFreq();
3145         break;
3146       case UART_CLOCKSOURCE_LSE:
3147         pclk = (uint32_t) LSE_VALUE;
3148         break;
3149       default:
3150         pclk = 0U;
3151         ret = HAL_ERROR;
3152         break;
3153     }
3154 
3155     /* USARTDIV must be greater than or equal to 0d16 */
3156     if (pclk != 0U)
3157     {
3158       usartdiv = (uint32_t)(UART_DIV_SAMPLING8(pclk, huart->Init.BaudRate, huart->Init.ClockPrescaler));
3159       if ((usartdiv >= UART_BRR_MIN) && (usartdiv <= UART_BRR_MAX))
3160       {
3161         brrtemp = (uint16_t)(usartdiv & 0xFFF0U);
3162         brrtemp |= (uint16_t)((usartdiv & (uint16_t)0x000FU) >> 1U);
3163         huart->Instance->BRR = brrtemp;
3164       }
3165       else
3166       {
3167         ret = HAL_ERROR;
3168       }
3169     }
3170   }
3171   else
3172   {
3173     switch (clocksource)
3174     {
3175       case UART_CLOCKSOURCE_PCLK1:
3176         pclk = HAL_RCC_GetPCLK1Freq();
3177         break;
3178       case UART_CLOCKSOURCE_PCLK2:
3179         pclk = HAL_RCC_GetPCLK2Freq();
3180         break;
3181       case UART_CLOCKSOURCE_HSI:
3182         pclk = (uint32_t) HSI_VALUE;
3183         break;
3184       case UART_CLOCKSOURCE_SYSCLK:
3185         pclk = HAL_RCC_GetSysClockFreq();
3186         break;
3187       case UART_CLOCKSOURCE_LSE:
3188         pclk = (uint32_t) LSE_VALUE;
3189         break;
3190       default:
3191         pclk = 0U;
3192         ret = HAL_ERROR;
3193         break;
3194     }
3195 
3196     if (pclk != 0U)
3197     {
3198       /* USARTDIV must be greater than or equal to 0d16 */
3199       usartdiv = (uint32_t)(UART_DIV_SAMPLING16(pclk, huart->Init.BaudRate, huart->Init.ClockPrescaler));
3200       if ((usartdiv >= UART_BRR_MIN) && (usartdiv <= UART_BRR_MAX))
3201       {
3202         huart->Instance->BRR = (uint16_t)usartdiv;
3203       }
3204       else
3205       {
3206         ret = HAL_ERROR;
3207       }
3208     }
3209   }
3210 
3211   /* Initialize the number of data to process during RX/TX ISR execution */
3212   huart->NbTxDataToProcess = 1;
3213   huart->NbRxDataToProcess = 1;
3214 
3215   /* Clear ISR function pointers */
3216   huart->RxISR = NULL;
3217   huart->TxISR = NULL;
3218 
3219   return ret;
3220 }
3221 
3222 /**
3223   * @brief Configure the UART peripheral advanced features.
3224   * @param huart UART handle.
3225   * @retval None
3226   */
UART_AdvFeatureConfig(UART_HandleTypeDef * huart)3227 void UART_AdvFeatureConfig(UART_HandleTypeDef *huart)
3228 {
3229   /* Check whether the set of advanced features to configure is properly set */
3230   assert_param(IS_UART_ADVFEATURE_INIT(huart->AdvancedInit.AdvFeatureInit));
3231 
3232   /* if required, configure TX pin active level inversion */
3233   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_TXINVERT_INIT))
3234   {
3235     assert_param(IS_UART_ADVFEATURE_TXINV(huart->AdvancedInit.TxPinLevelInvert));
3236     MODIFY_REG(huart->Instance->CR2, USART_CR2_TXINV, huart->AdvancedInit.TxPinLevelInvert);
3237   }
3238 
3239   /* if required, configure RX pin active level inversion */
3240   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_RXINVERT_INIT))
3241   {
3242     assert_param(IS_UART_ADVFEATURE_RXINV(huart->AdvancedInit.RxPinLevelInvert));
3243     MODIFY_REG(huart->Instance->CR2, USART_CR2_RXINV, huart->AdvancedInit.RxPinLevelInvert);
3244   }
3245 
3246   /* if required, configure data inversion */
3247   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_DATAINVERT_INIT))
3248   {
3249     assert_param(IS_UART_ADVFEATURE_DATAINV(huart->AdvancedInit.DataInvert));
3250     MODIFY_REG(huart->Instance->CR2, USART_CR2_DATAINV, huart->AdvancedInit.DataInvert);
3251   }
3252 
3253   /* if required, configure RX/TX pins swap */
3254   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_SWAP_INIT))
3255   {
3256     assert_param(IS_UART_ADVFEATURE_SWAP(huart->AdvancedInit.Swap));
3257     MODIFY_REG(huart->Instance->CR2, USART_CR2_SWAP, huart->AdvancedInit.Swap);
3258   }
3259 
3260   /* if required, configure RX overrun detection disabling */
3261   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_RXOVERRUNDISABLE_INIT))
3262   {
3263     assert_param(IS_UART_OVERRUN(huart->AdvancedInit.OverrunDisable));
3264     MODIFY_REG(huart->Instance->CR3, USART_CR3_OVRDIS, huart->AdvancedInit.OverrunDisable);
3265   }
3266 
3267   /* if required, configure DMA disabling on reception error */
3268   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_DMADISABLEONERROR_INIT))
3269   {
3270     assert_param(IS_UART_ADVFEATURE_DMAONRXERROR(huart->AdvancedInit.DMADisableonRxError));
3271     MODIFY_REG(huart->Instance->CR3, USART_CR3_DDRE, huart->AdvancedInit.DMADisableonRxError);
3272   }
3273 
3274   /* if required, configure auto Baud rate detection scheme */
3275   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_AUTOBAUDRATE_INIT))
3276   {
3277     assert_param(IS_USART_AUTOBAUDRATE_DETECTION_INSTANCE(huart->Instance));
3278     assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATE(huart->AdvancedInit.AutoBaudRateEnable));
3279     MODIFY_REG(huart->Instance->CR2, USART_CR2_ABREN, huart->AdvancedInit.AutoBaudRateEnable);
3280     /* set auto Baudrate detection parameters if detection is enabled */
3281     if (huart->AdvancedInit.AutoBaudRateEnable == UART_ADVFEATURE_AUTOBAUDRATE_ENABLE)
3282     {
3283       assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATEMODE(huart->AdvancedInit.AutoBaudRateMode));
3284       MODIFY_REG(huart->Instance->CR2, USART_CR2_ABRMODE, huart->AdvancedInit.AutoBaudRateMode);
3285     }
3286   }
3287 
3288   /* if required, configure MSB first on communication line */
3289   if (HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_MSBFIRST_INIT))
3290   {
3291     assert_param(IS_UART_ADVFEATURE_MSBFIRST(huart->AdvancedInit.MSBFirst));
3292     MODIFY_REG(huart->Instance->CR2, USART_CR2_MSBFIRST, huart->AdvancedInit.MSBFirst);
3293   }
3294 }
3295 
3296 /**
3297   * @brief Check the UART Idle State.
3298   * @param huart UART handle.
3299   * @retval HAL status
3300   */
UART_CheckIdleState(UART_HandleTypeDef * huart)3301 HAL_StatusTypeDef UART_CheckIdleState(UART_HandleTypeDef *huart)
3302 {
3303   uint32_t tickstart;
3304 
3305   /* Initialize the UART ErrorCode */
3306   huart->ErrorCode = HAL_UART_ERROR_NONE;
3307 
3308   /* Init tickstart for timeout management */
3309   tickstart = HAL_GetTick();
3310 
3311   /* Check if the Transmitter is enabled */
3312   if ((huart->Instance->CR1 & USART_CR1_TE) == USART_CR1_TE)
3313   {
3314     /* Wait until TEACK flag is set */
3315     if (UART_WaitOnFlagUntilTimeout(huart, USART_ISR_TEACK, RESET, tickstart, HAL_UART_TIMEOUT_VALUE) != HAL_OK)
3316     {
3317       /* Disable TXE interrupt for the interrupt process */
3318       ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TXEIE_TXFNFIE));
3319 
3320       huart->gState = HAL_UART_STATE_READY;
3321 
3322       __HAL_UNLOCK(huart);
3323 
3324       /* Timeout occurred */
3325       return HAL_TIMEOUT;
3326     }
3327   }
3328 
3329   /* Check if the Receiver is enabled */
3330   if ((huart->Instance->CR1 & USART_CR1_RE) == USART_CR1_RE)
3331   {
3332     /* Wait until REACK flag is set */
3333     if (UART_WaitOnFlagUntilTimeout(huart, USART_ISR_REACK, RESET, tickstart, HAL_UART_TIMEOUT_VALUE) != HAL_OK)
3334     {
3335       /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error)
3336       interrupts for the interrupt process */
3337       ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
3338       ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
3339 
3340       huart->RxState = HAL_UART_STATE_READY;
3341 
3342       __HAL_UNLOCK(huart);
3343 
3344       /* Timeout occurred */
3345       return HAL_TIMEOUT;
3346     }
3347   }
3348 
3349   /* Initialize the UART State */
3350   huart->gState = HAL_UART_STATE_READY;
3351   huart->RxState = HAL_UART_STATE_READY;
3352   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
3353   huart->RxEventType = HAL_UART_RXEVENT_TC;
3354 
3355   __HAL_UNLOCK(huart);
3356 
3357   return HAL_OK;
3358 }
3359 
3360 /**
3361   * @brief  This function handles UART Communication Timeout. It waits
3362   *                  until a flag is no longer in the specified status.
3363   * @param huart     UART handle.
3364   * @param Flag      Specifies the UART flag to check
3365   * @param Status    The actual Flag status (SET or RESET)
3366   * @param Tickstart Tick start value
3367   * @param Timeout   Timeout duration
3368   * @retval HAL status
3369   */
UART_WaitOnFlagUntilTimeout(UART_HandleTypeDef * huart,uint32_t Flag,FlagStatus Status,uint32_t Tickstart,uint32_t Timeout)3370 HAL_StatusTypeDef UART_WaitOnFlagUntilTimeout(UART_HandleTypeDef *huart, uint32_t Flag, FlagStatus Status,
3371                                               uint32_t Tickstart, uint32_t Timeout)
3372 {
3373   /* Wait until flag is set */
3374   while ((__HAL_UART_GET_FLAG(huart, Flag) ? SET : RESET) == Status)
3375   {
3376     /* Check for the Timeout */
3377     if (Timeout != HAL_MAX_DELAY)
3378     {
3379       if (((HAL_GetTick() - Tickstart) > Timeout) || (Timeout == 0U))
3380       {
3381 
3382         return HAL_TIMEOUT;
3383       }
3384 
3385       if (READ_BIT(huart->Instance->CR1, USART_CR1_RE) != 0U)
3386       {
3387         if (__HAL_UART_GET_FLAG(huart, UART_FLAG_ORE) == SET)
3388         {
3389            /* Clear Overrun Error flag*/
3390            __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF);
3391 
3392            /* Blocking error : transfer is aborted
3393            Set the UART state ready to be able to start again the process,
3394            Disable Rx Interrupts if ongoing */
3395            UART_EndRxTransfer(huart);
3396 
3397            huart->ErrorCode = HAL_UART_ERROR_ORE;
3398 
3399            /* Process Unlocked */
3400            __HAL_UNLOCK(huart);
3401 
3402            return HAL_ERROR;
3403         }
3404         if (__HAL_UART_GET_FLAG(huart, UART_FLAG_RTOF) == SET)
3405         {
3406           /* Clear Receiver Timeout flag*/
3407           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_RTOF);
3408 
3409           /* Blocking error : transfer is aborted
3410           Set the UART state ready to be able to start again the process,
3411           Disable Rx Interrupts if ongoing */
3412           UART_EndRxTransfer(huart);
3413 
3414           huart->ErrorCode = HAL_UART_ERROR_RTO;
3415 
3416           /* Process Unlocked */
3417           __HAL_UNLOCK(huart);
3418 
3419           return HAL_TIMEOUT;
3420         }
3421       }
3422     }
3423   }
3424   return HAL_OK;
3425 }
3426 
3427 /**
3428   * @brief  Start Receive operation in interrupt mode.
3429   * @note   This function could be called by all HAL UART API providing reception in Interrupt mode.
3430   * @note   When calling this function, parameters validity is considered as already checked,
3431   *         i.e. Rx State, buffer address, ...
3432   *         UART Handle is assumed as Locked.
3433   * @param  huart UART handle.
3434   * @param  pData Pointer to data buffer (u8 or u16 data elements).
3435   * @param  Size  Amount of data elements (u8 or u16) to be received.
3436   * @retval HAL status
3437   */
UART_Start_Receive_IT(UART_HandleTypeDef * huart,uint8_t * pData,uint16_t Size)3438 HAL_StatusTypeDef UART_Start_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
3439 {
3440   huart->pRxBuffPtr  = pData;
3441   huart->RxXferSize  = Size;
3442   huart->RxXferCount = Size;
3443   huart->RxISR       = NULL;
3444 
3445   /* Computation of UART mask to apply to RDR register */
3446   UART_MASK_COMPUTATION(huart);
3447 
3448   huart->ErrorCode = HAL_UART_ERROR_NONE;
3449   huart->RxState = HAL_UART_STATE_BUSY_RX;
3450 
3451   /* Enable the UART Error Interrupt: (Frame error, noise error, overrun error) */
3452   ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_EIE);
3453 
3454   /* Configure Rx interrupt processing */
3455   if ((huart->FifoMode == UART_FIFOMODE_ENABLE) && (Size >= huart->NbRxDataToProcess))
3456   {
3457     /* Set the Rx ISR function pointer according to the data word length */
3458     if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
3459     {
3460       huart->RxISR = UART_RxISR_16BIT_FIFOEN;
3461     }
3462     else
3463     {
3464       huart->RxISR = UART_RxISR_8BIT_FIFOEN;
3465     }
3466 
3467     /* Enable the UART Parity Error interrupt and RX FIFO Threshold interrupt */
3468     if (huart->Init.Parity != UART_PARITY_NONE)
3469     {
3470       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_PEIE);
3471     }
3472     ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_RXFTIE);
3473   }
3474   else
3475   {
3476     /* Set the Rx ISR function pointer according to the data word length */
3477     if ((huart->Init.WordLength == UART_WORDLENGTH_9B) && (huart->Init.Parity == UART_PARITY_NONE))
3478     {
3479       huart->RxISR = UART_RxISR_16BIT;
3480     }
3481     else
3482     {
3483       huart->RxISR = UART_RxISR_8BIT;
3484     }
3485 
3486     /* Enable the UART Parity Error interrupt and Data Register Not Empty interrupt */
3487     if (huart->Init.Parity != UART_PARITY_NONE)
3488     {
3489       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_PEIE | USART_CR1_RXNEIE_RXFNEIE);
3490     }
3491     else
3492     {
3493       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
3494     }
3495   }
3496   return HAL_OK;
3497 }
3498 
3499 /**
3500   * @brief  Start Receive operation in DMA mode.
3501   * @note   This function could be called by all HAL UART API providing reception in DMA mode.
3502   * @note   When calling this function, parameters validity is considered as already checked,
3503   *         i.e. Rx State, buffer address, ...
3504   *         UART Handle is assumed as Locked.
3505   * @param  huart UART handle.
3506   * @param  pData Pointer to data buffer (u8 or u16 data elements).
3507   * @param  Size  Amount of data elements (u8 or u16) to be received.
3508   * @retval HAL status
3509   */
UART_Start_Receive_DMA(UART_HandleTypeDef * huart,uint8_t * pData,uint16_t Size)3510 HAL_StatusTypeDef UART_Start_Receive_DMA(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
3511 {
3512   huart->pRxBuffPtr = pData;
3513   huart->RxXferSize = Size;
3514 
3515   huart->ErrorCode = HAL_UART_ERROR_NONE;
3516   huart->RxState = HAL_UART_STATE_BUSY_RX;
3517 
3518   if (huart->hdmarx != NULL)
3519   {
3520     /* Set the UART DMA transfer complete callback */
3521     huart->hdmarx->XferCpltCallback = UART_DMAReceiveCplt;
3522 
3523     /* Set the UART DMA Half transfer complete callback */
3524     huart->hdmarx->XferHalfCpltCallback = UART_DMARxHalfCplt;
3525 
3526     /* Set the DMA error callback */
3527     huart->hdmarx->XferErrorCallback = UART_DMAError;
3528 
3529     /* Set the DMA abort callback */
3530     huart->hdmarx->XferAbortCallback = NULL;
3531 
3532     /* Enable the DMA channel */
3533     if (HAL_DMA_Start_IT(huart->hdmarx, (uint32_t)&huart->Instance->RDR, (uint32_t)huart->pRxBuffPtr, Size) != HAL_OK)
3534     {
3535       /* Set error code to DMA */
3536       huart->ErrorCode = HAL_UART_ERROR_DMA;
3537 
3538       /* Restore huart->RxState to ready */
3539       huart->RxState = HAL_UART_STATE_READY;
3540 
3541       return HAL_ERROR;
3542     }
3543   }
3544 
3545   /* Enable the UART Parity Error Interrupt */
3546   if (huart->Init.Parity != UART_PARITY_NONE)
3547   {
3548     ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_PEIE);
3549   }
3550 
3551   /* Enable the UART Error Interrupt: (Frame error, noise error, overrun error) */
3552   ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_EIE);
3553 
3554   /* Enable the DMA transfer for the receiver request by setting the DMAR bit
3555   in the UART CR3 register */
3556   ATOMIC_SET_BIT(huart->Instance->CR3, USART_CR3_DMAR);
3557 
3558   return HAL_OK;
3559 }
3560 
3561 
3562 /**
3563   * @brief  End ongoing Tx transfer on UART peripheral (following error detection or Transmit completion).
3564   * @param  huart UART handle.
3565   * @retval None
3566   */
UART_EndTxTransfer(UART_HandleTypeDef * huart)3567 static void UART_EndTxTransfer(UART_HandleTypeDef *huart)
3568 {
3569   /* Disable TXEIE, TCIE, TXFT interrupts */
3570   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_TXEIE_TXFNFIE | USART_CR1_TCIE));
3571   ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_TXFTIE));
3572 
3573   /* At end of Tx process, restore huart->gState to Ready */
3574   huart->gState = HAL_UART_STATE_READY;
3575 }
3576 
3577 
3578 /**
3579   * @brief  End ongoing Rx transfer on UART peripheral (following error detection or Reception completion).
3580   * @param  huart UART handle.
3581   * @retval None
3582   */
UART_EndRxTransfer(UART_HandleTypeDef * huart)3583 static void UART_EndRxTransfer(UART_HandleTypeDef *huart)
3584 {
3585   /* Disable RXNE, PE and ERR (Frame error, noise error, overrun error) interrupts */
3586   ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
3587   ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
3588 
3589   /* In case of reception waiting for IDLE event, disable also the IDLE IE interrupt source */
3590   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
3591   {
3592     ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
3593   }
3594 
3595   /* At end of Rx process, restore huart->RxState to Ready */
3596   huart->RxState = HAL_UART_STATE_READY;
3597   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
3598 
3599   /* Reset RxIsr function pointer */
3600   huart->RxISR = NULL;
3601 }
3602 
3603 
3604 /**
3605   * @brief DMA UART transmit process complete callback.
3606   * @param hdma DMA handle.
3607   * @retval None
3608   */
UART_DMATransmitCplt(DMA_HandleTypeDef * hdma)3609 static void UART_DMATransmitCplt(DMA_HandleTypeDef *hdma)
3610 {
3611   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3612 
3613   /* DMA Normal mode */
3614   if (HAL_IS_BIT_CLR(hdma->Instance->CCR, DMA_CCR_CIRC))
3615   {
3616     huart->TxXferCount = 0U;
3617 
3618     /* Disable the DMA transfer for transmit request by resetting the DMAT bit
3619        in the UART CR3 register */
3620     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAT);
3621 
3622     /* Enable the UART Transmit Complete Interrupt */
3623     ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TCIE);
3624   }
3625   /* DMA Circular mode */
3626   else
3627   {
3628 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3629     /*Call registered Tx complete callback*/
3630     huart->TxCpltCallback(huart);
3631 #else
3632     /*Call legacy weak Tx complete callback*/
3633     HAL_UART_TxCpltCallback(huart);
3634 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3635   }
3636 }
3637 
3638 /**
3639   * @brief DMA UART transmit process half complete callback.
3640   * @param hdma DMA handle.
3641   * @retval None
3642   */
UART_DMATxHalfCplt(DMA_HandleTypeDef * hdma)3643 static void UART_DMATxHalfCplt(DMA_HandleTypeDef *hdma)
3644 {
3645   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3646 
3647 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3648   /*Call registered Tx Half complete callback*/
3649   huart->TxHalfCpltCallback(huart);
3650 #else
3651   /*Call legacy weak Tx Half complete callback*/
3652   HAL_UART_TxHalfCpltCallback(huart);
3653 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3654 }
3655 
3656 /**
3657   * @brief DMA UART receive process complete callback.
3658   * @param hdma DMA handle.
3659   * @retval None
3660   */
UART_DMAReceiveCplt(DMA_HandleTypeDef * hdma)3661 static void UART_DMAReceiveCplt(DMA_HandleTypeDef *hdma)
3662 {
3663   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3664 
3665   /* DMA Normal mode */
3666   if (HAL_IS_BIT_CLR(hdma->Instance->CCR, DMA_CCR_CIRC))
3667   {
3668     huart->RxXferCount = 0U;
3669 
3670     /* Disable PE and ERR (Frame error, noise error, overrun error) interrupts */
3671     ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_PEIE);
3672     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
3673 
3674     /* Disable the DMA transfer for the receiver request by resetting the DMAR bit
3675        in the UART CR3 register */
3676     ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_DMAR);
3677 
3678     /* At end of Rx process, restore huart->RxState to Ready */
3679     huart->RxState = HAL_UART_STATE_READY;
3680 
3681     /* If Reception till IDLE event has been selected, Disable IDLE Interrupt */
3682     if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
3683     {
3684       ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
3685     }
3686   }
3687 
3688   /* Initialize type of RxEvent that correspond to RxEvent callback execution;
3689      In this case, Rx Event type is Transfer Complete */
3690   huart->RxEventType = HAL_UART_RXEVENT_TC;
3691 
3692   /* Check current reception Mode :
3693      If Reception till IDLE event has been selected : use Rx Event callback */
3694   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
3695   {
3696 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3697     /*Call registered Rx Event callback*/
3698     huart->RxEventCallback(huart, huart->RxXferSize);
3699 #else
3700     /*Call legacy weak Rx Event callback*/
3701     HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize);
3702 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3703   }
3704   else
3705   {
3706     /* In other cases : use Rx Complete callback */
3707 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3708     /*Call registered Rx complete callback*/
3709     huart->RxCpltCallback(huart);
3710 #else
3711     /*Call legacy weak Rx complete callback*/
3712     HAL_UART_RxCpltCallback(huart);
3713 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3714   }
3715 }
3716 
3717 /**
3718   * @brief DMA UART receive process half complete callback.
3719   * @param hdma DMA handle.
3720   * @retval None
3721   */
UART_DMARxHalfCplt(DMA_HandleTypeDef * hdma)3722 static void UART_DMARxHalfCplt(DMA_HandleTypeDef *hdma)
3723 {
3724   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3725 
3726   /* Initialize type of RxEvent that correspond to RxEvent callback execution;
3727      In this case, Rx Event type is Half Transfer */
3728   huart->RxEventType = HAL_UART_RXEVENT_HT;
3729 
3730   /* Check current reception Mode :
3731      If Reception till IDLE event has been selected : use Rx Event callback */
3732   if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
3733   {
3734 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3735     /*Call registered Rx Event callback*/
3736     huart->RxEventCallback(huart, huart->RxXferSize / 2U);
3737 #else
3738     /*Call legacy weak Rx Event callback*/
3739     HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize / 2U);
3740 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3741   }
3742   else
3743   {
3744     /* In other cases : use Rx Half Complete callback */
3745 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3746     /*Call registered Rx Half complete callback*/
3747     huart->RxHalfCpltCallback(huart);
3748 #else
3749     /*Call legacy weak Rx Half complete callback*/
3750     HAL_UART_RxHalfCpltCallback(huart);
3751 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3752   }
3753 }
3754 
3755 /**
3756   * @brief DMA UART communication error callback.
3757   * @param hdma DMA handle.
3758   * @retval None
3759   */
UART_DMAError(DMA_HandleTypeDef * hdma)3760 static void UART_DMAError(DMA_HandleTypeDef *hdma)
3761 {
3762   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3763 
3764   const HAL_UART_StateTypeDef gstate = huart->gState;
3765   const HAL_UART_StateTypeDef rxstate = huart->RxState;
3766 
3767   /* Stop UART DMA Tx request if ongoing */
3768   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAT)) &&
3769       (gstate == HAL_UART_STATE_BUSY_TX))
3770   {
3771     huart->TxXferCount = 0U;
3772     UART_EndTxTransfer(huart);
3773   }
3774 
3775   /* Stop UART DMA Rx request if ongoing */
3776   if ((HAL_IS_BIT_SET(huart->Instance->CR3, USART_CR3_DMAR)) &&
3777       (rxstate == HAL_UART_STATE_BUSY_RX))
3778   {
3779     huart->RxXferCount = 0U;
3780     UART_EndRxTransfer(huart);
3781   }
3782 
3783   huart->ErrorCode |= HAL_UART_ERROR_DMA;
3784 
3785 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3786   /*Call registered error callback*/
3787   huart->ErrorCallback(huart);
3788 #else
3789   /*Call legacy weak error callback*/
3790   HAL_UART_ErrorCallback(huart);
3791 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3792 }
3793 
3794 /**
3795   * @brief  DMA UART communication abort callback, when initiated by HAL services on Error
3796   *         (To be called at end of DMA Abort procedure following error occurrence).
3797   * @param  hdma DMA handle.
3798   * @retval None
3799   */
UART_DMAAbortOnError(DMA_HandleTypeDef * hdma)3800 static void UART_DMAAbortOnError(DMA_HandleTypeDef *hdma)
3801 {
3802   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3803   huart->RxXferCount = 0U;
3804   huart->TxXferCount = 0U;
3805 
3806 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3807   /*Call registered error callback*/
3808   huart->ErrorCallback(huart);
3809 #else
3810   /*Call legacy weak error callback*/
3811   HAL_UART_ErrorCallback(huart);
3812 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3813 }
3814 
3815 /**
3816   * @brief  DMA UART Tx communication abort callback, when initiated by user
3817   *         (To be called at end of DMA Tx Abort procedure following user abort request).
3818   * @note   When this callback is executed, User Abort complete call back is called only if no
3819   *         Abort still ongoing for Rx DMA Handle.
3820   * @param  hdma DMA handle.
3821   * @retval None
3822   */
UART_DMATxAbortCallback(DMA_HandleTypeDef * hdma)3823 static void UART_DMATxAbortCallback(DMA_HandleTypeDef *hdma)
3824 {
3825   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3826 
3827   huart->hdmatx->XferAbortCallback = NULL;
3828 
3829   /* Check if an Abort process is still ongoing */
3830   if (huart->hdmarx != NULL)
3831   {
3832     if (huart->hdmarx->XferAbortCallback != NULL)
3833     {
3834       return;
3835     }
3836   }
3837 
3838   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
3839   huart->TxXferCount = 0U;
3840   huart->RxXferCount = 0U;
3841 
3842   /* Reset errorCode */
3843   huart->ErrorCode = HAL_UART_ERROR_NONE;
3844 
3845   /* Clear the Error flags in the ICR register */
3846   __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
3847 
3848   /* Flush the whole TX FIFO (if needed) */
3849   if (huart->FifoMode == UART_FIFOMODE_ENABLE)
3850   {
3851     __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
3852   }
3853 
3854   /* Restore huart->gState and huart->RxState to Ready */
3855   huart->gState  = HAL_UART_STATE_READY;
3856   huart->RxState = HAL_UART_STATE_READY;
3857   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
3858 
3859   /* Call user Abort complete callback */
3860 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3861   /* Call registered Abort complete callback */
3862   huart->AbortCpltCallback(huart);
3863 #else
3864   /* Call legacy weak Abort complete callback */
3865   HAL_UART_AbortCpltCallback(huart);
3866 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3867 }
3868 
3869 
3870 /**
3871   * @brief  DMA UART Rx communication abort callback, when initiated by user
3872   *         (To be called at end of DMA Rx Abort procedure following user abort request).
3873   * @note   When this callback is executed, User Abort complete call back is called only if no
3874   *         Abort still ongoing for Tx DMA Handle.
3875   * @param  hdma DMA handle.
3876   * @retval None
3877   */
UART_DMARxAbortCallback(DMA_HandleTypeDef * hdma)3878 static void UART_DMARxAbortCallback(DMA_HandleTypeDef *hdma)
3879 {
3880   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3881 
3882   huart->hdmarx->XferAbortCallback = NULL;
3883 
3884   /* Check if an Abort process is still ongoing */
3885   if (huart->hdmatx != NULL)
3886   {
3887     if (huart->hdmatx->XferAbortCallback != NULL)
3888     {
3889       return;
3890     }
3891   }
3892 
3893   /* No Abort process still ongoing : All DMA channels are aborted, call user Abort Complete callback */
3894   huart->TxXferCount = 0U;
3895   huart->RxXferCount = 0U;
3896 
3897   /* Reset errorCode */
3898   huart->ErrorCode = HAL_UART_ERROR_NONE;
3899 
3900   /* Clear the Error flags in the ICR register */
3901   __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
3902 
3903   /* Discard the received data */
3904   __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
3905 
3906   /* Restore huart->gState and huart->RxState to Ready */
3907   huart->gState  = HAL_UART_STATE_READY;
3908   huart->RxState = HAL_UART_STATE_READY;
3909   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
3910 
3911   /* Call user Abort complete callback */
3912 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3913   /* Call registered Abort complete callback */
3914   huart->AbortCpltCallback(huart);
3915 #else
3916   /* Call legacy weak Abort complete callback */
3917   HAL_UART_AbortCpltCallback(huart);
3918 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3919 }
3920 
3921 
3922 /**
3923   * @brief  DMA UART Tx communication abort callback, when initiated by user by a call to
3924   *         HAL_UART_AbortTransmit_IT API (Abort only Tx transfer)
3925   *         (This callback is executed at end of DMA Tx Abort procedure following user abort request,
3926   *         and leads to user Tx Abort Complete callback execution).
3927   * @param  hdma DMA handle.
3928   * @retval None
3929   */
UART_DMATxOnlyAbortCallback(DMA_HandleTypeDef * hdma)3930 static void UART_DMATxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
3931 {
3932   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)(hdma->Parent);
3933 
3934   huart->TxXferCount = 0U;
3935 
3936   /* Flush the whole TX FIFO (if needed) */
3937   if (huart->FifoMode == UART_FIFOMODE_ENABLE)
3938   {
3939     __HAL_UART_SEND_REQ(huart, UART_TXDATA_FLUSH_REQUEST);
3940   }
3941 
3942   /* Restore huart->gState to Ready */
3943   huart->gState = HAL_UART_STATE_READY;
3944 
3945   /* Call user Abort complete callback */
3946 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3947   /* Call registered Abort Transmit Complete Callback */
3948   huart->AbortTransmitCpltCallback(huart);
3949 #else
3950   /* Call legacy weak Abort Transmit Complete Callback */
3951   HAL_UART_AbortTransmitCpltCallback(huart);
3952 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3953 }
3954 
3955 /**
3956   * @brief  DMA UART Rx communication abort callback, when initiated by user by a call to
3957   *         HAL_UART_AbortReceive_IT API (Abort only Rx transfer)
3958   *         (This callback is executed at end of DMA Rx Abort procedure following user abort request,
3959   *         and leads to user Rx Abort Complete callback execution).
3960   * @param  hdma DMA handle.
3961   * @retval None
3962   */
UART_DMARxOnlyAbortCallback(DMA_HandleTypeDef * hdma)3963 static void UART_DMARxOnlyAbortCallback(DMA_HandleTypeDef *hdma)
3964 {
3965   UART_HandleTypeDef *huart = (UART_HandleTypeDef *)((DMA_HandleTypeDef *)hdma)->Parent;
3966 
3967   huart->RxXferCount = 0U;
3968 
3969   /* Clear the Error flags in the ICR register */
3970   __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_OREF | UART_CLEAR_NEF | UART_CLEAR_PEF | UART_CLEAR_FEF);
3971 
3972   /* Discard the received data */
3973   __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
3974 
3975   /* Restore huart->RxState to Ready */
3976   huart->RxState = HAL_UART_STATE_READY;
3977   huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
3978 
3979   /* Call user Abort complete callback */
3980 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
3981   /* Call registered Abort Receive Complete Callback */
3982   huart->AbortReceiveCpltCallback(huart);
3983 #else
3984   /* Call legacy weak Abort Receive Complete Callback */
3985   HAL_UART_AbortReceiveCpltCallback(huart);
3986 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
3987 }
3988 
3989 /**
3990   * @brief TX interrupt handler for 7 or 8 bits data word length .
3991   * @note   Function is called under interruption only, once
3992   *         interruptions have been enabled by HAL_UART_Transmit_IT().
3993   * @param huart UART handle.
3994   * @retval None
3995   */
UART_TxISR_8BIT(UART_HandleTypeDef * huart)3996 static void UART_TxISR_8BIT(UART_HandleTypeDef *huart)
3997 {
3998   /* Check that a Tx process is ongoing */
3999   if (huart->gState == HAL_UART_STATE_BUSY_TX)
4000   {
4001     if (huart->TxXferCount == 0U)
4002     {
4003       /* Disable the UART Transmit Data Register Empty Interrupt */
4004       ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
4005 
4006       /* Enable the UART Transmit Complete Interrupt */
4007       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TCIE);
4008     }
4009     else
4010     {
4011       huart->Instance->TDR = (uint8_t)(*huart->pTxBuffPtr & (uint8_t)0xFF);
4012       huart->pTxBuffPtr++;
4013       huart->TxXferCount--;
4014     }
4015   }
4016 }
4017 
4018 /**
4019   * @brief TX interrupt handler for 9 bits data word length.
4020   * @note   Function is called under interruption only, once
4021   *         interruptions have been enabled by HAL_UART_Transmit_IT().
4022   * @param huart UART handle.
4023   * @retval None
4024   */
UART_TxISR_16BIT(UART_HandleTypeDef * huart)4025 static void UART_TxISR_16BIT(UART_HandleTypeDef *huart)
4026 {
4027   const uint16_t *tmp;
4028 
4029   /* Check that a Tx process is ongoing */
4030   if (huart->gState == HAL_UART_STATE_BUSY_TX)
4031   {
4032     if (huart->TxXferCount == 0U)
4033     {
4034       /* Disable the UART Transmit Data Register Empty Interrupt */
4035       ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_TXEIE_TXFNFIE);
4036 
4037       /* Enable the UART Transmit Complete Interrupt */
4038       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TCIE);
4039     }
4040     else
4041     {
4042       tmp = (const uint16_t *) huart->pTxBuffPtr;
4043       huart->Instance->TDR = (((uint32_t)(*tmp)) & 0x01FFUL);
4044       huart->pTxBuffPtr += 2U;
4045       huart->TxXferCount--;
4046     }
4047   }
4048 }
4049 
4050 /**
4051   * @brief TX interrupt handler for 7 or 8 bits data word length and FIFO mode is enabled.
4052   * @note   Function is called under interruption only, once
4053   *         interruptions have been enabled by HAL_UART_Transmit_IT().
4054   * @param huart UART handle.
4055   * @retval None
4056   */
UART_TxISR_8BIT_FIFOEN(UART_HandleTypeDef * huart)4057 static void UART_TxISR_8BIT_FIFOEN(UART_HandleTypeDef *huart)
4058 {
4059   uint16_t  nb_tx_data;
4060 
4061   /* Check that a Tx process is ongoing */
4062   if (huart->gState == HAL_UART_STATE_BUSY_TX)
4063   {
4064     for (nb_tx_data = huart->NbTxDataToProcess ; nb_tx_data > 0U ; nb_tx_data--)
4065     {
4066       if (huart->TxXferCount == 0U)
4067       {
4068         /* Disable the TX FIFO threshold interrupt */
4069         ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_TXFTIE);
4070 
4071         /* Enable the UART Transmit Complete Interrupt */
4072         ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TCIE);
4073 
4074         break; /* force exit loop */
4075       }
4076       else if (READ_BIT(huart->Instance->ISR, USART_ISR_TXE_TXFNF) != 0U)
4077       {
4078         huart->Instance->TDR = (uint8_t)(*huart->pTxBuffPtr & (uint8_t)0xFF);
4079         huart->pTxBuffPtr++;
4080         huart->TxXferCount--;
4081       }
4082       else
4083       {
4084         /* Nothing to do */
4085       }
4086     }
4087   }
4088 }
4089 
4090 /**
4091   * @brief TX interrupt handler for 9 bits data word length and FIFO mode is enabled.
4092   * @note   Function is called under interruption only, once
4093   *         interruptions have been enabled by HAL_UART_Transmit_IT().
4094   * @param huart UART handle.
4095   * @retval None
4096   */
UART_TxISR_16BIT_FIFOEN(UART_HandleTypeDef * huart)4097 static void UART_TxISR_16BIT_FIFOEN(UART_HandleTypeDef *huart)
4098 {
4099   const uint16_t *tmp;
4100   uint16_t  nb_tx_data;
4101 
4102   /* Check that a Tx process is ongoing */
4103   if (huart->gState == HAL_UART_STATE_BUSY_TX)
4104   {
4105     for (nb_tx_data = huart->NbTxDataToProcess ; nb_tx_data > 0U ; nb_tx_data--)
4106     {
4107       if (huart->TxXferCount == 0U)
4108       {
4109         /* Disable the TX FIFO threshold interrupt */
4110         ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_TXFTIE);
4111 
4112         /* Enable the UART Transmit Complete Interrupt */
4113         ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_TCIE);
4114 
4115         break; /* force exit loop */
4116       }
4117       else if (READ_BIT(huart->Instance->ISR, USART_ISR_TXE_TXFNF) != 0U)
4118       {
4119         tmp = (const uint16_t *) huart->pTxBuffPtr;
4120         huart->Instance->TDR = (((uint32_t)(*tmp)) & 0x01FFUL);
4121         huart->pTxBuffPtr += 2U;
4122         huart->TxXferCount--;
4123       }
4124       else
4125       {
4126         /* Nothing to do */
4127       }
4128     }
4129   }
4130 }
4131 
4132 /**
4133   * @brief  Wrap up transmission in non-blocking mode.
4134   * @param  huart pointer to a UART_HandleTypeDef structure that contains
4135   *                the configuration information for the specified UART module.
4136   * @retval None
4137   */
UART_EndTransmit_IT(UART_HandleTypeDef * huart)4138 static void UART_EndTransmit_IT(UART_HandleTypeDef *huart)
4139 {
4140   /* Disable the UART Transmit Complete Interrupt */
4141   ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_TCIE);
4142 
4143   /* Tx process is ended, restore huart->gState to Ready */
4144   huart->gState = HAL_UART_STATE_READY;
4145 
4146   /* Cleat TxISR function pointer */
4147   huart->TxISR = NULL;
4148 
4149 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4150   /*Call registered Tx complete callback*/
4151   huart->TxCpltCallback(huart);
4152 #else
4153   /*Call legacy weak Tx complete callback*/
4154   HAL_UART_TxCpltCallback(huart);
4155 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4156 }
4157 
4158 /**
4159   * @brief RX interrupt handler for 7 or 8 bits data word length .
4160   * @param huart UART handle.
4161   * @retval None
4162   */
UART_RxISR_8BIT(UART_HandleTypeDef * huart)4163 static void UART_RxISR_8BIT(UART_HandleTypeDef *huart)
4164 {
4165   uint16_t uhMask = huart->Mask;
4166   uint16_t  uhdata;
4167 
4168   /* Check that a Rx process is ongoing */
4169   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
4170   {
4171     uhdata = (uint16_t) READ_REG(huart->Instance->RDR);
4172     *huart->pRxBuffPtr = (uint8_t)(uhdata & (uint8_t)uhMask);
4173     huart->pRxBuffPtr++;
4174     huart->RxXferCount--;
4175 
4176     if (huart->RxXferCount == 0U)
4177     {
4178       /* Disable the UART Parity Error Interrupt and RXNE interrupts */
4179       ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
4180 
4181       /* Disable the UART Error Interrupt: (Frame error, noise error, overrun error) */
4182       ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
4183 
4184       /* Rx process is completed, restore huart->RxState to Ready */
4185       huart->RxState = HAL_UART_STATE_READY;
4186 
4187       /* Clear RxISR function pointer */
4188       huart->RxISR = NULL;
4189 
4190       /* Initialize type of RxEvent to Transfer Complete */
4191       huart->RxEventType = HAL_UART_RXEVENT_TC;
4192 
4193       if (!(IS_LPUART_INSTANCE(huart->Instance)))
4194       {
4195         /* Check that USART RTOEN bit is set */
4196         if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
4197         {
4198           /* Enable the UART Receiver Timeout Interrupt */
4199           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
4200         }
4201       }
4202 
4203       /* Check current reception Mode :
4204          If Reception till IDLE event has been selected : */
4205       if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
4206       {
4207         /* Set reception type to Standard */
4208         huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
4209 
4210         /* Disable IDLE interrupt */
4211         ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
4212 
4213         if (__HAL_UART_GET_FLAG(huart, UART_FLAG_IDLE) == SET)
4214         {
4215           /* Clear IDLE Flag */
4216           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_IDLEF);
4217         }
4218 
4219 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4220         /*Call registered Rx Event callback*/
4221         huart->RxEventCallback(huart, huart->RxXferSize);
4222 #else
4223         /*Call legacy weak Rx Event callback*/
4224         HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize);
4225 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
4226       }
4227       else
4228       {
4229         /* Standard reception API called */
4230 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4231         /*Call registered Rx complete callback*/
4232         huart->RxCpltCallback(huart);
4233 #else
4234         /*Call legacy weak Rx complete callback*/
4235         HAL_UART_RxCpltCallback(huart);
4236 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4237       }
4238     }
4239   }
4240   else
4241   {
4242     /* Clear RXNE interrupt flag */
4243     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
4244   }
4245 }
4246 
4247 /**
4248   * @brief RX interrupt handler for 9 bits data word length .
4249   * @note   Function is called under interruption only, once
4250   *         interruptions have been enabled by HAL_UART_Receive_IT()
4251   * @param huart UART handle.
4252   * @retval None
4253   */
UART_RxISR_16BIT(UART_HandleTypeDef * huart)4254 static void UART_RxISR_16BIT(UART_HandleTypeDef *huart)
4255 {
4256   uint16_t *tmp;
4257   uint16_t uhMask = huart->Mask;
4258   uint16_t  uhdata;
4259 
4260   /* Check that a Rx process is ongoing */
4261   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
4262   {
4263     uhdata = (uint16_t) READ_REG(huart->Instance->RDR);
4264     tmp = (uint16_t *) huart->pRxBuffPtr ;
4265     *tmp = (uint16_t)(uhdata & uhMask);
4266     huart->pRxBuffPtr += 2U;
4267     huart->RxXferCount--;
4268 
4269     if (huart->RxXferCount == 0U)
4270     {
4271       /* Disable the UART Parity Error Interrupt and RXNE interrupt*/
4272       ATOMIC_CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
4273 
4274       /* Disable the UART Error Interrupt: (Frame error, noise error, overrun error) */
4275       ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);
4276 
4277       /* Rx process is completed, restore huart->RxState to Ready */
4278       huart->RxState = HAL_UART_STATE_READY;
4279 
4280       /* Clear RxISR function pointer */
4281       huart->RxISR = NULL;
4282 
4283       /* Initialize type of RxEvent to Transfer Complete */
4284       huart->RxEventType = HAL_UART_RXEVENT_TC;
4285 
4286       if (!(IS_LPUART_INSTANCE(huart->Instance)))
4287       {
4288         /* Check that USART RTOEN bit is set */
4289         if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
4290         {
4291           /* Enable the UART Receiver Timeout Interrupt */
4292           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
4293         }
4294       }
4295 
4296       /* Check current reception Mode :
4297          If Reception till IDLE event has been selected : */
4298       if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
4299       {
4300         /* Set reception type to Standard */
4301         huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
4302 
4303         /* Disable IDLE interrupt */
4304         ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
4305 
4306         if (__HAL_UART_GET_FLAG(huart, UART_FLAG_IDLE) == SET)
4307         {
4308           /* Clear IDLE Flag */
4309           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_IDLEF);
4310         }
4311 
4312 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4313         /*Call registered Rx Event callback*/
4314         huart->RxEventCallback(huart, huart->RxXferSize);
4315 #else
4316         /*Call legacy weak Rx Event callback*/
4317         HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize);
4318 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
4319       }
4320       else
4321       {
4322         /* Standard reception API called */
4323 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4324         /*Call registered Rx complete callback*/
4325         huart->RxCpltCallback(huart);
4326 #else
4327         /*Call legacy weak Rx complete callback*/
4328         HAL_UART_RxCpltCallback(huart);
4329 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4330       }
4331     }
4332   }
4333   else
4334   {
4335     /* Clear RXNE interrupt flag */
4336     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
4337   }
4338 }
4339 
4340 /**
4341   * @brief RX interrupt handler for 7 or 8  bits data word length and FIFO mode is enabled.
4342   * @note   Function is called under interruption only, once
4343   *         interruptions have been enabled by HAL_UART_Receive_IT()
4344   * @param huart UART handle.
4345   * @retval None
4346   */
UART_RxISR_8BIT_FIFOEN(UART_HandleTypeDef * huart)4347 static void UART_RxISR_8BIT_FIFOEN(UART_HandleTypeDef *huart)
4348 {
4349   uint16_t  uhMask = huart->Mask;
4350   uint16_t  uhdata;
4351   uint16_t  nb_rx_data;
4352   uint16_t  rxdatacount;
4353   uint32_t  isrflags = READ_REG(huart->Instance->ISR);
4354   uint32_t  cr1its   = READ_REG(huart->Instance->CR1);
4355   uint32_t  cr3its   = READ_REG(huart->Instance->CR3);
4356 
4357   /* Check that a Rx process is ongoing */
4358   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
4359   {
4360     nb_rx_data = huart->NbRxDataToProcess;
4361     while ((nb_rx_data > 0U) && ((isrflags & USART_ISR_RXNE_RXFNE) != 0U))
4362     {
4363       uhdata = (uint16_t) READ_REG(huart->Instance->RDR);
4364       *huart->pRxBuffPtr = (uint8_t)(uhdata & (uint8_t)uhMask);
4365       huart->pRxBuffPtr++;
4366       huart->RxXferCount--;
4367       isrflags = READ_REG(huart->Instance->ISR);
4368 
4369       /* If some non blocking errors occurred */
4370       if ((isrflags & (USART_ISR_PE | USART_ISR_FE | USART_ISR_NE)) != 0U)
4371       {
4372         /* UART parity error interrupt occurred -------------------------------------*/
4373         if (((isrflags & USART_ISR_PE) != 0U) && ((cr1its & USART_CR1_PEIE) != 0U))
4374         {
4375           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_PEF);
4376 
4377           huart->ErrorCode |= HAL_UART_ERROR_PE;
4378         }
4379 
4380         /* UART frame error interrupt occurred --------------------------------------*/
4381         if (((isrflags & USART_ISR_FE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
4382         {
4383           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_FEF);
4384 
4385           huart->ErrorCode |= HAL_UART_ERROR_FE;
4386         }
4387 
4388         /* UART noise error interrupt occurred --------------------------------------*/
4389         if (((isrflags & USART_ISR_NE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
4390         {
4391           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_NEF);
4392 
4393           huart->ErrorCode |= HAL_UART_ERROR_NE;
4394         }
4395 
4396         /* Call UART Error Call back function if need be ----------------------------*/
4397         if (huart->ErrorCode != HAL_UART_ERROR_NONE)
4398         {
4399           /* Non Blocking error : transfer could go on.
4400           Error is notified to user through user error callback */
4401 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4402           /*Call registered error callback*/
4403           huart->ErrorCallback(huart);
4404 #else
4405           /*Call legacy weak error callback*/
4406           HAL_UART_ErrorCallback(huart);
4407 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4408           huart->ErrorCode = HAL_UART_ERROR_NONE;
4409         }
4410       }
4411 
4412       if (huart->RxXferCount == 0U)
4413       {
4414         /* Disable the UART Parity Error Interrupt and RXFT interrupt*/
4415         ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_PEIE);
4416 
4417         /* Disable the UART Error Interrupt: (Frame error, noise error, overrun error)
4418            and RX FIFO Threshold interrupt */
4419         ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
4420 
4421         /* Rx process is completed, restore huart->RxState to Ready */
4422         huart->RxState = HAL_UART_STATE_READY;
4423 
4424         /* Clear RxISR function pointer */
4425         huart->RxISR = NULL;
4426 
4427         /* Initialize type of RxEvent to Transfer Complete */
4428         huart->RxEventType = HAL_UART_RXEVENT_TC;
4429 
4430         if (!(IS_LPUART_INSTANCE(huart->Instance)))
4431         {
4432           /* Check that USART RTOEN bit is set */
4433           if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
4434           {
4435             /* Enable the UART Receiver Timeout Interrupt */
4436             ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
4437           }
4438         }
4439 
4440         /* Check current reception Mode :
4441            If Reception till IDLE event has been selected : */
4442         if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
4443         {
4444           /* Set reception type to Standard */
4445           huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
4446 
4447           /* Disable IDLE interrupt */
4448           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
4449 
4450           if (__HAL_UART_GET_FLAG(huart, UART_FLAG_IDLE) == SET)
4451           {
4452             /* Clear IDLE Flag */
4453             __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_IDLEF);
4454           }
4455 
4456 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4457           /*Call registered Rx Event callback*/
4458           huart->RxEventCallback(huart, huart->RxXferSize);
4459 #else
4460           /*Call legacy weak Rx Event callback*/
4461           HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize);
4462 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
4463         }
4464         else
4465         {
4466           /* Standard reception API called */
4467 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4468           /*Call registered Rx complete callback*/
4469           huart->RxCpltCallback(huart);
4470 #else
4471           /*Call legacy weak Rx complete callback*/
4472           HAL_UART_RxCpltCallback(huart);
4473 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4474         }
4475       }
4476     }
4477 
4478     /* When remaining number of bytes to receive is less than the RX FIFO
4479     threshold, next incoming frames are processed as if FIFO mode was
4480     disabled (i.e. one interrupt per received frame).
4481     */
4482     rxdatacount = huart->RxXferCount;
4483     if ((rxdatacount != 0U) && (rxdatacount < huart->NbRxDataToProcess))
4484     {
4485       /* Disable the UART RXFT interrupt*/
4486       ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_RXFTIE);
4487 
4488       /* Update the RxISR function pointer */
4489       huart->RxISR = UART_RxISR_8BIT;
4490 
4491       /* Enable the UART Data Register Not Empty interrupt */
4492       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
4493     }
4494   }
4495   else
4496   {
4497     /* Clear RXNE interrupt flag */
4498     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
4499   }
4500 }
4501 
4502 /**
4503   * @brief RX interrupt handler for 9 bits data word length and FIFO mode is enabled.
4504   * @note   Function is called under interruption only, once
4505   *         interruptions have been enabled by HAL_UART_Receive_IT()
4506   * @param huart UART handle.
4507   * @retval None
4508   */
UART_RxISR_16BIT_FIFOEN(UART_HandleTypeDef * huart)4509 static void UART_RxISR_16BIT_FIFOEN(UART_HandleTypeDef *huart)
4510 {
4511   uint16_t *tmp;
4512   uint16_t  uhMask = huart->Mask;
4513   uint16_t  uhdata;
4514   uint16_t  nb_rx_data;
4515   uint16_t  rxdatacount;
4516   uint32_t  isrflags = READ_REG(huart->Instance->ISR);
4517   uint32_t  cr1its   = READ_REG(huart->Instance->CR1);
4518   uint32_t  cr3its   = READ_REG(huart->Instance->CR3);
4519 
4520   /* Check that a Rx process is ongoing */
4521   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
4522   {
4523     nb_rx_data = huart->NbRxDataToProcess;
4524     while ((nb_rx_data > 0U) && ((isrflags & USART_ISR_RXNE_RXFNE) != 0U))
4525     {
4526       uhdata = (uint16_t) READ_REG(huart->Instance->RDR);
4527       tmp = (uint16_t *) huart->pRxBuffPtr ;
4528       *tmp = (uint16_t)(uhdata & uhMask);
4529       huart->pRxBuffPtr += 2U;
4530       huart->RxXferCount--;
4531       isrflags = READ_REG(huart->Instance->ISR);
4532 
4533       /* If some non blocking errors occurred */
4534       if ((isrflags & (USART_ISR_PE | USART_ISR_FE | USART_ISR_NE)) != 0U)
4535       {
4536         /* UART parity error interrupt occurred -------------------------------------*/
4537         if (((isrflags & USART_ISR_PE) != 0U) && ((cr1its & USART_CR1_PEIE) != 0U))
4538         {
4539           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_PEF);
4540 
4541           huart->ErrorCode |= HAL_UART_ERROR_PE;
4542         }
4543 
4544         /* UART frame error interrupt occurred --------------------------------------*/
4545         if (((isrflags & USART_ISR_FE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
4546         {
4547           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_FEF);
4548 
4549           huart->ErrorCode |= HAL_UART_ERROR_FE;
4550         }
4551 
4552         /* UART noise error interrupt occurred --------------------------------------*/
4553         if (((isrflags & USART_ISR_NE) != 0U) && ((cr3its & USART_CR3_EIE) != 0U))
4554         {
4555           __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_NEF);
4556 
4557           huart->ErrorCode |= HAL_UART_ERROR_NE;
4558         }
4559 
4560         /* Call UART Error Call back function if need be ----------------------------*/
4561         if (huart->ErrorCode != HAL_UART_ERROR_NONE)
4562         {
4563           /* Non Blocking error : transfer could go on.
4564           Error is notified to user through user error callback */
4565 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4566           /*Call registered error callback*/
4567           huart->ErrorCallback(huart);
4568 #else
4569           /*Call legacy weak error callback*/
4570           HAL_UART_ErrorCallback(huart);
4571 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4572           huart->ErrorCode = HAL_UART_ERROR_NONE;
4573         }
4574       }
4575 
4576       if (huart->RxXferCount == 0U)
4577       {
4578         /* Disable the UART Parity Error Interrupt and RXFT interrupt*/
4579         ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_PEIE);
4580 
4581         /* Disable the UART Error Interrupt: (Frame error, noise error, overrun error)
4582            and RX FIFO Threshold interrupt */
4583         ATOMIC_CLEAR_BIT(huart->Instance->CR3, (USART_CR3_EIE | USART_CR3_RXFTIE));
4584 
4585         /* Rx process is completed, restore huart->RxState to Ready */
4586         huart->RxState = HAL_UART_STATE_READY;
4587 
4588         /* Clear RxISR function pointer */
4589         huart->RxISR = NULL;
4590 
4591         /* Initialize type of RxEvent to Transfer Complete */
4592         huart->RxEventType = HAL_UART_RXEVENT_TC;
4593 
4594         if (!(IS_LPUART_INSTANCE(huart->Instance)))
4595         {
4596           /* Check that USART RTOEN bit is set */
4597           if (READ_BIT(huart->Instance->CR2, USART_CR2_RTOEN) != 0U)
4598           {
4599             /* Enable the UART Receiver Timeout Interrupt */
4600             ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_RTOIE);
4601           }
4602         }
4603 
4604         /* Check current reception Mode :
4605            If Reception till IDLE event has been selected : */
4606         if (huart->ReceptionType == HAL_UART_RECEPTION_TOIDLE)
4607         {
4608           /* Set reception type to Standard */
4609           huart->ReceptionType = HAL_UART_RECEPTION_STANDARD;
4610 
4611           /* Disable IDLE interrupt */
4612           ATOMIC_CLEAR_BIT(huart->Instance->CR1, USART_CR1_IDLEIE);
4613 
4614           if (__HAL_UART_GET_FLAG(huart, UART_FLAG_IDLE) == SET)
4615           {
4616             /* Clear IDLE Flag */
4617             __HAL_UART_CLEAR_FLAG(huart, UART_CLEAR_IDLEF);
4618           }
4619 
4620 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4621           /*Call registered Rx Event callback*/
4622           huart->RxEventCallback(huart, huart->RxXferSize);
4623 #else
4624           /*Call legacy weak Rx Event callback*/
4625           HAL_UARTEx_RxEventCallback(huart, huart->RxXferSize);
4626 #endif /* (USE_HAL_UART_REGISTER_CALLBACKS) */
4627         }
4628         else
4629         {
4630           /* Standard reception API called */
4631 #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)
4632           /*Call registered Rx complete callback*/
4633           huart->RxCpltCallback(huart);
4634 #else
4635           /*Call legacy weak Rx complete callback*/
4636           HAL_UART_RxCpltCallback(huart);
4637 #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
4638         }
4639       }
4640     }
4641 
4642     /* When remaining number of bytes to receive is less than the RX FIFO
4643     threshold, next incoming frames are processed as if FIFO mode was
4644     disabled (i.e. one interrupt per received frame).
4645     */
4646     rxdatacount = huart->RxXferCount;
4647     if ((rxdatacount != 0U) && (rxdatacount < huart->NbRxDataToProcess))
4648     {
4649       /* Disable the UART RXFT interrupt*/
4650       ATOMIC_CLEAR_BIT(huart->Instance->CR3, USART_CR3_RXFTIE);
4651 
4652       /* Update the RxISR function pointer */
4653       huart->RxISR = UART_RxISR_16BIT;
4654 
4655       /* Enable the UART Data Register Not Empty interrupt */
4656       ATOMIC_SET_BIT(huart->Instance->CR1, USART_CR1_RXNEIE_RXFNEIE);
4657     }
4658   }
4659   else
4660   {
4661     /* Clear RXNE interrupt flag */
4662     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
4663   }
4664 }
4665 
4666 /**
4667   * @}
4668   */
4669 
4670 #endif /* HAL_UART_MODULE_ENABLED */
4671 /**
4672   * @}
4673   */
4674 
4675 /**
4676   * @}
4677   */
4678 
4679