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