PERFORCE change 35119 for review
Marcel Moolenaar
marcel at FreeBSD.org
Sun Jul 27 23:11:21 PDT 2003
http://perforce.freebsd.org/chv.cgi?CH=35119
Change 35119 by marcel at marcel_nfs on 2003/07/27 23:11:17
o Simplify the TX buffer. We always send in chucks the size of
the TX FIFO.
o Add a txbusy flag that's set when the transmitter is actually
transmitting.
o Improve UART_IPEND for the ns8250.
Affected files ...
.. //depot/projects/uart/dev/uart/uart_bus.h#11 edit
.. //depot/projects/uart/dev/uart/uart_core.c#12 edit
.. //depot/projects/uart/dev/uart/uart_dev_ns8250.c#12 edit
Differences ...
==== //depot/projects/uart/dev/uart/uart_bus.h#11 (text+ko) ====
@@ -100,6 +100,7 @@
int sc_hasfifo:1; /* This UART has FIFOs. */
int sc_leaving:1; /* This UART is going away. */
int sc_polled:1; /* This UART has no interrupts. */
+ int sc_txbusy:1; /* This UART is transmitting. */
/* Receiver data. */
uint16_t *sc_rxbuf;
@@ -110,10 +111,8 @@
/* Transmitter data. */
uint8_t *sc_txbuf;
- int sc_txbufsz;
- int sc_txput;
- int sc_txget;
- int sc_txfifosz; /* Size of TX FIFO. */
+ int sc_txdatasz;
+ int sc_txfifosz; /* Size of TX FIFO and buffer. */
dev_t sc_si;
void *sc_softih;
@@ -176,46 +175,4 @@
return (0);
}
-/*
- * Transmit buffer operations.
- */
-static __inline int
-uart_tx_empty(struct uart_softc *sc)
-{
- return ((sc->sc_txget == sc->sc_txput) ? 1 : 0);
-}
-
-static __inline int
-uart_tx_full(struct uart_softc *sc)
-{
- return ((sc->sc_txput + 1 < sc->sc_txbufsz)
- ? (sc->sc_txput + 1 == sc->sc_txget) : (sc->sc_txget == 0));
-}
-
-static __inline int
-uart_tx_get(struct uart_softc *sc)
-{
- int ptr, c;
-
- ptr = sc->sc_txget;
- if (ptr == sc->sc_txput)
- return (-1);
- c = sc->sc_txbuf[ptr++];
- sc->sc_txget = (ptr < sc->sc_txbufsz) ? ptr : 0;
- return (c);
-}
-
-static __inline int
-uart_tx_put(struct uart_softc *sc, int c)
-{
- int ptr;
-
- ptr = (sc->sc_txput + 1 < sc->sc_txbufsz) ? sc->sc_txput + 1 : 0;
- if (ptr == sc->sc_txget)
- return (ENOSPC);
- sc->sc_txbuf[sc->sc_txput] = c;
- sc->sc_txput = ptr;
- return (0);
-}
-
#endif /* _DEV_UART_BUS_H_ */
==== //depot/projects/uart/dev/uart/uart_core.c#12 (text+ko) ====
@@ -75,7 +75,6 @@
uart_tty_oproc(struct tty *tp)
{
struct uart_softc *sc;
- int c;
sc = tp->t_dev->si_drv1;
if (sc == NULL || sc->sc_leaving)
@@ -92,12 +91,12 @@
return;
}
- while (!uart_tx_full(sc) && tp->t_outq.c_cc > 0) {
- c = getc(&tp->t_outq);
- uart_tx_put(sc, c);
+ if (tp->t_outq.c_cc > 0 && !sc->sc_txbusy) {
+ sc->sc_txdatasz = q_to_b(&tp->t_outq, sc->sc_txbuf,
+ sc->sc_txfifosz);
+ tp->t_state |= TS_BUSY;
+ UART_TRANSMIT(sc);
}
- tp->t_state |= TS_BUSY;
- UART_TRANSMIT(sc);
ttwwakeup(tp);
}
@@ -229,10 +228,10 @@
static void
uart_intr_txidle(struct uart_softc *sc)
{
- if (sc->sc_txget != sc->sc_txput)
- UART_TRANSMIT(sc);
- else
+ if (sc->sc_txbusy) {
+ sc->sc_txbusy = 0;
atomic_set_32(&sc->sc_ttypend, UART_IPEND_TXIDLE);
+ }
}
static void
@@ -389,8 +388,7 @@
sc->sc_rxbufsz = IBUFSIZ;
sc->sc_rxbuf = malloc(sc->sc_rxbufsz * sizeof(*sc->sc_rxbuf),
M_UART, M_WAITOK);
- sc->sc_txbufsz = OBUFSIZ;
- sc->sc_txbuf = malloc(sc->sc_txbufsz * sizeof(*sc->sc_txbuf),
+ sc->sc_txbuf = malloc(sc->sc_txfifosz * sizeof(*sc->sc_txbuf),
M_UART, M_WAITOK);
error = UART_ATTACH(sc);
==== //depot/projects/uart/dev/uart/uart_dev_ns8250.c#12 (text+ko) ====
@@ -423,29 +423,31 @@
static int
ns8250_bus_ipend(struct uart_softc *sc)
{
- struct ns8250_softc *ns8250 = (struct ns8250_softc*)sc;
struct uart_bas *bas;
- int ipend, sig;
- uint8_t lsr;
+ int ipend;
+ uint8_t iir, lsr;
bas = &sc->sc_bas;
+ iir = uart_getreg(bas, REG_IIR);
+ if (iir & IIR_NOPEND)
+ return (0);
+
ipend = 0;
- lsr = uart_getreg(bas, REG_LSR);
- if (lsr & LSR_OE)
- ipend |= UART_IPEND_OVERRUN;
- if (lsr & LSR_BI)
- ipend |= UART_IPEND_BREAK;
- if (lsr & LSR_RXRDY)
- ipend |= UART_IPEND_RXREADY;
- if (lsr & LSR_TEMT) {
- (void)uart_getreg(bas, REG_IIR);
- ipend |= UART_IPEND_TXIDLE;
+ if (iir & IIR_RXRDY) {
+ lsr = uart_getreg(bas, REG_LSR);
+ if (lsr & LSR_OE)
+ ipend |= UART_IPEND_OVERRUN;
+ if (lsr & LSR_BI)
+ ipend |= UART_IPEND_BREAK;
+ if (lsr & LSR_RXRDY)
+ ipend |= UART_IPEND_RXREADY;
+ } else {
+ if (iir & IIR_TXRDY)
+ ipend |= UART_IPEND_TXIDLE;
+ else
+ ipend |= UART_IPEND_SIGCHG;
}
- sig = ns8250_bus_getsig(sc);
- if (sig & UART_SIGMASK_DELTA) {
- ns8250->signals = sig; /* restore delta bits. */
- ipend |= UART_IPEND_SIGCHG;
- }
+
return ((sc->sc_leaving) ? 0 : ipend);
}
@@ -626,15 +628,16 @@
ns8250_bus_transmit(struct uart_softc *sc)
{
struct uart_bas *bas;
- int xc;
+ int i;
bas = &sc->sc_bas;
- while (!uart_tx_empty(sc)) {
- if ((uart_getreg(bas, REG_LSR) & LSR_THRE) == 0)
- break;
- xc = uart_tx_get(sc);
- uart_setreg(bas, REG_DATA, xc);
+
+ for (i = 0; i < sc->sc_txdatasz; i++) {
+ while ((uart_getreg(bas, REG_LSR) & LSR_THRE) == 0)
+ ;
+ uart_setreg(bas, REG_DATA, sc->sc_txbuf[i]);
uart_barrier(bas);
}
+ sc->sc_txbusy = 1;
return (0);
}
More information about the p4-projects
mailing list