Skip to content

Commit

Permalink
uart_sifive: Implement wait_tx_done
Browse files Browse the repository at this point in the history
Both documentation and RTL give the impression that the pending
interrupt conditions in the ip register are updated independent of
whether the corresponding interrupts are enabled in the ie register.

Change-Id: I6845e169a795677393129cd62337828a06de8766
  • Loading branch information
gkotheim authored and jermar committed Jul 3, 2024
1 parent 87b34ca commit 5ce6edd
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 3 deletions.
18 changes: 16 additions & 2 deletions src/lib/uart/uart_sifive.cc
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,13 @@ namespace L4
UARTSFV_RXDATA_DATA = 0xff,

UARTSFV_TXCTRL_TXEN = 1,
UARTSFV_TXCTRL_TXCNT_SHIFT = 16,

UARTSFV_RXCTRL_RXEN = 1,

UARTSFV_IE_RXWM = 2,

UARTSFV_IP_TXWM = 1,
UARTSFV_IP_RXWM = 2,
};
bool Uart_sifive::startup(Io_register_block const *regs)
Expand All @@ -30,8 +34,11 @@ namespace L4
// Disable TX and RX interrupts
_regs->write<unsigned>(UARTSFV_IE, 0);

// Enable RX and TX
_regs->write<unsigned>(UARTSFV_TXCTRL, UARTSFV_TXCTRL_TXEN);
// Enable TX and set transmit watermark level to 1, i.e. it triggers when
// the transmit FIFO is empty.
_regs->write<unsigned>(UARTSFV_TXCTRL, UARTSFV_TXCTRL_TXEN
| 1u << UARTSFV_TXCTRL_TXCNT_SHIFT);
// Enable RX
_regs->write<unsigned>(UARTSFV_RXCTRL, UARTSFV_RXCTRL_RXEN);

return true;
Expand Down Expand Up @@ -88,6 +95,13 @@ namespace L4
return !(_regs->read<unsigned>(UARTSFV_TXDATA) & UARTSFV_TXDATA_FULL);
}

void Uart_sifive::wait_tx_done() const
{
Poll_timeout_counter i(5000000);
while (i.test(!(_regs->read<unsigned>(UARTSFV_IP) & UARTSFV_IP_TXWM)))
;
}

void Uart_sifive::out_char(char c) const
{
_regs->write<unsigned>(UARTSFV_TXDATA, c);
Expand Down
2 changes: 1 addition & 1 deletion src/lib/uart/uart_sifive.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ namespace L4
int get_char(bool blocking = true) const override;
int char_avail() const override;
int tx_avail() const;
void wait_tx_done() const {}
void wait_tx_done() const;
inline void out_char(char c) const;
int write(char const *s, unsigned long count,
bool blocking = true) const override;
Expand Down

0 comments on commit 5ce6edd

Please sign in to comment.