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