Skip to content

Commit

Permalink
rp2/machine_uart: Make it so TX is done only when no longer busy.
Browse files Browse the repository at this point in the history
Prior to this commit, when flushing a UART on the rp2 port, it returns just
before the last character is sent out the wire.

Fix this by waiting until the BUSY flag is cleared.

This also fixes the behaviour of `UART.txdone()` to return `True` only when
the last byte has gone out.

Updated docs and tests to match.  The test now checks that UART TX time is
very close to the expected time (prior, it was just testing that the TX
time was less than the expected time).

Signed-off-by: Damien George <damien@micropython.org>
  • Loading branch information
dpgeorge committed Oct 21, 2024
1 parent 1b89c50 commit 97af100
Show file tree
Hide file tree
Showing 3 changed files with 7 additions and 4 deletions.
4 changes: 2 additions & 2 deletions docs/library/machine.UART.rst
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ Methods

.. note::

For the rp2, esp8266 and nrf ports the call returns while the last byte is sent.
For the esp8266 and nrf ports the call returns while the last byte is sent.
If required, a one character wait time has to be added in the calling script.

Availability: rp2, esp32, esp8266, mimxrt, cc3200, stm32, nrf ports, renesas-ra
Expand All @@ -172,7 +172,7 @@ Methods

.. note::

For the rp2, esp8266 and nrf ports the call may return ``True`` even if the last byte
For the esp8266 and nrf ports the call may return ``True`` even if the last byte
of a transfer is still being sent. If required, a one character wait time has to be
added in the calling script.

Expand Down
3 changes: 2 additions & 1 deletion ports/rp2/machine_uart.c
Original file line number Diff line number Diff line change
Expand Up @@ -491,8 +491,9 @@ static mp_int_t mp_machine_uart_any(machine_uart_obj_t *self) {
}

static bool mp_machine_uart_txdone(machine_uart_obj_t *self) {
// TX is done when: nothing in the ringbuf, TX FIFO is empty, TX output is not busy.
return ringbuf_avail(&self->write_buffer) == 0
&& (uart_get_hw(self->uart)->fr & UART_UARTFR_TXFE_BITS);
&& (uart_get_hw(self->uart)->fr & (UART_UARTFR_TXFE_BITS | UART_UARTFR_BUSY_BITS)) == UART_UARTFR_TXFE_BITS;
}

static void mp_machine_uart_sendbreak(machine_uart_obj_t *self) {
Expand Down
4 changes: 3 additions & 1 deletion tests/extmod/machine_uart_tx.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
uart_id = 0
tx_pin = "GPIO0"
rx_pin = "GPIO1"
timing_margin_us = 180
else:
print("SKIP")
raise SystemExit
Expand All @@ -31,4 +32,5 @@
# 1(startbit) + 8(bits) + 1(stopbit) + 0(parity)
bits_per_char = 10
expect_us = (len(text)) * bits_per_char * 1_000_000 // bits_per_s
print(bits_per_s, duration_us <= expect_us)
delta_us = abs(duration_us - expect_us)
print(bits_per_s, delta_us <= timing_margin_us or delta_us)

0 comments on commit 97af100

Please sign in to comment.