uart_dev_at91usart.c revision 266097
1176348Smarcel/*- 2176348Smarcel * Copyright (c) 2005 M. Warner Losh 3176348Smarcel * Copyright (c) 2005 Olivier Houchard 4176348Smarcel * Copyright (c) 2012 Ian Lepore 5176348Smarcel * All rights reserved. 6176348Smarcel * 7176348Smarcel * Redistribution and use in source and binary forms, with or without 8176348Smarcel * modification, are permitted provided that the following conditions 9176348Smarcel * are met: 10176348Smarcel * 11176348Smarcel * 1. Redistributions of source code must retain the above copyright 12176348Smarcel * notice, this list of conditions and the following disclaimer. 13176348Smarcel * 2. Redistributions in binary form must reproduce the above copyright 14176348Smarcel * notice, this list of conditions and the following disclaimer in the 15176348Smarcel * documentation and/or other materials provided with the distribution. 16176348Smarcel * 17176348Smarcel * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND 18176348Smarcel * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19176348Smarcel * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20176348Smarcel * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE 21176348Smarcel * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22176348Smarcel * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23176348Smarcel * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24176348Smarcel * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25176348Smarcel * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26176348Smarcel * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27176348Smarcel * SUCH DAMAGE. 28176348Smarcel */ 29176348Smarcel 30176348Smarcel#include <sys/cdefs.h> 31176348Smarcel__FBSDID("$FreeBSD: stable/10/sys/arm/at91/uart_dev_at91usart.c 266097 2014-05-14 23:51:07Z ian $"); 32176348Smarcel 33182723Sraj#include <sys/param.h> 34182723Sraj#include <sys/systm.h> 35176348Smarcel#include <sys/bus.h> 36176348Smarcel#include <sys/conf.h> 37176348Smarcel#include <sys/cons.h> 38176348Smarcel#include <sys/tty.h> 39176348Smarcel#include <machine/bus.h> 40176348Smarcel 41176348Smarcel#include <dev/uart/uart.h> 42176348Smarcel#include <dev/uart/uart_cpu.h> 43176348Smarcel#include <dev/uart/uart_bus.h> 44176348Smarcel#include <arm/at91/at91_usartreg.h> 45176348Smarcel#include <arm/at91/at91_pdcreg.h> 46176348Smarcel#include <arm/at91/at91_piovar.h> 47182723Sraj#include <arm/at91/at91_pioreg.h> 48176348Smarcel#include <arm/at91/at91rm92reg.h> 49176348Smarcel#include <arm/at91/at91var.h> 50176348Smarcel 51176348Smarcel#include "uart_if.h" 52176348Smarcel 53177108Sraj#define DEFAULT_RCLK at91_master_clock 54176348Smarcel#define USART_DEFAULT_FIFO_BYTES 128 55176348Smarcel 56176348Smarcel#define USART_DCE_CHANGE_BITS (USART_CSR_CTSIC | USART_CSR_DCDIC | \ 57176348Smarcel USART_CSR_DSRIC | USART_CSR_RIIC) 58176348Smarcel 59176348Smarcel/* 60176348Smarcel * High-level UART interface. 61176348Smarcel */ 62176348Smarcelstruct at91_usart_rx { 63177108Sraj bus_addr_t pa; 64176348Smarcel uint8_t *buffer; 65176348Smarcel bus_dmamap_t map; 66}; 67 68struct at91_usart_softc { 69 struct uart_softc base; 70 bus_dma_tag_t tx_tag; 71 bus_dmamap_t tx_map; 72 uint32_t flags; 73#define HAS_TIMEOUT 0x1 74#define USE_RTS0_WORKAROUND 0x2 75 bus_dma_tag_t rx_tag; 76 struct at91_usart_rx ping_pong[2]; 77 struct at91_usart_rx *ping; 78 struct at91_usart_rx *pong; 79}; 80 81#define RD4(bas, reg) \ 82 bus_space_read_4((bas)->bst, (bas)->bsh, uart_regofs(bas, reg)) 83#define WR4(bas, reg, value) \ 84 bus_space_write_4((bas)->bst, (bas)->bsh, uart_regofs(bas, reg), value) 85 86#define SIGCHG(c, i, s, d) \ 87 do { \ 88 if (c) { \ 89 i |= (i & s) ? s : s | d; \ 90 } else { \ 91 i = (i & s) ? (i & ~s) | d : i; \ 92 } \ 93 } while (0); 94 95#define BAUD2DIVISOR(b) \ 96 ((((DEFAULT_RCLK * 10) / ((b) * 16)) + 5) / 10) 97 98/* 99 * Low-level UART interface. 100 */ 101static int at91_usart_probe(struct uart_bas *bas); 102static void at91_usart_init(struct uart_bas *bas, int, int, int, int); 103static void at91_usart_term(struct uart_bas *bas); 104static void at91_usart_putc(struct uart_bas *bas, int); 105static int at91_usart_rxready(struct uart_bas *bas); 106static int at91_usart_getc(struct uart_bas *bas, struct mtx *hwmtx); 107 108extern SLIST_HEAD(uart_devinfo_list, uart_devinfo) uart_sysdevs; 109 110static int 111at91_usart_param(struct uart_bas *bas, int baudrate, int databits, 112 int stopbits, int parity) 113{ 114 uint32_t mr; 115 116 /* 117 * Assume 3-wire RS-232 configuration. 118 * XXX Not sure how uart will present the other modes to us, so 119 * XXX they are unimplemented. maybe ioctl? 120 */ 121 mr = USART_MR_MODE_NORMAL; 122 mr |= USART_MR_USCLKS_MCK; /* Assume MCK */ 123 124 /* 125 * Or in the databits requested 126 */ 127 if (databits < 9) 128 mr &= ~USART_MR_MODE9; 129 switch (databits) { 130 case 5: 131 mr |= USART_MR_CHRL_5BITS; 132 break; 133 case 6: 134 mr |= USART_MR_CHRL_6BITS; 135 break; 136 case 7: 137 mr |= USART_MR_CHRL_7BITS; 138 break; 139 case 8: 140 mr |= USART_MR_CHRL_8BITS; 141 break; 142 case 9: 143 mr |= USART_MR_CHRL_8BITS | USART_MR_MODE9; 144 break; 145 default: 146 return (EINVAL); 147 } 148 149 /* 150 * Or in the parity 151 */ 152 switch (parity) { 153 case UART_PARITY_NONE: 154 mr |= USART_MR_PAR_NONE; 155 break; 156 case UART_PARITY_ODD: 157 mr |= USART_MR_PAR_ODD; 158 break; 159 case UART_PARITY_EVEN: 160 mr |= USART_MR_PAR_EVEN; 161 break; 162 case UART_PARITY_MARK: 163 mr |= USART_MR_PAR_MARK; 164 break; 165 case UART_PARITY_SPACE: 166 mr |= USART_MR_PAR_SPACE; 167 break; 168 default: 169 return (EINVAL); 170 } 171 172 /* 173 * Or in the stop bits. Note: The hardware supports 1.5 stop 174 * bits in async mode, but there's no way to specify that 175 * AFAICT. Instead, rely on the convention documented at 176 * http://www.lammertbies.nl/comm/info/RS-232_specs.html which 177 * states that 1.5 stop bits are used for 5 bit bytes and 178 * 2 stop bits only for longer bytes. 179 */ 180 if (stopbits == 1) 181 mr |= USART_MR_NBSTOP_1; 182 else if (databits > 5) 183 mr |= USART_MR_NBSTOP_2; 184 else 185 mr |= USART_MR_NBSTOP_1_5; 186 187 /* 188 * We want normal plumbing mode too, none of this fancy 189 * loopback or echo mode. 190 */ 191 mr |= USART_MR_CHMODE_NORMAL; 192 193 mr &= ~USART_MR_MSBF; /* lsb first */ 194 mr &= ~USART_MR_CKLO_SCK; /* Don't drive SCK */ 195 196 WR4(bas, USART_MR, mr); 197 198 /* 199 * Set the baud rate (only if we know our master clock rate) 200 */ 201 if (DEFAULT_RCLK != 0) 202 WR4(bas, USART_BRGR, BAUD2DIVISOR(baudrate)); 203 204 /* 205 * Set the receive timeout based on the baud rate. The idea is to 206 * compromise between being responsive on an interactive connection and 207 * giving a bulk data sender a bit of time to queue up a new buffer 208 * without mistaking it for a stopping point in the transmission. For 209 * 19.2kbps and below, use 20 * bit time (2 characters). For faster 210 * connections use 500 microseconds worth of bits. 211 */ 212 if (baudrate <= 19200) 213 WR4(bas, USART_RTOR, 20); 214 else 215 WR4(bas, USART_RTOR, baudrate / 2000); 216 WR4(bas, USART_CR, USART_CR_STTTO); 217 218 /* XXX Need to take possible synchronous mode into account */ 219 return (0); 220} 221 222static struct uart_ops at91_usart_ops = { 223 .probe = at91_usart_probe, 224 .init = at91_usart_init, 225 .term = at91_usart_term, 226 .putc = at91_usart_putc, 227 .rxready = at91_usart_rxready, 228 .getc = at91_usart_getc, 229}; 230 231static int 232at91_usart_probe(struct uart_bas *bas) 233{ 234 235 /* We know that this is always here */ 236 return (0); 237} 238 239/* 240 * Initialize this device for use as a console. 241 */ 242static void 243at91_usart_init(struct uart_bas *bas, int baudrate, int databits, int stopbits, 244 int parity) 245{ 246 247 at91_usart_param(bas, baudrate, databits, stopbits, parity); 248 249 /* Reset the rx and tx buffers and turn on rx and tx */ 250 WR4(bas, USART_CR, USART_CR_RSTSTA | USART_CR_RSTRX | USART_CR_RSTTX); 251 WR4(bas, USART_CR, USART_CR_RXEN | USART_CR_TXEN); 252 WR4(bas, USART_IDR, 0xffffffff); 253} 254 255/* 256 * Free resources now that we're no longer the console. This appears to 257 * be never called, and I'm unsure quite what to do if I am called. 258 */ 259static void 260at91_usart_term(struct uart_bas *bas) 261{ 262 263 /* XXX */ 264} 265 266/* 267 * Put a character of console output (so we do it here polling rather than 268 * interrupt driven). 269 */ 270static void 271at91_usart_putc(struct uart_bas *bas, int c) 272{ 273 274 while (!(RD4(bas, USART_CSR) & USART_CSR_TXRDY)) 275 continue; 276 WR4(bas, USART_THR, c); 277} 278 279#ifdef EARLY_PRINTF 280/* 281 * Early printf support. This assumes that we have the SoC "system" devices 282 * mapped into AT91_BASE. To use this before we adjust the boostrap tables, 283 * You'll need to define SOCDEV_VA to be 0xdc000000 and SOCDEV_PA to be 284 * 0xfc000000 in your config file where you define EARLY_PRINTF 285 */ 286volatile uint32_t *at91_dbgu = (volatile uint32_t *)(AT91_BASE + AT91_DBGU0); 287 288void 289eputc(int c) 290{ 291 292 if (c == '\n') 293 eputc('\r'); 294 295 while (!(at91_dbgu[USART_CSR / 4] & USART_CSR_TXRDY)) 296 continue; 297 at91_dbgu[USART_THR / 4] = c; 298} 299#endif 300 301/* 302 * Check for a character available. 303 */ 304static int 305at91_usart_rxready(struct uart_bas *bas) 306{ 307 308 return ((RD4(bas, USART_CSR) & USART_CSR_RXRDY) != 0 ? 1 : 0); 309} 310 311/* 312 * Block waiting for a character. 313 */ 314static int 315at91_usart_getc(struct uart_bas *bas, struct mtx *hwmtx) 316{ 317 int c; 318 319 uart_lock(hwmtx); 320 while (!(RD4(bas, USART_CSR) & USART_CSR_RXRDY)) { 321 uart_unlock(hwmtx); 322 DELAY(4); 323 uart_lock(hwmtx); 324 } 325 c = RD4(bas, USART_RHR) & 0xff; 326 uart_unlock(hwmtx); 327 return (c); 328} 329 330static int at91_usart_bus_probe(struct uart_softc *sc); 331static int at91_usart_bus_attach(struct uart_softc *sc); 332static int at91_usart_bus_flush(struct uart_softc *, int); 333static int at91_usart_bus_getsig(struct uart_softc *); 334static int at91_usart_bus_ioctl(struct uart_softc *, int, intptr_t); 335static int at91_usart_bus_ipend(struct uart_softc *); 336static int at91_usart_bus_param(struct uart_softc *, int, int, int, int); 337static int at91_usart_bus_receive(struct uart_softc *); 338static int at91_usart_bus_setsig(struct uart_softc *, int); 339static int at91_usart_bus_transmit(struct uart_softc *); 340static void at91_usart_bus_grab(struct uart_softc *); 341static void at91_usart_bus_ungrab(struct uart_softc *); 342 343static kobj_method_t at91_usart_methods[] = { 344 KOBJMETHOD(uart_probe, at91_usart_bus_probe), 345 KOBJMETHOD(uart_attach, at91_usart_bus_attach), 346 KOBJMETHOD(uart_flush, at91_usart_bus_flush), 347 KOBJMETHOD(uart_getsig, at91_usart_bus_getsig), 348 KOBJMETHOD(uart_ioctl, at91_usart_bus_ioctl), 349 KOBJMETHOD(uart_ipend, at91_usart_bus_ipend), 350 KOBJMETHOD(uart_param, at91_usart_bus_param), 351 KOBJMETHOD(uart_receive, at91_usart_bus_receive), 352 KOBJMETHOD(uart_setsig, at91_usart_bus_setsig), 353 KOBJMETHOD(uart_transmit, at91_usart_bus_transmit), 354 KOBJMETHOD(uart_grab, at91_usart_bus_grab), 355 KOBJMETHOD(uart_ungrab, at91_usart_bus_ungrab), 356 357 KOBJMETHOD_END 358}; 359 360int 361at91_usart_bus_probe(struct uart_softc *sc) 362{ 363 int value; 364 365 value = USART_DEFAULT_FIFO_BYTES; 366 resource_int_value(device_get_name(sc->sc_dev), 367 device_get_unit(sc->sc_dev), "fifo_bytes", &value); 368 value = roundup2(value, arm_dcache_align); 369 sc->sc_txfifosz = value; 370 sc->sc_rxfifosz = value; 371 sc->sc_hwiflow = 0; 372 return (0); 373} 374 375static void 376at91_getaddr(void *arg, bus_dma_segment_t *segs, int nsegs, int error) 377{ 378 379 if (error != 0) 380 return; 381 *(bus_addr_t *)arg = segs[0].ds_addr; 382} 383 384static int 385at91_usart_requires_rts0_workaround(struct uart_softc *sc) 386{ 387 int value; 388 int unit; 389 390 unit = device_get_unit(sc->sc_dev); 391 392 /* 393 * On the rm9200 chips, the PA21/RTS0 pin is not correctly wired to the 394 * usart device interally (so-called 'erratum 39', but it's 41.14 in rev 395 * I of the manual). This prevents use of the hardware flow control 396 * feature in the usart itself. It also means that if we are to 397 * implement RTS/CTS flow via the tty layer logic, we must use pin PA21 398 * as a gpio and manually manipulate it in at91_usart_bus_setsig(). We 399 * can only safely do so if we've been given permission via a hint, 400 * otherwise we might manipulate a pin that's attached to who-knows-what 401 * and Bad Things could happen. 402 */ 403 if (at91_is_rm92() && unit == 1) { 404 value = 0; 405 resource_int_value(device_get_name(sc->sc_dev), unit, 406 "use_rts0_workaround", &value); 407 if (value != 0) { 408 at91_pio_use_gpio(AT91RM92_PIOA_BASE, AT91C_PIO_PA21); 409 at91_pio_gpio_output(AT91RM92_PIOA_BASE, 410 AT91C_PIO_PA21, 1); 411 at91_pio_use_periph_a(AT91RM92_PIOA_BASE, 412 AT91C_PIO_PA20, 0); 413 return (1); 414 } 415 } 416 return (0); 417} 418 419static int 420at91_usart_bus_attach(struct uart_softc *sc) 421{ 422 int err; 423 int i; 424 uint32_t cr; 425 struct at91_usart_softc *atsc; 426 427 atsc = (struct at91_usart_softc *)sc; 428 429 if (at91_usart_requires_rts0_workaround(sc)) 430 atsc->flags |= USE_RTS0_WORKAROUND; 431 432 /* 433 * See if we have a TIMEOUT bit. We disable all interrupts as 434 * a side effect. Boot loaders may have enabled them. Since 435 * a TIMEOUT interrupt can't happen without other setup, the 436 * apparent race here can't actually happen. 437 */ 438 WR4(&sc->sc_bas, USART_IDR, 0xffffffff); 439 WR4(&sc->sc_bas, USART_IER, USART_CSR_TIMEOUT); 440 if (RD4(&sc->sc_bas, USART_IMR) & USART_CSR_TIMEOUT) 441 atsc->flags |= HAS_TIMEOUT; 442 WR4(&sc->sc_bas, USART_IDR, 0xffffffff); 443 444 /* 445 * Allocate transmit DMA tag and map. We allow a transmit buffer 446 * to be any size, but it must map to a single contiguous physical 447 * extent. 448 */ 449 err = bus_dma_tag_create(bus_get_dma_tag(sc->sc_dev), 1, 0, 450 BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL, 451 BUS_SPACE_MAXSIZE_32BIT, 1, BUS_SPACE_MAXSIZE_32BIT, 0, NULL, 452 NULL, &atsc->tx_tag); 453 if (err != 0) 454 goto errout; 455 err = bus_dmamap_create(atsc->tx_tag, 0, &atsc->tx_map); 456 if (err != 0) 457 goto errout; 458 459 if (atsc->flags & HAS_TIMEOUT) { 460 /* 461 * Allocate receive DMA tags, maps, and buffers. 462 * The receive buffers should be aligned to arm_dcache_align, 463 * otherwise partial cache line flushes on every receive 464 * interrupt are pretty much guaranteed. 465 */ 466 err = bus_dma_tag_create(bus_get_dma_tag(sc->sc_dev), 467 arm_dcache_align, 0, BUS_SPACE_MAXADDR_32BIT, 468 BUS_SPACE_MAXADDR, NULL, NULL, sc->sc_rxfifosz, 1, 469 sc->sc_rxfifosz, BUS_DMA_ALLOCNOW, NULL, NULL, 470 &atsc->rx_tag); 471 if (err != 0) 472 goto errout; 473 for (i = 0; i < 2; i++) { 474 err = bus_dmamem_alloc(atsc->rx_tag, 475 (void **)&atsc->ping_pong[i].buffer, 476 BUS_DMA_NOWAIT, &atsc->ping_pong[i].map); 477 if (err != 0) 478 goto errout; 479 err = bus_dmamap_load(atsc->rx_tag, 480 atsc->ping_pong[i].map, 481 atsc->ping_pong[i].buffer, sc->sc_rxfifosz, 482 at91_getaddr, &atsc->ping_pong[i].pa, 0); 483 if (err != 0) 484 goto errout; 485 bus_dmamap_sync(atsc->rx_tag, atsc->ping_pong[i].map, 486 BUS_DMASYNC_PREREAD); 487 } 488 atsc->ping = &atsc->ping_pong[0]; 489 atsc->pong = &atsc->ping_pong[1]; 490 } 491 492 /* Turn on rx and tx */ 493 cr = USART_CR_RSTSTA | USART_CR_RSTRX | USART_CR_RSTTX; 494 WR4(&sc->sc_bas, USART_CR, cr); 495 WR4(&sc->sc_bas, USART_CR, USART_CR_RXEN | USART_CR_TXEN); 496 497 /* 498 * Setup the PDC to receive data. We use the ping-pong buffers 499 * so that we can more easily bounce between the two and so that 500 * we get an interrupt 1/2 way through the software 'fifo' we have 501 * to avoid overruns. 502 */ 503 if (atsc->flags & HAS_TIMEOUT) { 504 WR4(&sc->sc_bas, PDC_RPR, atsc->ping->pa); 505 WR4(&sc->sc_bas, PDC_RCR, sc->sc_rxfifosz); 506 WR4(&sc->sc_bas, PDC_RNPR, atsc->pong->pa); 507 WR4(&sc->sc_bas, PDC_RNCR, sc->sc_rxfifosz); 508 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_RXTEN); 509 510 /* 511 * Set the receive timeout to be 1.5 character times 512 * assuming 8N1. 513 */ 514 WR4(&sc->sc_bas, USART_RTOR, 15); 515 WR4(&sc->sc_bas, USART_CR, USART_CR_STTTO); 516 WR4(&sc->sc_bas, USART_IER, USART_CSR_TIMEOUT | 517 USART_CSR_RXBUFF | USART_CSR_ENDRX); 518 } else { 519 WR4(&sc->sc_bas, USART_IER, USART_CSR_RXRDY); 520 } 521 WR4(&sc->sc_bas, USART_IER, USART_CSR_RXBRK | USART_DCE_CHANGE_BITS); 522 523 /* Prime sc->hwsig with the initial hw line states. */ 524 at91_usart_bus_getsig(sc); 525 526errout: 527 return (err); 528} 529 530static int 531at91_usart_bus_transmit(struct uart_softc *sc) 532{ 533 bus_addr_t addr; 534 struct at91_usart_softc *atsc; 535 int err; 536 537 err = 0; 538 atsc = (struct at91_usart_softc *)sc; 539 uart_lock(sc->sc_hwmtx); 540 if (bus_dmamap_load(atsc->tx_tag, atsc->tx_map, sc->sc_txbuf, 541 sc->sc_txdatasz, at91_getaddr, &addr, 0) != 0) { 542 err = EAGAIN; 543 goto errout; 544 } 545 bus_dmamap_sync(atsc->tx_tag, atsc->tx_map, BUS_DMASYNC_PREWRITE); 546 sc->sc_txbusy = 1; 547 /* 548 * Setup the PDC to transfer the data and interrupt us when it 549 * is done. We've already requested the interrupt. 550 */ 551 WR4(&sc->sc_bas, PDC_TPR, addr); 552 WR4(&sc->sc_bas, PDC_TCR, sc->sc_txdatasz); 553 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_TXTEN); 554 WR4(&sc->sc_bas, USART_IER, USART_CSR_ENDTX); 555errout: 556 uart_unlock(sc->sc_hwmtx); 557 return (err); 558} 559 560static int 561at91_usart_bus_setsig(struct uart_softc *sc, int sig) 562{ 563 uint32_t new, old, cr; 564 struct at91_usart_softc *atsc; 565 566 atsc = (struct at91_usart_softc *)sc; 567 568 do { 569 old = sc->sc_hwsig; 570 new = old; 571 if (sig & SER_DDTR) 572 SIGCHG(sig & SER_DTR, new, SER_DTR, SER_DDTR); 573 if (sig & SER_DRTS) 574 SIGCHG(sig & SER_RTS, new, SER_RTS, SER_DRTS); 575 } while (!atomic_cmpset_32(&sc->sc_hwsig, old, new)); 576 577 cr = 0; 578 if (new & SER_DTR) 579 cr |= USART_CR_DTREN; 580 else 581 cr |= USART_CR_DTRDIS; 582 if (new & SER_RTS) 583 cr |= USART_CR_RTSEN; 584 else 585 cr |= USART_CR_RTSDIS; 586 587 uart_lock(sc->sc_hwmtx); 588 WR4(&sc->sc_bas, USART_CR, cr); 589 if (atsc->flags & USE_RTS0_WORKAROUND) { 590 /* Signal is active-low. */ 591 if (new & SER_RTS) 592 at91_pio_gpio_clear(AT91RM92_PIOA_BASE, AT91C_PIO_PA21); 593 else 594 at91_pio_gpio_set(AT91RM92_PIOA_BASE,AT91C_PIO_PA21); 595 } 596 uart_unlock(sc->sc_hwmtx); 597 598 return (0); 599} 600 601static int 602at91_usart_bus_receive(struct uart_softc *sc) 603{ 604 605 return (0); 606} 607 608static int 609at91_usart_bus_param(struct uart_softc *sc, int baudrate, int databits, 610 int stopbits, int parity) 611{ 612 613 return (at91_usart_param(&sc->sc_bas, baudrate, databits, stopbits, 614 parity)); 615} 616 617static __inline void 618at91_rx_put(struct uart_softc *sc, int key) 619{ 620 621#if defined(KDB) 622 if (sc->sc_sysdev != NULL && sc->sc_sysdev->type == UART_DEV_CONSOLE) 623 kdb_alt_break(key, &sc->sc_altbrk); 624#endif 625 uart_rx_put(sc, key); 626} 627 628static int 629at91_usart_bus_ipend(struct uart_softc *sc) 630{ 631 struct at91_usart_softc *atsc; 632 struct at91_usart_rx *p; 633 int i, ipend, len; 634 uint32_t csr; 635 636 ipend = 0; 637 atsc = (struct at91_usart_softc *)sc; 638 uart_lock(sc->sc_hwmtx); 639 csr = RD4(&sc->sc_bas, USART_CSR); 640 641 if (csr & USART_CSR_OVRE) { 642 WR4(&sc->sc_bas, USART_CR, USART_CR_RSTSTA); 643 ipend |= SER_INT_OVERRUN; 644 } 645 646 if (csr & USART_DCE_CHANGE_BITS) 647 ipend |= SER_INT_SIGCHG; 648 649 if (csr & USART_CSR_ENDTX) { 650 bus_dmamap_sync(atsc->tx_tag, atsc->tx_map, 651 BUS_DMASYNC_POSTWRITE); 652 bus_dmamap_unload(atsc->tx_tag, atsc->tx_map); 653 } 654 if (csr & (USART_CSR_TXRDY | USART_CSR_ENDTX)) { 655 if (sc->sc_txbusy) 656 ipend |= SER_INT_TXIDLE; 657 WR4(&sc->sc_bas, USART_IDR, csr & (USART_CSR_TXRDY | 658 USART_CSR_ENDTX)); 659 } 660 661 /* 662 * Due to the contraints of the DMA engine present in the 663 * atmel chip, I can't just say I have a rx interrupt pending 664 * and do all the work elsewhere. I need to look at the CSR 665 * bits right now and do things based on them to avoid races. 666 */ 667 if (atsc->flags & HAS_TIMEOUT) { 668 if (csr & USART_CSR_RXBUFF) { 669 /* 670 * We have a buffer overflow. Consume data from ping 671 * and give it back to the hardware before worrying 672 * about pong, to minimze data loss. Insert an overrun 673 * marker after the contents of the pong buffer. 674 */ 675 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_RXTDIS); 676 bus_dmamap_sync(atsc->rx_tag, atsc->ping->map, 677 BUS_DMASYNC_POSTREAD); 678 for (i = 0; i < sc->sc_rxfifosz; i++) 679 at91_rx_put(sc, atsc->ping->buffer[i]); 680 bus_dmamap_sync(atsc->rx_tag, atsc->ping->map, 681 BUS_DMASYNC_PREREAD); 682 WR4(&sc->sc_bas, PDC_RPR, atsc->ping->pa); 683 WR4(&sc->sc_bas, PDC_RCR, sc->sc_rxfifosz); 684 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_RXTEN); 685 bus_dmamap_sync(atsc->rx_tag, atsc->pong->map, 686 BUS_DMASYNC_POSTREAD); 687 for (i = 0; i < sc->sc_rxfifosz; i++) 688 at91_rx_put(sc, atsc->pong->buffer[i]); 689 uart_rx_put(sc, UART_STAT_OVERRUN); 690 bus_dmamap_sync(atsc->rx_tag, atsc->pong->map, 691 BUS_DMASYNC_PREREAD); 692 WR4(&sc->sc_bas, PDC_RNPR, atsc->pong->pa); 693 WR4(&sc->sc_bas, PDC_RNCR, sc->sc_rxfifosz); 694 ipend |= SER_INT_RXREADY; 695 } else if (csr & USART_CSR_ENDRX) { 696 /* 697 * Consume data from ping of ping pong buffer, but leave 698 * current pong in place, as it has become the new ping. 699 * We need to copy data and setup the old ping as the 700 * new pong when we're done. 701 */ 702 bus_dmamap_sync(atsc->rx_tag, atsc->ping->map, 703 BUS_DMASYNC_POSTREAD); 704 for (i = 0; i < sc->sc_rxfifosz; i++) 705 at91_rx_put(sc, atsc->ping->buffer[i]); 706 p = atsc->ping; 707 atsc->ping = atsc->pong; 708 atsc->pong = p; 709 bus_dmamap_sync(atsc->rx_tag, atsc->pong->map, 710 BUS_DMASYNC_PREREAD); 711 WR4(&sc->sc_bas, PDC_RNPR, atsc->pong->pa); 712 WR4(&sc->sc_bas, PDC_RNCR, sc->sc_rxfifosz); 713 ipend |= SER_INT_RXREADY; 714 } else if (csr & USART_CSR_TIMEOUT) { 715 /* 716 * On a timeout, one of the following applies: 717 * 1. Two empty buffers. The last received byte exactly 718 * filled a buffer, causing an ENDTX that got 719 * processed earlier; no new bytes have arrived. 720 * 2. Ping buffer contains some data and pong is empty. 721 * This should be the most common timeout condition. 722 * 3. Ping buffer is full and pong is now being filled. 723 * This is exceedingly rare; it can happen only if 724 * the ping buffer is almost full when a timeout is 725 * signaled, and then dataflow resumes and the ping 726 * buffer filled up between the time we read the 727 * status register above and the point where the 728 * RXTDIS takes effect here. Yes, it can happen. 729 * Because dataflow can resume at any time following a 730 * timeout (it may have already resumed before we get 731 * here), it's important to minimize the time the PDC is 732 * disabled -- just long enough to take the ping buffer 733 * out of service (so we can consume it) and install the 734 * pong buffer as the active one. Note that in case 3 735 * the hardware has already done the ping-pong swap. 736 */ 737 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_RXTDIS); 738 if (RD4(&sc->sc_bas, PDC_RNCR) == 0) { 739 len = sc->sc_rxfifosz; 740 } else { 741 len = sc->sc_rxfifosz - RD4(&sc->sc_bas, PDC_RCR); 742 WR4(&sc->sc_bas, PDC_RPR, atsc->pong->pa); 743 WR4(&sc->sc_bas, PDC_RCR, sc->sc_rxfifosz); 744 WR4(&sc->sc_bas, PDC_RNCR, 0); 745 } 746 WR4(&sc->sc_bas, USART_CR, USART_CR_STTTO); 747 WR4(&sc->sc_bas, PDC_PTCR, PDC_PTCR_RXTEN); 748 bus_dmamap_sync(atsc->rx_tag, atsc->ping->map, 749 BUS_DMASYNC_POSTREAD); 750 for (i = 0; i < len; i++) 751 at91_rx_put(sc, atsc->ping->buffer[i]); 752 bus_dmamap_sync(atsc->rx_tag, atsc->ping->map, 753 BUS_DMASYNC_PREREAD); 754 p = atsc->ping; 755 atsc->ping = atsc->pong; 756 atsc->pong = p; 757 WR4(&sc->sc_bas, PDC_RNPR, atsc->pong->pa); 758 WR4(&sc->sc_bas, PDC_RNCR, sc->sc_rxfifosz); 759 ipend |= SER_INT_RXREADY; 760 } 761 } else if (csr & USART_CSR_RXRDY) { 762 /* 763 * We have another charater in a device that doesn't support 764 * timeouts, so we do it one character at a time. 765 */ 766 at91_rx_put(sc, RD4(&sc->sc_bas, USART_RHR) & 0xff); 767 ipend |= SER_INT_RXREADY; 768 } 769 770 if (csr & USART_CSR_RXBRK) { 771 ipend |= SER_INT_BREAK; 772 WR4(&sc->sc_bas, USART_CR, USART_CR_RSTSTA); 773 } 774 uart_unlock(sc->sc_hwmtx); 775 return (ipend); 776} 777 778static int 779at91_usart_bus_flush(struct uart_softc *sc, int what) 780{ 781 782 return (0); 783} 784 785static int 786at91_usart_bus_getsig(struct uart_softc *sc) 787{ 788 uint32_t csr, new, old, sig; 789 790 /* 791 * Note that the atmel channel status register DCE status bits reflect 792 * the electrical state of the lines, not the logical state. Since they 793 * are logically active-low signals, we invert the tests here. 794 */ 795 do { 796 old = sc->sc_hwsig; 797 sig = old; 798 csr = RD4(&sc->sc_bas, USART_CSR); 799 SIGCHG(!(csr & USART_CSR_DSR), sig, SER_DSR, SER_DDSR); 800 SIGCHG(!(csr & USART_CSR_CTS), sig, SER_CTS, SER_DCTS); 801 SIGCHG(!(csr & USART_CSR_DCD), sig, SER_DCD, SER_DDCD); 802 SIGCHG(!(csr & USART_CSR_RI), sig, SER_RI, SER_DRI); 803 new = sig & ~SER_MASK_DELTA; 804 } while (!atomic_cmpset_32(&sc->sc_hwsig, old, new)); 805 806 return (sig); 807} 808 809static int 810at91_usart_bus_ioctl(struct uart_softc *sc, int request, intptr_t data) 811{ 812 813 switch (request) { 814 case UART_IOCTL_BREAK: 815 case UART_IOCTL_IFLOW: 816 case UART_IOCTL_OFLOW: 817 break; 818 case UART_IOCTL_BAUD: 819 /* only if we know our master clock rate */ 820 if (DEFAULT_RCLK != 0) 821 WR4(&sc->sc_bas, USART_BRGR, 822 BAUD2DIVISOR(*(int *)data)); 823 return (0); 824 } 825 return (EINVAL); 826} 827 828 829static void 830at91_usart_bus_grab(struct uart_softc *sc) 831{ 832 833 uart_lock(sc->sc_hwmtx); 834 WR4(&sc->sc_bas, USART_IDR, USART_CSR_RXRDY); 835 uart_unlock(sc->sc_hwmtx); 836} 837 838static void 839at91_usart_bus_ungrab(struct uart_softc *sc) 840{ 841 842 uart_lock(sc->sc_hwmtx); 843 WR4(&sc->sc_bas, USART_IER, USART_CSR_RXRDY); 844 uart_unlock(sc->sc_hwmtx); 845} 846 847struct uart_class at91_usart_class = { 848 "at91_usart", 849 at91_usart_methods, 850 sizeof(struct at91_usart_softc), 851 .uc_ops = &at91_usart_ops, 852 .uc_range = 8 853}; 854