From b57aecdfe93546f32f49e90c5dd710fe6891ecb1 Mon Sep 17 00:00:00 2001 From: Ivan Grokhotkov Date: Thu, 8 Dec 2016 01:37:07 +0800 Subject: [PATCH] uart_tx_wait_idle: fix issue with last character not transmitted MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - ROM function uart_tx_wait_idle may have a bug which causes the function to return before the final character is fully transmitted. This replaces uart_tx_wait_idle declaration with a static inline definition which fixes the issue. - Also replaces the use of uart_tx_flush with uart_tx_wait_idle in esp_restart, to remove garbage in console output on restart. - rtc_printf is temporary replaced with a no-op, pending a new release of librtc.a. Current release assumes that UART0 is used for output, and switches UART0 baud rate while doing frequency changes and printing some log output. This doesn’t work if a different UART is used for output. --- components/esp32/include/rom/uart.h | 13 ++++++++++--- components/esp32/lib_printf.c | 7 ++----- components/esp32/system_api.c | 8 ++++---- 3 files changed, 16 insertions(+), 12 deletions(-) diff --git a/components/esp32/include/rom/uart.h b/components/esp32/include/rom/uart.h index aa3cf59217..81fa26c238 100644 --- a/components/esp32/include/rom/uart.h +++ b/components/esp32/include/rom/uart.h @@ -18,6 +18,8 @@ #include "esp_types.h" #include "esp_attr.h" #include "ets_sys.h" +#include "soc/soc.h" +#include "soc/uart_reg.h" #ifdef __cplusplus extern "C" { @@ -260,11 +262,16 @@ void uart_tx_flush(uint8_t uart_no); /** * @brief Wait until uart tx full empty and the last char send ok. * - * @param uint8_t uart_no : 0 for UART0, 1 for UART1. + * @param uart_no : 0 for UART0, 1 for UART1, 2 for UART2 * - * @return None. + * The function defined in ROM code has a bug, so we define the correct version + * here for compatibility. */ -void uart_tx_wait_idle(uint8_t uart_no); +static inline void uart_tx_wait_idle(uint8_t uart_no) { + while(REG_GET_FIELD(UART_STATUS_REG(uart_no), UART_ST_UTX_OUT)) { + ; + } +} /** * @brief Get an input char from message channel. diff --git a/components/esp32/lib_printf.c b/components/esp32/lib_printf.c index a2aff4cf56..417e71bdf7 100644 --- a/components/esp32/lib_printf.c +++ b/components/esp32/lib_printf.c @@ -62,11 +62,8 @@ int phy_printf(const char* format, ...) int rtc_printf(const char* format, ...) { - va_list arg; - va_start(arg, format); - int res = lib_printf("rtc", format, arg); - va_end(arg); - return res; + // librtc.a printf temporary disabled due to UART baud rate switching bug. + return 0; } int wpa_printf(const char* format, ...) diff --git a/components/esp32/system_api.c b/components/esp32/system_api.c index 36a5f806da..e8013441b1 100644 --- a/components/esp32/system_api.c +++ b/components/esp32/system_api.c @@ -105,10 +105,10 @@ void IRAM_ATTR esp_restart(void) Cache_Read_Disable(0); Cache_Read_Disable(1); - // Flush any data left in UART FIFO - uart_tx_flush(0); - uart_tx_flush(1); - uart_tx_flush(2); + // Flush any data left in UART FIFOs + uart_tx_wait_idle(0); + uart_tx_wait_idle(1); + uart_tx_wait_idle(2); // Reset wifi/bluetooth (bb/mac) SET_PERI_REG_MASK(DPORT_WIFI_RST_EN_REG, 0x1f);