@@ -83,8 +83,6 @@ static int uart_cdns_fill_fifo(const struct device *dev, const uint8_t *tx_data,
83
83
84
84
for (i = 0 ; i < len && (!uart_cdns_is_tx_fifo_full (uart_regs )); i ++ ) {
85
85
uart_regs -> rx_tx_fifo = tx_data [i ];
86
- while (!uart_cdns_is_tx_fifo_empty (uart_regs )) {
87
- }
88
86
}
89
87
return i ;
90
88
}
@@ -108,14 +106,20 @@ void uart_cdns_enable_tx_irq(const struct device *dev)
108
106
{
109
107
struct uart_cdns_regs * uart_regs = DEV_UART (dev );
110
108
111
- uart_regs -> intr_enable |= CSR_TTRIG_MASK ;
109
+ /*
110
+ * TX empty interrupt only triggered when TX removes the last byte from the
111
+ * TX FIFO. We need another way generate the first interrupt. This is why
112
+ * we have the timer involved here
113
+ */
114
+ uart_regs -> rx_timeout = DEFAULT_RTO_PERIODS_FACTOR ;
115
+ uart_regs -> intr_enable = CSR_TEMPTY_MASK | CSR_TOUT_MASK ;
112
116
}
113
117
114
118
void uart_cdns_disable_tx_irq (const struct device * dev )
115
119
{
116
120
struct uart_cdns_regs * uart_regs = DEV_UART (dev );
117
121
118
- uart_regs -> intr_disable |= CSR_TTRIG_MASK ;
122
+ uart_regs -> intr_disable = CSR_TEMPTY_MASK | CSR_TOUT_MASK ;
119
123
}
120
124
121
125
static int uart_cdns_irq_tx_ready (const struct device * dev )
@@ -132,16 +136,16 @@ void uart_cdns_enable_rx_irq(const struct device *dev)
132
136
{
133
137
struct uart_cdns_regs * uart_regs = DEV_UART (dev );
134
138
135
- uart_regs -> rx_timeout = DEFAULT_RTO_PERIODS_FACTOR ;
136
- uart_regs -> intr_enable |= ( CSR_RTRIG_MASK | CSR_RBRK_MASK | CSR_TOUT_MASK ) ;
139
+ uart_regs -> rx_fifo_trigger_level = 1 ;
140
+ uart_regs -> intr_enable = CSR_RTRIG_MASK ;
137
141
}
138
142
139
143
/** Disable RX UART interrupt */
140
144
void uart_cdns_disable_rx_irq (const struct device * dev )
141
145
{
142
146
struct uart_cdns_regs * uart_regs = DEV_UART (dev );
143
147
144
- uart_regs -> intr_disable |= ( CSR_RTRIG_MASK | CSR_RBRK_MASK | CSR_TOUT_MASK ) ;
148
+ uart_regs -> intr_disable = CSR_RTRIG_MASK ;
145
149
}
146
150
147
151
static int uart_cdns_irq_rx_ready (const struct device * dev )
@@ -204,6 +208,10 @@ static void uart_cdns_irq_handler(const struct device *dev)
204
208
/* need to make local copy of the status */
205
209
isr_status = uart_regs -> channel_intr_status ;
206
210
211
+ if (isr_status & CSR_TOUT_MASK ) {
212
+ uart_regs -> intr_disable = CSR_TOUT_MASK ;
213
+ }
214
+
207
215
irq_unlock (key );
208
216
}
209
217
0 commit comments