PERFORCE change 88429 for review
Warner Losh
imp at FreeBSD.org
Mon Dec 19 16:20:47 PST 2005
http://perforce.freebsd.org/chv.cgi?CH=88429
Change 88429 by imp at imp_Speedy on 2005/12/20 00:19:55
Lame transmit code
decent get/set sig code
start on setting parameters
# this is a checkpoint, more to follow
Affected files ...
.. //depot/projects/arm/src/sys/arm/at91/at91usartreg.h#2 edit
.. //depot/projects/arm/src/sys/arm/at91/uart_cpu_at91rm9200usart.c#3 edit
.. //depot/projects/arm/src/sys/arm/at91/uart_dev_at91usart.c#5 edit
Differences ...
==== //depot/projects/arm/src/sys/arm/at91/at91usartreg.h#2 (text+ko) ====
@@ -48,13 +48,62 @@
#define USART_CR_RTSDIS (1 << 19) /* Request to Send Disable */
#define USART_MR 0x04 /* Mode register */
+#define USART_MR_MODE_NORMAL 0 /* Normal/Async/3-wire rs-232 */
+#define USART_MR_MODE_RS485 1 /* RS485 */
+#define USART_MR_MODE_HWFLOW 2 /* Hardware flow control/handshake */
+#define USART_MR_MODE_MODEM 3 /* Full modem protocol */
+#define USART_MR_MODE_ISO7816T0 4 /* ISO7816 T=0 */
+#define USART_MR_MODE_ISO7816T1 6 /* ISO7816 T=1 */
+#define USART_MR_MODE_IRDA 8 /* IrDA mode */
+#define USART_MR_USCLKS_MCK (0U << 4) /* use MCK for baudclock */
+#define USART_MR_USCLKS_MCKDIV (1U << 4) /* use MCK/DIV for baudclock */
+#define USART_MR_USCLKS_SCK (3U << 4) /* use SCK (ext) for baudclock */
+#define USART_MR_CHRL_5BITS (0U << 6)
+#define USART_MR_CHRL_6BITS (1U << 6)
+#define USART_MR_CHRL_7BITS (2U << 6)
+#define USART_MR_CHRL_8BITS (3U << 6)
+#define USART_MR_SYNC (1U << 8) /* 1 -> sync 0 -> async */
+#define USART_MR_PAR_EVEN (0U << 9)
+#define USART_MR_PAR_ODD (1U << 9)
+#define USART_MR_PAR_SPACE (2U << 9)
+#define USART_MR_PAR_MARK (3U << 9)
+#define USART_MR_PAR_NONE (4U << 9)
+#define USART_MR_PAR_MULTIDROP (6U << 9)
+#define USART_MR_NBSTOP_1 (0U << 12)
+#define USART_MR_NBSTOP_1_5 (1U << 12)
+#define USART_MR_NBSTOP_2 (2U << 12)
+#define USART_MR_CHMODE_NORMAL (0U << 14)
+#define USART_MR_CHMODE_ECHO (1U << 14)
+#define USART_MR_CHMODE_LOOP (2U << 14)
+#define USART_MR_CHMODE_REMLOOP (3U << 14)
+
#define USART_IER 0x08 /* Interrupt enable register */
#define USART_IDR 0x0c /* Interrupt disable register */
#define USART_IMR 0x10 /* Interrupt mask register */
#define USART_CSR 0x14 /* Channel status register */
-#define USART_CSR_RXRDY (1 << 0) /* Receiver ready */
-#define USART_CSR_TXRDY (1 << 1) /* Transmitter ready */
+#define USART_CSR_RXRDY (1U << 0) /* Receiver ready */
+#define USART_CSR_TXRDY (1U << 1) /* Transmitter ready */
+#define USART_CSR_RXBRK (1U << 2) /* Break received */
+#define USART_CSR_ENDRX (1U << 3) /* End of Transfer RX from PDC */
+#define USART_CSR_ENDTX (1U << 4) /* End of Transfer TX from PDC */
+#define USART_CSR_OVRE (1U << 5) /* Overrun error */
+#define USART_CSR_FRAME (1U << 6) /* Framing error */
+#define USART_CSR_PARE (1U << 7) /* Parity Error */
+#define USART_CSR_TIMEOUT (1U << 8) /* Timeout since start-timeout */
+#define USART_CSR_TXEMPTY (1U << 9) /* Transmitter empty */
+#define USART_CSR_ITERATION (1U << 10) /* max repetitions since RSIT */
+#define USART_CSR_TXBUFE (1U << 11) /* Buffer empty from PDC */
+#define USART_CSR_RXBUFF (1U << 12) /* Buffer full from PDC */
+#define USART_CSR_NACK (1U << 13) /* NACK since last RSTNACK */
+#define USART_CSR_RIIC (1U << 16) /* RI delta since last csr read */
+#define USART_CSR_DSRIC (1U << 17) /* DSR delta */
+#define USART_CSR_DCDIC (1U << 18) /* DCD delta */
+#define USART_CSR_CTSIC (1U << 19) /* CTS delta */
+#define USART_CSR_RI (1U << 20) /* RI status */
+#define USART_CSR_DSR (1U << 21) /* DSR status */
+#define USART_CSR_DCD (1U << 22) /* DCD status */
+#define USART_CSR_CTS (1U << 23) /* CTS status */
#define USART_RHR 0x18 /* Receiver holding register */
#define USART_THR 0x1c /* Transmitter holding register */
==== //depot/projects/arm/src/sys/arm/at91/uart_cpu_at91rm9200usart.c#3 (text+ko) ====
==== //depot/projects/arm/src/sys/arm/at91/uart_dev_at91usart.c#5 (text+ko) ====
@@ -1,5 +1,6 @@
/*-
- * Copyright (c) 2003 Marcel Moolenaar
+ * Copyright (c) 2005 M. Warner Losh
+ * Copyright (c) 2005 cognet
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -45,6 +46,14 @@
#define DEFAULT_RCLK AT91C_MASTER_CLOCK
+#define SIGCHG(c, i, s, d) \
+ if (c) { \
+ i |= (i & s) ? s : s | d; \
+ } else { \
+ i = (i & s) ? (i & ~s) | d : i; \
+ }
+
+
/*
* Low-level UART interface.
*/
@@ -55,9 +64,41 @@
static int at91_usart_poll(struct uart_bas *bas);
static int at91_usart_getc(struct uart_bas *bas);
-int did_mmu = 0;
+extern SLIST_HEAD(uart_devinfo_list, uart_devinfo) uart_sysdevs;
+
+static int
+at91_usart_param(struct uart_bas *bas, int baudrate, int databits,
+ int stopbits, int parity)
+{
+ uint32_t mr;
+
+ /*
+ * Assume 3-write RS-232 configuration.
+ * XXX Not sure how uart will present the other modes to us, so
+ * XXX they are unimplemented. maybe ioctl?
+ */
+ mr = USART_MR_MODE_NORMAL;
+ mr |= USART_MR_USCLKS_MCK; /* Assume MCK */
+
+ switch (databits) {
+ case 5:
+ mr |= USART_MR_CHRL_5BITS;
+ break;
+ case 6:
+ mr |= USART_MR_CHRL_6BITS;
+ break;
+ case 7:
+ mr |= USART_MR_CHRL_7BITS;
+ break;
+ case 8:
+ mr |= USART_MR_CHRL_8BITS;
+ break;
+ default:
+ return (EINVAL);
+ }
-extern SLIST_HEAD(uart_devinfo_list, uart_devinfo) uart_sysdevs;
+ return (0);
+}
struct uart_ops at91_usart_ops = {
.probe = at91_usart_probe,
@@ -82,10 +123,13 @@
at91_usart_init(struct uart_bas *bas, int baudrate, int databits, int stopbits,
int parity)
{
+ at91_usart_param(bas, baudrate, databits, stopbits, parity);
+ /* Turn on rx and tx */
uart_setreg(bas, USART_CR, USART_CR_RSTRX | USART_CR_RSTTX);
uart_setreg(bas, USART_CR, USART_CR_RXEN | USART_CR_TXEN);
uart_setreg(bas, USART_IER, USART_CSR_TXRDY | USART_CSR_RXRDY);
+ uart_barrier(bas);
}
/*
@@ -172,22 +216,59 @@
static int
at91_usart_bus_attach(struct uart_softc *sc)
{
- bcopy(&sc->sc_sysdev->bas, &sc->sc_bas, sizeof(sc->sc_bas));
+ bcopy(&sc->sc_sysdev->bas, &sc->sc_bas, sizeof(sc->sc_bas));
- sc->sc_txfifosz = 3;
- sc->sc_rxfifosz = 1;
- sc->sc_hwiflow = 0;
+ sc->sc_txfifosz = 1;
+ sc->sc_rxfifosz = 1;
+ sc->sc_hwiflow = 0;
return (0);
}
static int
at91_usart_bus_transmit(struct uart_softc *sc)
{
+ int i;
+ /* XXX very sub-optimial */
+ mtx_lock_spin(&sc->sc_hwmtx);
+ for (i = 0; i < sc->sc_txdatasz; i++)
+ at91_usart_putc(&sc->sc_bas, sc->sc_txbuf[i]);
+ mtx_unlock_spin(&sc->sc_hwmtx);
return (0);
}
static int
at91_usart_bus_setsig(struct uart_softc *sc, int sig)
{
+ uint32_t new, old, cr;
+ struct uart_bas *bas;
+
+ do {
+ old = sc->sc_hwsig;
+ new = old;
+ if (sig & SER_DDTR) {
+ SIGCHG(sig & SER_DTR, new, SER_DTR,
+ SER_DDTR);
+ }
+ if (sig & SER_DRTS) {
+ SIGCHG(sig & SER_RTS, new, SER_RTS,
+ SER_DRTS);
+ }
+ } while (!atomic_cmpset_32(&sc->sc_hwsig, old, new));
+ bas = &sc->sc_bas;
+ mtx_lock_spin(&sc->sc_hwmtx);
+ cr = uart_getreg(bas, USART_CR);
+ cr &= ~(USART_CR_DTREN | USART_CR_DTRDIS | USART_CR_RTSEN |
+ USART_CR_RTSDIS);
+ if (new & SER_DTR)
+ cr |= USART_CR_DTREN;
+ else
+ cr |= USART_CR_DTRDIS;
+ if (new & SER_RTS)
+ cr |= USART_CR_RTSEN;
+ else
+ cr |= USART_CR_RTSDIS;
+ uart_setreg(bas, USART_CR, cr);
+ uart_barrier(bas);
+ mtx_unlock_spin(&sc->sc_hwmtx);
return (0);
}
static int
@@ -216,7 +297,24 @@
static int
at91_usart_bus_getsig(struct uart_softc *sc)
{
- return (0);
+ uint32_t new, sig;
+ uint8_t csr;
+
+ mtx_lock_spin(&sc->sc_hwmtx);
+ csr = uart_getreg(&sc->sc_bas, USART_CSR);
+ sig = 0;
+ if (csr & USART_CSR_CTS)
+ sig |= SER_CTS;
+ if (csr & USART_CSR_DCD)
+ sig |= SER_DCD;
+ if (csr & USART_CSR_DSR)
+ sig |= SER_DSR;
+ if (csr & USART_CSR_RI)
+ sig |= SER_RI;
+ new = sig & ~UART_SIGMASK_DELTA;
+ sc->sc_hwsig = new;
+ mtx_unlock_spin(&sc->sc_hwmtx);
+ return (sig);
}
static int
More information about the p4-projects
mailing list