1 /* $OpenBSD: com.c,v 1.63 2001/04/17 04:30:49 aaron Exp $ */ 2 /* $NetBSD: com.c,v 1.82.4.1 1996/06/02 09:08:00 mrg Exp $ */ 3 4 /* 5 * Copyright (c) 1997 - 1999, Jason Downs. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. Neither the name(s) of the author(s) nor the name OpenBSD 16 * may be used to endorse or promote products derived from this software 17 * without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS 20 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 22 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, 23 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 25 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 26 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 29 * SUCH DAMAGE. 30 */ 31 /*- 32 * Copyright (c) 1993, 1994, 1995, 1996 33 * Charles M. Hannum. All rights reserved. 34 * Copyright (c) 1991 The Regents of the University of California. 35 * All rights reserved. 36 * 37 * Redistribution and use in source and binary forms, with or without 38 * modification, are permitted provided that the following conditions 39 * are met: 40 * 1. Redistributions of source code must retain the above copyright 41 * notice, this list of conditions and the following disclaimer. 42 * 2. Redistributions in binary form must reproduce the above copyright 43 * notice, this list of conditions and the following disclaimer in the 44 * documentation and/or other materials provided with the distribution. 45 * 3. All advertising materials mentioning features or use of this software 46 * must display the following acknowledgement: 47 * This product includes software developed by the University of 48 * California, Berkeley and its contributors. 49 * 4. Neither the name of the University nor the names of its contributors 50 * may be used to endorse or promote products derived from this software 51 * without specific prior written permission. 52 * 53 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 54 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 55 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 56 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 57 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 58 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 59 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 60 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 61 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 62 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 63 * SUCH DAMAGE. 64 * 65 * @(#)com.c 7.5 (Berkeley) 5/16/91 66 */ 67 68 /* 69 * COM driver, based on HP dca driver 70 * uses National Semiconductor NS16450/NS16550AF UART 71 */ 72 #include <sys/param.h> 73 #include <sys/systm.h> 74 #include <sys/ioctl.h> 75 #include <sys/select.h> 76 #include <sys/tty.h> 77 #include <sys/proc.h> 78 #include <sys/user.h> 79 #include <sys/conf.h> 80 #include <sys/file.h> 81 #include <sys/uio.h> 82 #include <sys/kernel.h> 83 #include <sys/syslog.h> 84 #include <sys/types.h> 85 #include <sys/device.h> 86 #include <sys/vnode.h> 87 #ifdef DDB 88 #include <ddb/db_var.h> 89 #endif 90 91 #include <machine/bus.h> 92 #include <machine/intr.h> 93 94 #include <dev/cons.h> 95 96 #include <dev/ic/comreg.h> 97 #include <dev/ic/comvar.h> 98 #include <dev/ic/ns16550reg.h> 99 #ifdef COM_HAYESP 100 #include <dev/ic/hayespreg.h> 101 #endif 102 #define com_lcr com_cfcr 103 104 #include "com.h" 105 106 #if NCOM_ISA || NCOM_ISAPNP 107 #include <dev/isa/isavar.h> /* XXX */ 108 #endif 109 110 /* XXX: These belong elsewhere */ 111 cdev_decl(com); 112 bdev_decl(com); 113 114 static u_char tiocm_xxx2mcr __P((int)); 115 116 /* 117 * XXX the following two cfattach structs should be different, and possibly 118 * XXX elsewhere. 119 */ 120 int comprobe __P((struct device *, void *, void *)); 121 void comattach __P((struct device *, struct device *, void *)); 122 void compwroff __P((struct com_softc *)); 123 void com_raisedtr __P((void *)); 124 125 #if NCOM_ISA 126 struct cfattach com_isa_ca = { 127 sizeof(struct com_softc), comprobe, comattach 128 }; 129 #endif 130 131 #if NCOM_ISAPNP 132 struct cfattach com_isapnp_ca = { 133 sizeof(struct com_softc), comprobe, comattach 134 }; 135 #endif 136 137 #if NCOM_COMMULTI 138 struct cfattach com_commulti_ca = { 139 sizeof(struct com_softc), comprobe, comattach 140 }; 141 #endif 142 143 struct cfdriver com_cd = { 144 NULL, "com", DV_TTY 145 }; 146 147 #ifndef CONSPEED 148 #define CONSPEED B9600 149 #endif 150 151 #ifdef COMCONSOLE 152 int comdefaultrate = CONSPEED; /* XXX why set default? */ 153 #else 154 int comdefaultrate = TTYDEF_SPEED; 155 #endif 156 int comconsaddr; 157 int comconsinit; 158 int comconsattached; 159 int comconsrate; 160 bus_space_tag_t comconsiot; 161 bus_space_handle_t comconsioh; 162 tcflag_t comconscflag = TTYDEF_CFLAG; 163 164 struct timeout compoll_to; 165 166 int commajor; 167 int comsopen = 0; 168 int comevents = 0; 169 170 #ifdef KGDB 171 #include <sys/kgdb.h> 172 173 static int com_kgdb_addr; 174 static bus_space_tag_t com_kgdb_iot; 175 static bus_space_handle_t com_kgdb_ioh; 176 static int com_kgdb_attached; 177 178 int com_kgdb_getc __P((void *)); 179 void com_kgdb_putc __P((void *, int)); 180 #endif /* KGDB */ 181 182 #define DEVUNIT(x) (minor(x) & 0x7f) 183 #define DEVCUA(x) (minor(x) & 0x80) 184 185 /* Macros to clear/set/test flags. */ 186 #define SET(t, f) (t) |= (f) 187 #define CLR(t, f) (t) &= ~(f) 188 #define ISSET(t, f) ((t) & (f)) 189 190 /* Macros for determining bus type. */ 191 #if NCOM_ISA 192 #define IS_ISA(parent) \ 193 (strcmp((parent)->dv_cfdata->cf_driver->cd_name, "isa") == 0) 194 #else 195 #define IS_ISA(parent) 0 196 #endif 197 198 #if NCOM_ISAPNP 199 #define IS_ISAPNP(parent) \ 200 (strcmp((parent)->dv_cfdata->cf_driver->cd_name, "isapnp") == 0) 201 #else 202 #define IS_ISAPNP(parent) 0 203 #endif 204 205 int 206 comspeed(freq, speed) 207 long freq; 208 long speed; 209 { 210 #define divrnd(n, q) (((n)*2/(q)+1)/2) /* divide and round off */ 211 212 int x, err; 213 214 if (speed == 0) 215 return 0; 216 if (speed < 0) 217 return -1; 218 x = divrnd((freq / 16), speed); 219 if (x <= 0) 220 return -1; 221 err = divrnd((freq / 16) * 1000, speed * x) - 1000; 222 if (err < 0) 223 err = -err; 224 if (err > COM_TOLERANCE) 225 return -1; 226 return x; 227 228 #undef divrnd 229 } 230 231 int 232 comprobe1(iot, ioh) 233 bus_space_tag_t iot; 234 bus_space_handle_t ioh; 235 { 236 int i, k; 237 238 /* force access to id reg */ 239 bus_space_write_1(iot, ioh, com_lcr, 0); 240 bus_space_write_1(iot, ioh, com_iir, 0); 241 for (i = 0; i < 32; i++) { 242 k = bus_space_read_1(iot, ioh, com_iir); 243 if (k & 0x38) { 244 bus_space_read_1(iot, ioh, com_data); /* cleanup */ 245 } else 246 break; 247 } 248 if (i >= 32) 249 return 0; 250 251 return 1; 252 } 253 254 #ifdef COM_HAYESP 255 int 256 comprobeHAYESP(hayespioh, sc) 257 bus_space_handle_t hayespioh; 258 struct com_softc *sc; 259 { 260 char val, dips; 261 int combaselist[] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8 }; 262 bus_space_tag_t iot = sc->sc_iot; 263 264 /* 265 * Hayes ESP cards have two iobases. One is for compatibility with 266 * 16550 serial chips, and at the same ISA PC base addresses. The 267 * other is for ESP-specific enhanced features, and lies at a 268 * different addressing range entirely (0x140, 0x180, 0x280, or 0x300). 269 */ 270 271 /* Test for ESP signature */ 272 if ((bus_space_read_1(iot, hayespioh, 0) & 0xf3) == 0) 273 return 0; 274 275 /* 276 * ESP is present at ESP enhanced base address; unknown com port 277 */ 278 279 /* Get the dip-switch configurations */ 280 bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_GETDIPS); 281 dips = bus_space_read_1(iot, hayespioh, HAYESP_STATUS1); 282 283 /* Determine which com port this ESP card services: bits 0,1 of */ 284 /* dips is the port # (0-3); combaselist[val] is the com_iobase */ 285 if (sc->sc_iobase != combaselist[dips & 0x03]) 286 return 0; 287 288 printf(": ESP"); 289 290 /* Check ESP Self Test bits. */ 291 /* Check for ESP version 2.0: bits 4,5,6 == 010 */ 292 bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_GETTEST); 293 val = bus_space_read_1(iot, hayespioh, HAYESP_STATUS1); /* Clear reg 1 */ 294 val = bus_space_read_1(iot, hayespioh, HAYESP_STATUS2); 295 if ((val & 0x70) < 0x20) { 296 printf("-old (%o)", val & 0x70); 297 /* we do not support the necessary features */ 298 return 0; 299 } 300 301 /* Check for ability to emulate 16550: bit 8 == 1 */ 302 if ((dips & 0x80) == 0) { 303 printf(" slave"); 304 /* XXX Does slave really mean no 16550 support?? */ 305 return 0; 306 } 307 308 /* 309 * If we made it this far, we are a full-featured ESP v2.0 (or 310 * better), at the correct com port address. 311 */ 312 313 SET(sc->sc_hwflags, COM_HW_HAYESP); 314 printf(", 1024 byte fifo\n"); 315 return 1; 316 } 317 #endif 318 319 int 320 comprobe(parent, match, aux) 321 struct device *parent; 322 void *match, *aux; 323 { 324 bus_space_tag_t iot; 325 bus_space_handle_t ioh; 326 int iobase, needioh; 327 int rv = 1; 328 329 /* 330 * XXX should be broken out into functions for isa probe and 331 * XXX for commulti probe, with a helper function that contains 332 * XXX most of the interesting stuff. 333 */ 334 #if NCOM_ISA || NCOM_ISAPNP 335 if (IS_ISA(parent) || IS_ISAPNP(parent)) { 336 struct isa_attach_args *ia = aux; 337 338 iot = ia->ia_iot; 339 iobase = ia->ia_iobase; 340 if (IS_ISAPNP(parent)) { 341 ioh = ia->ia_ioh; 342 needioh = 0; 343 } else 344 needioh = 1; 345 } else 346 #endif 347 #if NCOM_COMMULTI 348 if (1) { 349 struct cfdata *cf = match; 350 struct commulti_attach_args *ca = aux; 351 352 if (cf->cf_loc[0] != -1 && cf->cf_loc[0] != ca->ca_slave) 353 return (0); 354 355 iot = ca->ca_iot; 356 iobase = ca->ca_iobase; 357 ioh = ca->ca_ioh; 358 needioh = 0; 359 } else 360 #endif 361 return(0); /* This cannot happen */ 362 363 #ifdef KGDB 364 if (iobase == com_kgdb_addr) 365 goto out; 366 #endif 367 /* if it's in use as console, it's there. */ 368 if (iobase == comconsaddr && !comconsattached) 369 goto out; 370 371 if (needioh && bus_space_map(iot, iobase, COM_NPORTS, 0, &ioh)) { 372 rv = 0; 373 goto out; 374 } 375 rv = comprobe1(iot, ioh); 376 if (needioh) 377 bus_space_unmap(iot, ioh, COM_NPORTS); 378 379 out: 380 #if NCOM_ISA 381 if (rv && IS_ISA(parent)) { 382 struct isa_attach_args *ia = aux; 383 384 ia->ia_iosize = COM_NPORTS; 385 ia->ia_msize = 0; 386 } 387 #endif 388 return (rv); 389 } 390 391 void 392 comattach(parent, self, aux) 393 struct device *parent, *self; 394 void *aux; 395 { 396 struct com_softc *sc = (void *)self; 397 int iobase; 398 #if NCOM_ISA || NCOM_ISAPNP || NCOM_COMMULTI 399 int irq; 400 #endif 401 bus_space_tag_t iot; 402 bus_space_handle_t ioh; 403 #ifdef COM_HAYESP 404 int hayesp_ports[] = { 0x140, 0x180, 0x280, 0x300, 0 }; 405 int *hayespp; 406 #endif 407 u_int8_t lcr; 408 409 /* 410 * XXX should be broken out into functions for isa attach and 411 * XXX for commulti attach, with a helper function that contains 412 * XXX most of the interesting stuff. 413 */ 414 sc->sc_hwflags = 0; 415 sc->sc_swflags = 0; 416 #if NCOM_ISA || NCOM_ISAPNP 417 if (IS_ISA(parent) || IS_ISAPNP(parent)) { 418 struct isa_attach_args *ia = aux; 419 420 /* 421 * We're living on an isa. 422 */ 423 iobase = ia->ia_iobase; 424 iot = ia->ia_iot; 425 if (IS_ISAPNP(parent)) { 426 /* No console support! */ 427 ioh = ia->ia_ioh; 428 } else { 429 #ifdef KGDB 430 if ((iobase != comconsaddr) && 431 (iobase != com_kgdb_addr)) { 432 #else 433 if (iobase != comconsaddr) { 434 #endif 435 if (bus_space_map(iot, iobase, COM_NPORTS, 0, 436 &ioh)) 437 panic("comattach: io mapping failed"); 438 } else 439 #ifdef KGDB 440 if (iobase == comconsaddr) { 441 ioh = comconsioh; 442 } else { 443 ioh = com_kgdb_ioh; 444 } 445 #else 446 ioh = comconsioh; 447 #endif 448 } 449 irq = ia->ia_irq; 450 } else 451 #endif 452 #if NCOM_COMMULTI 453 if (1) { 454 struct commulti_attach_args *ca = aux; 455 456 /* 457 * We're living on a commulti. 458 */ 459 iobase = ca->ca_iobase; 460 iot = ca->ca_iot; 461 ioh = ca->ca_ioh; 462 irq = IRQUNK; 463 464 if (ca->ca_noien) 465 SET(sc->sc_hwflags, COM_HW_NOIEN); 466 } else 467 #endif 468 panic("comattach: impossible"); 469 470 sc->sc_iot = iot; 471 sc->sc_ioh = ioh; 472 sc->sc_iobase = iobase; 473 sc->sc_frequency = COM_FREQ; 474 475 if (iobase == comconsaddr) { 476 comconsattached = 1; 477 478 /* 479 * Need to reset baud rate, etc. of next print so reset 480 * comconsinit. Also make sure console is always "hardwired". 481 */ 482 delay(1000); /* wait for output to finish */ 483 comconsinit = 0; 484 SET(sc->sc_hwflags, COM_HW_CONSOLE); 485 SET(sc->sc_swflags, COM_SW_SOFTCAR); 486 } 487 488 #ifdef COM_HAYESP 489 /* Look for a Hayes ESP board. */ 490 for (hayespp = hayesp_ports; *hayespp != 0; hayespp++) { 491 bus_space_handle_t hayespioh; 492 493 #define HAYESP_NPORTS 8 /* XXX XXX XXX ??? ??? ??? */ 494 if (bus_space_map(iot, *hayespp, HAYESP_NPORTS, 0, &hayespioh)) 495 continue; 496 if (comprobeHAYESP(hayespioh, sc)) { 497 sc->sc_hayespbase = *hayespp; 498 sc->sc_hayespioh = hayespioh; 499 sc->sc_fifolen = 1024; 500 break; 501 } 502 bus_space_unmap(iot, hayespioh, HAYESP_NPORTS); 503 } 504 /* No ESP; look for other things. */ 505 if (*hayespp == 0) { 506 #endif 507 508 /* 509 * Probe for all known forms of UART. 510 */ 511 lcr = bus_space_read_1(iot, ioh, com_lcr); 512 513 bus_space_write_1(iot, ioh, com_lcr, 0xbf); 514 bus_space_write_1(iot, ioh, com_efr, 0); 515 bus_space_write_1(iot, ioh, com_lcr, 0); 516 517 bus_space_write_1(iot, ioh, com_fifo, FIFO_ENABLE); 518 delay(100); 519 520 switch(bus_space_read_1(iot, ioh, com_iir) >> 6) { 521 case 0: 522 sc->sc_uarttype = COM_UART_16450; 523 break; 524 case 2: 525 sc->sc_uarttype = COM_UART_16550; 526 break; 527 case 3: 528 sc->sc_uarttype = COM_UART_16550A; 529 break; 530 default: 531 sc->sc_uarttype = COM_UART_UNKNOWN; 532 break; 533 } 534 535 if (sc->sc_uarttype == COM_UART_16550A) { /* Probe for ST16650s */ 536 bus_space_write_1(iot, ioh, com_lcr, lcr | LCR_DLAB); 537 if (bus_space_read_1(iot, ioh, com_efr) == 0) { 538 sc->sc_uarttype = COM_UART_ST16650; 539 } else { 540 bus_space_write_1(iot, ioh, com_lcr, 0xbf); 541 if (bus_space_read_1(iot, ioh, com_efr) == 0) 542 sc->sc_uarttype = COM_UART_ST16650V2; 543 } 544 } 545 546 if (sc->sc_uarttype == COM_UART_16550A) { /* Probe for TI16750s */ 547 bus_space_write_1(iot, ioh, com_lcr, lcr | LCR_DLAB); 548 bus_space_write_1(iot, ioh, com_fifo, 549 FIFO_ENABLE | FIFO_ENABLE_64BYTE); 550 if ((bus_space_read_1(iot, ioh, com_iir) >> 5) == 7) { 551 #if 0 552 bus_space_write_1(iot, ioh, com_lcr, 0); 553 if ((bus_space_read_1(iot, ioh, com_iir) >> 5) == 6) 554 #endif 555 sc->sc_uarttype = COM_UART_TI16750; 556 } 557 bus_space_write_1(iot, ioh, com_fifo, FIFO_ENABLE); 558 } 559 560 bus_space_write_1(iot, ioh, com_lcr, lcr); 561 if (sc->sc_uarttype == COM_UART_16450) { /* Probe for 8250 */ 562 u_int8_t scr0, scr1, scr2; 563 564 scr0 = bus_space_read_1(iot, ioh, com_scratch); 565 bus_space_write_1(iot, ioh, com_scratch, 0xa5); 566 scr1 = bus_space_read_1(iot, ioh, com_scratch); 567 bus_space_write_1(iot, ioh, com_scratch, 0x5a); 568 scr2 = bus_space_read_1(iot, ioh, com_scratch); 569 bus_space_write_1(iot, ioh, com_scratch, scr0); 570 571 if ((scr1 != 0xa5) || (scr2 != 0x5a)) 572 sc->sc_uarttype = COM_UART_8250; 573 } 574 575 /* 576 * Print UART type and initialize ourself. 577 */ 578 sc->sc_fifolen = 1; /* default */ 579 switch (sc->sc_uarttype) { 580 case COM_UART_UNKNOWN: 581 printf(": unknown uart\n"); 582 break; 583 case COM_UART_8250: 584 printf(": ns8250, no fifo\n"); 585 break; 586 case COM_UART_16450: 587 printf(": ns16450, no fifo\n"); 588 break; 589 case COM_UART_16550: 590 printf(": ns16550, no working fifo\n"); 591 break; 592 case COM_UART_16550A: 593 printf(": ns16550a, 16 byte fifo\n"); 594 SET(sc->sc_hwflags, COM_HW_FIFO); 595 sc->sc_fifolen = 16; 596 break; 597 case COM_UART_ST16650: 598 printf(": st16650, no working fifo\n"); 599 break; 600 case COM_UART_ST16650V2: 601 printf(": st16650, 32 byte fifo\n"); 602 SET(sc->sc_hwflags, COM_HW_FIFO); 603 sc->sc_fifolen = 32; 604 break; 605 case COM_UART_TI16750: 606 printf(": ti16750, 64 byte fifo\n"); 607 SET(sc->sc_hwflags, COM_HW_FIFO); 608 sc->sc_fifolen = 64; 609 break; 610 default: 611 panic("comattach: bad fifo type"); 612 } 613 614 /* clear and disable fifo */ 615 bus_space_write_1(iot, ioh, com_fifo, FIFO_RCV_RST | FIFO_XMT_RST); 616 (void)bus_space_read_1(iot, ioh, com_data); 617 bus_space_write_1(iot, ioh, com_fifo, 0); 618 #ifdef COM_HAYESP 619 } 620 #endif 621 622 /* disable interrupts */ 623 bus_space_write_1(iot, ioh, com_ier, 0); 624 bus_space_write_1(iot, ioh, com_mcr, 0); 625 626 #if NCOM_ISA || NCOM_ISAPNP || NCOM_COMMULTI 627 if (irq != IRQUNK) { 628 #if NCOM_ISA || NCOM_ISAPNP 629 if (IS_ISA(parent) || IS_ISAPNP(parent)) { 630 struct isa_attach_args *ia = aux; 631 632 #ifdef KGDB 633 if (iobase == com_kgdb_addr) { 634 sc->sc_ih = isa_intr_establish(ia->ia_ic, irq, 635 IST_EDGE, IPL_HIGH, kgdbintr, sc, 636 sc->sc_dev.dv_xname); 637 } else { 638 sc->sc_ih = isa_intr_establish(ia->ia_ic, irq, 639 IST_EDGE, IPL_TTY, comintr, sc, 640 sc->sc_dev.dv_xname); 641 } 642 #else 643 sc->sc_ih = isa_intr_establish(ia->ia_ic, irq, 644 IST_EDGE, IPL_TTY, comintr, sc, 645 sc->sc_dev.dv_xname); 646 #endif /* KGDB */ 647 } else 648 #endif 649 panic("comattach: IRQ but can't have one"); 650 } 651 #endif 652 #ifdef KGDB 653 /* 654 * Allow kgdb to "take over" this port. If this is 655 * the kgdb device, it has exclusive use. 656 */ 657 658 if (iot == com_kgdb_iot && iobase == com_kgdb_addr && 659 !ISSET(sc->sc_hwflags, COM_HW_CONSOLE)) { 660 printf("%s: kgdb\n", sc->sc_dev.dv_xname); 661 SET(sc->sc_hwflags, COM_HW_KGDB); 662 com_enable_debugport(sc); 663 com_kgdb_attached = 1; 664 } 665 #endif /* KGDB */ 666 667 /* XXX maybe move up some? */ 668 if (ISSET(sc->sc_hwflags, COM_HW_CONSOLE)) { 669 int maj; 670 671 /* locate the major number */ 672 for (maj = 0; maj < nchrdev; maj++) 673 if (cdevsw[maj].d_open == comopen) 674 break; 675 676 if (maj < nchrdev && cn_tab->cn_dev == NODEV) 677 cn_tab->cn_dev = makedev(maj, sc->sc_dev.dv_unit); 678 679 printf("%s: console\n", sc->sc_dev.dv_xname); 680 } 681 682 if (!timeout_initialized(&compoll_to)) 683 timeout_set(&compoll_to, compoll, NULL); 684 685 timeout_set(&sc->sc_diag_tmo, comdiag, sc); 686 timeout_set(&sc->sc_dtr_tmo, com_raisedtr, sc); 687 688 /* 689 * If there are no enable/disable functions, assume the device 690 * is always enabled. 691 */ 692 if (!sc->enable) 693 sc->enabled = 1; 694 } 695 696 #ifdef KGDB 697 void 698 com_enable_debugport(sc) 699 struct com_softc *sc; 700 { 701 int s; 702 703 /* Turn on line break interrupt, set carrier. */ 704 s = splhigh(); 705 SET(sc->sc_ier, IER_ERXRDY); 706 bus_space_write_1(sc->sc_iot, sc->sc_ioh, com_ier, sc->sc_ier); 707 SET(sc->sc_mcr, MCR_DTR | MCR_RTS | MCR_IENABLE); 708 bus_space_write_1(sc->sc_iot, sc->sc_ioh, com_mcr, sc->sc_mcr); 709 710 splx(s); 711 } 712 #endif /* KGDB */ 713 714 int 715 com_detach(self, flags) 716 struct device *self; 717 int flags; 718 { 719 struct com_softc *sc = (struct com_softc *)self; 720 int maj, mn; 721 722 /* locate the major number */ 723 for (maj = 0; maj < nchrdev; maj++) 724 if (cdevsw[maj].d_open == comopen) 725 break; 726 727 /* Nuke the vnodes for any open instances. */ 728 mn = self->dv_unit; 729 vdevgone(maj, mn, mn, VCHR); 730 731 /* XXX a symbolic constant for the cua bit would be nicer. */ 732 mn |= 0x80; 733 vdevgone(maj, mn, mn, VCHR); 734 735 /* Detach and free the tty. */ 736 if (sc->sc_tty) { 737 tty_detach(sc->sc_tty); 738 ttyfree(sc->sc_tty); 739 } 740 741 timeout_del(&sc->sc_dtr_tmo); 742 timeout_del(&sc->sc_diag_tmo); 743 744 return (0); 745 } 746 747 int 748 com_activate(self, act) 749 struct device *self; 750 enum devact act; 751 { 752 struct com_softc *sc = (struct com_softc *)self; 753 int s, rv = 0; 754 755 s = spltty(); 756 switch (act) { 757 case DVACT_ACTIVATE: 758 rv = EOPNOTSUPP; 759 break; 760 761 case DVACT_DEACTIVATE: 762 #ifdef KGDB 763 if (sc->sc_hwflags & (COM_HW_CONSOLE|COM_HW_KGDB)) { 764 #else 765 if (sc->sc_hwflags & COM_HW_CONSOLE) { 766 #endif /* KGDB */ 767 rv = EBUSY; 768 break; 769 } 770 771 if (sc->disable != NULL && sc->enabled != 0) { 772 (*sc->disable)(sc); 773 sc->enabled = 0; 774 } 775 break; 776 } 777 splx(s); 778 return (rv); 779 } 780 781 int 782 comopen(dev, flag, mode, p) 783 dev_t dev; 784 int flag, mode; 785 struct proc *p; 786 { 787 int unit = DEVUNIT(dev); 788 struct com_softc *sc; 789 bus_space_tag_t iot; 790 bus_space_handle_t ioh; 791 struct tty *tp; 792 int s; 793 int error = 0; 794 795 if (unit >= com_cd.cd_ndevs) 796 return ENXIO; 797 sc = com_cd.cd_devs[unit]; 798 if (!sc) 799 return ENXIO; 800 801 #ifdef KGDB 802 /* 803 * If this is the kgdb port, no other use is permitted. 804 */ 805 if (ISSET(sc->sc_hwflags, COM_HW_KGDB)) 806 return (EBUSY); 807 #endif /* KGDB */ 808 809 s = spltty(); 810 if (!sc->sc_tty) { 811 tp = sc->sc_tty = ttymalloc(); 812 tty_attach(tp); 813 } else 814 tp = sc->sc_tty; 815 splx(s); 816 817 tp->t_oproc = comstart; 818 tp->t_param = comparam; 819 tp->t_dev = dev; 820 if (!ISSET(tp->t_state, TS_ISOPEN)) { 821 SET(tp->t_state, TS_WOPEN); 822 ttychars(tp); 823 tp->t_iflag = TTYDEF_IFLAG; 824 tp->t_oflag = TTYDEF_OFLAG; 825 if (ISSET(sc->sc_hwflags, COM_HW_CONSOLE)) 826 tp->t_cflag = comconscflag; 827 else 828 tp->t_cflag = TTYDEF_CFLAG; 829 if (ISSET(sc->sc_swflags, COM_SW_CLOCAL)) 830 SET(tp->t_cflag, CLOCAL); 831 if (ISSET(sc->sc_swflags, COM_SW_CRTSCTS)) 832 SET(tp->t_cflag, CRTSCTS); 833 if (ISSET(sc->sc_swflags, COM_SW_MDMBUF)) 834 SET(tp->t_cflag, MDMBUF); 835 tp->t_lflag = TTYDEF_LFLAG; 836 tp->t_ispeed = tp->t_ospeed = comdefaultrate; 837 838 s = spltty(); 839 840 sc->sc_initialize = 1; 841 comparam(tp, &tp->t_termios); 842 ttsetwater(tp); 843 844 if (comsopen++ == 0) 845 timeout_add(&compoll_to, 1); 846 847 sc->sc_ibufp = sc->sc_ibuf = sc->sc_ibufs[0]; 848 sc->sc_ibufhigh = sc->sc_ibuf + COM_IHIGHWATER; 849 sc->sc_ibufend = sc->sc_ibuf + COM_IBUFSIZE; 850 851 iot = sc->sc_iot; 852 ioh = sc->sc_ioh; 853 854 /* 855 * Wake up the sleepy heads. 856 */ 857 switch (sc->sc_uarttype) { 858 case COM_UART_ST16650: 859 case COM_UART_ST16650V2: 860 bus_space_write_1(iot, ioh, com_lcr, 0xbf); 861 bus_space_write_1(iot, ioh, com_efr, EFR_ECB); 862 bus_space_write_1(iot, ioh, com_ier, 0); 863 bus_space_write_1(iot, ioh, com_efr, 0); 864 bus_space_write_1(iot, ioh, com_lcr, 0); 865 break; 866 case COM_UART_TI16750: 867 bus_space_write_1(iot, ioh, com_ier, 0); 868 break; 869 } 870 871 #ifdef COM_HAYESP 872 /* Setup the ESP board */ 873 if (ISSET(sc->sc_hwflags, COM_HW_HAYESP)) { 874 bus_space_handle_t hayespioh = sc->sc_hayespioh; 875 876 bus_space_write_1(iot, ioh, com_fifo, 877 FIFO_DMA_MODE|FIFO_ENABLE| 878 FIFO_RCV_RST|FIFO_XMT_RST|FIFO_TRIGGER_8); 879 880 /* Set 16550 compatibility mode */ 881 bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETMODE); 882 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 883 HAYESP_MODE_FIFO|HAYESP_MODE_RTS| 884 HAYESP_MODE_SCALE); 885 886 /* Set RTS/CTS flow control */ 887 bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETFLOWTYPE); 888 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, HAYESP_FLOW_RTS); 889 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, HAYESP_FLOW_CTS); 890 891 /* Set flow control levels */ 892 bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETRXFLOW); 893 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 894 HAYESP_HIBYTE(HAYESP_RXHIWMARK)); 895 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 896 HAYESP_LOBYTE(HAYESP_RXHIWMARK)); 897 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 898 HAYESP_HIBYTE(HAYESP_RXLOWMARK)); 899 bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 900 HAYESP_LOBYTE(HAYESP_RXLOWMARK)); 901 } else 902 #endif 903 if (ISSET(sc->sc_hwflags, COM_HW_FIFO)) { 904 u_int8_t fifo = FIFO_ENABLE|FIFO_RCV_RST|FIFO_XMT_RST; 905 u_int8_t lcr; 906 907 if (tp->t_ispeed <= 1200) 908 fifo |= FIFO_TRIGGER_1; 909 else 910 fifo |= FIFO_TRIGGER_8; 911 if (sc->sc_uarttype == COM_UART_TI16750) { 912 fifo |= FIFO_ENABLE_64BYTE; 913 lcr = bus_space_read_1(iot, ioh, com_lcr); 914 bus_space_write_1(iot, ioh, com_lcr, 915 lcr | LCR_DLAB); 916 } 917 918 /* 919 * (Re)enable and drain FIFOs. 920 * 921 * Certain SMC chips cause problems if the FIFOs are 922 * enabled while input is ready. Turn off the FIFO 923 * if necessary to clear the input. Test the input 924 * ready bit after enabling the FIFOs to handle races 925 * between enabling and fresh input. 926 * 927 * Set the FIFO threshold based on the receive speed. 928 */ 929 for (;;) { 930 bus_space_write_1(iot, ioh, com_fifo, 0); 931 delay(100); 932 (void) bus_space_read_1(iot, ioh, com_data); 933 bus_space_write_1(iot, ioh, com_fifo, fifo | 934 FIFO_RCV_RST | FIFO_XMT_RST); 935 delay(100); 936 if(!ISSET(bus_space_read_1(iot, ioh, 937 com_lsr), LSR_RXRDY)) 938 break; 939 } 940 if (sc->sc_uarttype == COM_UART_TI16750) 941 bus_space_write_1(iot, ioh, com_lcr, lcr); 942 } 943 944 /* flush any pending I/O */ 945 while (ISSET(bus_space_read_1(iot, ioh, com_lsr), LSR_RXRDY)) 946 (void) bus_space_read_1(iot, ioh, com_data); 947 /* you turn me on, baby */ 948 sc->sc_mcr = MCR_DTR | MCR_RTS; 949 if (!ISSET(sc->sc_hwflags, COM_HW_NOIEN)) 950 SET(sc->sc_mcr, MCR_IENABLE); 951 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 952 sc->sc_ier = IER_ERXRDY | IER_ERLS | IER_EMSC; 953 bus_space_write_1(iot, ioh, com_ier, sc->sc_ier); 954 955 sc->sc_msr = bus_space_read_1(iot, ioh, com_msr); 956 if (ISSET(sc->sc_swflags, COM_SW_SOFTCAR) || DEVCUA(dev) || 957 ISSET(sc->sc_msr, MSR_DCD) || ISSET(tp->t_cflag, MDMBUF)) 958 SET(tp->t_state, TS_CARR_ON); 959 else 960 CLR(tp->t_state, TS_CARR_ON); 961 } else if (ISSET(tp->t_state, TS_XCLUDE) && p->p_ucred->cr_uid != 0) 962 return EBUSY; 963 else 964 s = spltty(); 965 966 if (DEVCUA(dev)) { 967 if (ISSET(tp->t_state, TS_ISOPEN)) { 968 /* Ah, but someone already is dialed in... */ 969 splx(s); 970 return EBUSY; 971 } 972 sc->sc_cua = 1; /* We go into CUA mode */ 973 } else { 974 /* tty (not cua) device; wait for carrier if necessary */ 975 if (ISSET(flag, O_NONBLOCK)) { 976 if (sc->sc_cua) { 977 /* Opening TTY non-blocking... but the CUA is busy */ 978 splx(s); 979 return EBUSY; 980 } 981 } else { 982 while (sc->sc_cua || 983 (!ISSET(tp->t_cflag, CLOCAL) && 984 !ISSET(tp->t_state, TS_CARR_ON))) { 985 SET(tp->t_state, TS_WOPEN); 986 error = ttysleep(tp, &tp->t_rawq, TTIPRI | PCATCH, ttopen, 0); 987 /* 988 * If TS_WOPEN has been reset, that means the cua device 989 * has been closed. We don't want to fail in that case, 990 * so just go around again. 991 */ 992 if (error && ISSET(tp->t_state, TS_WOPEN)) { 993 CLR(tp->t_state, TS_WOPEN); 994 if (!sc->sc_cua && !ISSET(tp->t_state, TS_ISOPEN)) 995 compwroff(sc); 996 splx(s); 997 return error; 998 } 999 } 1000 } 1001 } 1002 splx(s); 1003 1004 return (*linesw[tp->t_line].l_open)(dev, tp); 1005 } 1006 1007 int 1008 comclose(dev, flag, mode, p) 1009 dev_t dev; 1010 int flag, mode; 1011 struct proc *p; 1012 { 1013 int unit = DEVUNIT(dev); 1014 struct com_softc *sc = com_cd.cd_devs[unit]; 1015 bus_space_tag_t iot = sc->sc_iot; 1016 bus_space_handle_t ioh = sc->sc_ioh; 1017 struct tty *tp = sc->sc_tty; 1018 int s; 1019 1020 /* XXX This is for cons.c. */ 1021 if (!ISSET(tp->t_state, TS_ISOPEN)) 1022 return 0; 1023 1024 (*linesw[tp->t_line].l_close)(tp, flag); 1025 s = spltty(); 1026 if (ISSET(tp->t_state, TS_WOPEN)) { 1027 /* tty device is waiting for carrier; drop dtr then re-raise */ 1028 CLR(sc->sc_mcr, MCR_DTR | MCR_RTS); 1029 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1030 timeout_add(&sc->sc_dtr_tmo, hz * 2); 1031 } else { 1032 /* no one else waiting; turn off the uart */ 1033 compwroff(sc); 1034 } 1035 CLR(tp->t_state, TS_BUSY | TS_FLUSH); 1036 if (--comsopen == 0) 1037 timeout_del(&compoll_to); 1038 sc->sc_cua = 0; 1039 splx(s); 1040 ttyclose(tp); 1041 1042 #ifdef notyet /* XXXX */ 1043 if (ISSET(sc->sc_hwflags, COM_HW_CONSOLE)) { 1044 ttyfree(tp); 1045 sc->sc_tty = 0; 1046 } 1047 #endif 1048 return 0; 1049 } 1050 1051 void 1052 compwroff(sc) 1053 struct com_softc *sc; 1054 { 1055 bus_space_tag_t iot = sc->sc_iot; 1056 bus_space_handle_t ioh = sc->sc_ioh; 1057 struct tty *tp = sc->sc_tty; 1058 1059 CLR(sc->sc_lcr, LCR_SBREAK); 1060 bus_space_write_1(iot, ioh, com_lcr, sc->sc_lcr); 1061 bus_space_write_1(iot, ioh, com_ier, 0); 1062 if (ISSET(tp->t_cflag, HUPCL) && 1063 !ISSET(sc->sc_swflags, COM_SW_SOFTCAR)) { 1064 /* XXX perhaps only clear DTR */ 1065 sc->sc_mcr = 0; 1066 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1067 } 1068 1069 /* 1070 * Turn FIFO off; enter sleep mode if possible. 1071 */ 1072 bus_space_write_1(iot, ioh, com_fifo, 0); 1073 delay(100); 1074 (void) bus_space_read_1(iot, ioh, com_data); 1075 delay(100); 1076 bus_space_write_1(iot, ioh, com_fifo, 1077 FIFO_RCV_RST | FIFO_XMT_RST); 1078 1079 switch (sc->sc_uarttype) { 1080 case COM_UART_ST16650: 1081 case COM_UART_ST16650V2: 1082 bus_space_write_1(iot, ioh, com_lcr, 0xbf); 1083 bus_space_write_1(iot, ioh, com_efr, EFR_ECB); 1084 bus_space_write_1(iot, ioh, com_ier, IER_SLEEP); 1085 bus_space_write_1(iot, ioh, com_lcr, 0); 1086 break; 1087 case COM_UART_TI16750: 1088 bus_space_write_1(iot, ioh, com_ier, IER_SLEEP); 1089 break; 1090 } 1091 } 1092 1093 void 1094 com_raisedtr(arg) 1095 void *arg; 1096 { 1097 struct com_softc *sc = arg; 1098 1099 SET(sc->sc_mcr, MCR_DTR | MCR_RTS); 1100 bus_space_write_1(sc->sc_iot, sc->sc_ioh, com_mcr, sc->sc_mcr); 1101 } 1102 1103 int 1104 comread(dev, uio, flag) 1105 dev_t dev; 1106 struct uio *uio; 1107 int flag; 1108 { 1109 struct com_softc *sc = com_cd.cd_devs[DEVUNIT(dev)]; 1110 struct tty *tp = sc->sc_tty; 1111 1112 return ((*linesw[tp->t_line].l_read)(tp, uio, flag)); 1113 } 1114 1115 int 1116 comwrite(dev, uio, flag) 1117 dev_t dev; 1118 struct uio *uio; 1119 int flag; 1120 { 1121 struct com_softc *sc = com_cd.cd_devs[DEVUNIT(dev)]; 1122 struct tty *tp = sc->sc_tty; 1123 1124 return ((*linesw[tp->t_line].l_write)(tp, uio, flag)); 1125 } 1126 1127 struct tty * 1128 comtty(dev) 1129 dev_t dev; 1130 { 1131 struct com_softc *sc = com_cd.cd_devs[DEVUNIT(dev)]; 1132 struct tty *tp = sc->sc_tty; 1133 1134 return (tp); 1135 } 1136 1137 static u_char 1138 tiocm_xxx2mcr(data) 1139 int data; 1140 { 1141 u_char m = 0; 1142 1143 if (ISSET(data, TIOCM_DTR)) 1144 SET(m, MCR_DTR); 1145 if (ISSET(data, TIOCM_RTS)) 1146 SET(m, MCR_RTS); 1147 return m; 1148 } 1149 1150 int 1151 comioctl(dev, cmd, data, flag, p) 1152 dev_t dev; 1153 u_long cmd; 1154 caddr_t data; 1155 int flag; 1156 struct proc *p; 1157 { 1158 int unit = DEVUNIT(dev); 1159 struct com_softc *sc = com_cd.cd_devs[unit]; 1160 struct tty *tp = sc->sc_tty; 1161 bus_space_tag_t iot = sc->sc_iot; 1162 bus_space_handle_t ioh = sc->sc_ioh; 1163 int error; 1164 1165 error = (*linesw[tp->t_line].l_ioctl)(tp, cmd, data, flag, p); 1166 if (error >= 0) 1167 return error; 1168 error = ttioctl(tp, cmd, data, flag, p); 1169 if (error >= 0) 1170 return error; 1171 1172 switch (cmd) { 1173 case TIOCSBRK: 1174 SET(sc->sc_lcr, LCR_SBREAK); 1175 bus_space_write_1(iot, ioh, com_lcr, sc->sc_lcr); 1176 break; 1177 case TIOCCBRK: 1178 CLR(sc->sc_lcr, LCR_SBREAK); 1179 bus_space_write_1(iot, ioh, com_lcr, sc->sc_lcr); 1180 break; 1181 case TIOCSDTR: 1182 SET(sc->sc_mcr, sc->sc_dtr); 1183 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1184 break; 1185 case TIOCCDTR: 1186 CLR(sc->sc_mcr, sc->sc_dtr); 1187 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1188 break; 1189 case TIOCMSET: 1190 CLR(sc->sc_mcr, MCR_DTR | MCR_RTS); 1191 case TIOCMBIS: 1192 SET(sc->sc_mcr, tiocm_xxx2mcr(*(int *)data)); 1193 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1194 break; 1195 case TIOCMBIC: 1196 CLR(sc->sc_mcr, tiocm_xxx2mcr(*(int *)data)); 1197 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1198 break; 1199 case TIOCMGET: { 1200 u_char m; 1201 int bits = 0; 1202 1203 m = sc->sc_mcr; 1204 if (ISSET(m, MCR_DTR)) 1205 SET(bits, TIOCM_DTR); 1206 if (ISSET(m, MCR_RTS)) 1207 SET(bits, TIOCM_RTS); 1208 m = sc->sc_msr; 1209 if (ISSET(m, MSR_DCD)) 1210 SET(bits, TIOCM_CD); 1211 if (ISSET(m, MSR_CTS)) 1212 SET(bits, TIOCM_CTS); 1213 if (ISSET(m, MSR_DSR)) 1214 SET(bits, TIOCM_DSR); 1215 if (ISSET(m, MSR_RI | MSR_TERI)) 1216 SET(bits, TIOCM_RI); 1217 if (bus_space_read_1(iot, ioh, com_ier)) 1218 SET(bits, TIOCM_LE); 1219 *(int *)data = bits; 1220 break; 1221 } 1222 case TIOCGFLAGS: { 1223 int driverbits, userbits = 0; 1224 1225 driverbits = sc->sc_swflags; 1226 if (ISSET(driverbits, COM_SW_SOFTCAR)) 1227 SET(userbits, TIOCFLAG_SOFTCAR); 1228 if (ISSET(driverbits, COM_SW_CLOCAL)) 1229 SET(userbits, TIOCFLAG_CLOCAL); 1230 if (ISSET(driverbits, COM_SW_CRTSCTS)) 1231 SET(userbits, TIOCFLAG_CRTSCTS); 1232 if (ISSET(driverbits, COM_SW_MDMBUF)) 1233 SET(userbits, TIOCFLAG_MDMBUF); 1234 if (ISSET(driverbits, COM_SW_PPS)) 1235 SET(userbits, TIOCFLAG_PPS); 1236 1237 *(int *)data = userbits; 1238 break; 1239 } 1240 case TIOCSFLAGS: { 1241 int userbits, driverbits = 0; 1242 1243 error = suser(p->p_ucred, &p->p_acflag); 1244 if (error != 0) 1245 return(EPERM); 1246 1247 userbits = *(int *)data; 1248 if (ISSET(userbits, TIOCFLAG_SOFTCAR) || 1249 ISSET(sc->sc_hwflags, COM_HW_CONSOLE)) 1250 SET(driverbits, COM_SW_SOFTCAR); 1251 if (ISSET(userbits, TIOCFLAG_CLOCAL)) 1252 SET(driverbits, COM_SW_CLOCAL); 1253 if (ISSET(userbits, TIOCFLAG_CRTSCTS)) 1254 SET(driverbits, COM_SW_CRTSCTS); 1255 if (ISSET(userbits, TIOCFLAG_MDMBUF)) 1256 SET(driverbits, COM_SW_MDMBUF); 1257 if (ISSET(userbits, TIOCFLAG_PPS)) 1258 SET(driverbits, COM_SW_PPS); 1259 1260 sc->sc_swflags = driverbits; 1261 break; 1262 } 1263 default: 1264 return ENOTTY; 1265 } 1266 1267 return 0; 1268 } 1269 1270 int 1271 comparam(tp, t) 1272 struct tty *tp; 1273 struct termios *t; 1274 { 1275 struct com_softc *sc = com_cd.cd_devs[DEVUNIT(tp->t_dev)]; 1276 bus_space_tag_t iot = sc->sc_iot; 1277 bus_space_handle_t ioh = sc->sc_ioh; 1278 int ospeed = comspeed(sc->sc_frequency, t->c_ospeed); 1279 u_char lcr; 1280 tcflag_t oldcflag; 1281 int s; 1282 1283 /* check requested parameters */ 1284 if (ospeed < 0 || (t->c_ispeed && t->c_ispeed != t->c_ospeed)) 1285 return EINVAL; 1286 1287 lcr = ISSET(sc->sc_lcr, LCR_SBREAK); 1288 1289 switch (ISSET(t->c_cflag, CSIZE)) { 1290 case CS5: 1291 SET(lcr, LCR_5BITS); 1292 break; 1293 case CS6: 1294 SET(lcr, LCR_6BITS); 1295 break; 1296 case CS7: 1297 SET(lcr, LCR_7BITS); 1298 break; 1299 case CS8: 1300 SET(lcr, LCR_8BITS); 1301 break; 1302 } 1303 if (ISSET(t->c_cflag, PARENB)) { 1304 SET(lcr, LCR_PENAB); 1305 if (!ISSET(t->c_cflag, PARODD)) 1306 SET(lcr, LCR_PEVEN); 1307 } 1308 if (ISSET(t->c_cflag, CSTOPB)) 1309 SET(lcr, LCR_STOPB); 1310 1311 sc->sc_lcr = lcr; 1312 1313 s = spltty(); 1314 1315 if (ospeed == 0) { 1316 CLR(sc->sc_mcr, MCR_DTR); 1317 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1318 } 1319 1320 /* 1321 * Set the FIFO threshold based on the receive speed, if we are 1322 * changing it. 1323 */ 1324 if (sc->sc_initialize || (tp->t_ispeed != t->c_ispeed)) { 1325 sc->sc_initialize = 0; 1326 1327 if (ospeed != 0) { 1328 /* 1329 * Make sure the transmit FIFO is empty before 1330 * proceeding. If we don't do this, some revisions 1331 * of the UART will hang. Interestingly enough, 1332 * even if we do this while the last character is 1333 * still being pushed out, they don't hang. This 1334 * seems good enough. 1335 */ 1336 while (ISSET(tp->t_state, TS_BUSY)) { 1337 int error; 1338 1339 ++sc->sc_halt; 1340 error = ttysleep(tp, &tp->t_outq, 1341 TTOPRI | PCATCH, "comprm", 0); 1342 --sc->sc_halt; 1343 if (error) { 1344 splx(s); 1345 comstart(tp); 1346 return (error); 1347 } 1348 } 1349 1350 bus_space_write_1(iot, ioh, com_lcr, lcr | LCR_DLAB); 1351 bus_space_write_1(iot, ioh, com_dlbl, ospeed); 1352 bus_space_write_1(iot, ioh, com_dlbh, ospeed >> 8); 1353 bus_space_write_1(iot, ioh, com_lcr, lcr); 1354 SET(sc->sc_mcr, MCR_DTR); 1355 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1356 } else 1357 bus_space_write_1(iot, ioh, com_lcr, lcr); 1358 1359 if (!ISSET(sc->sc_hwflags, COM_HW_HAYESP) && 1360 ISSET(sc->sc_hwflags, COM_HW_FIFO)) { 1361 if (sc->sc_uarttype == COM_UART_TI16750) { 1362 bus_space_write_1(iot, ioh, com_lcr, 1363 lcr | LCR_DLAB); 1364 bus_space_write_1(iot, ioh, com_fifo, 1365 FIFO_ENABLE | FIFO_ENABLE_64BYTE | 1366 (t->c_ispeed <= 1200 ? FIFO_TRIGGER_1 : FIFO_TRIGGER_8)); 1367 bus_space_write_1(iot, ioh, com_lcr, lcr); 1368 } else 1369 bus_space_write_1(iot, ioh, com_fifo, 1370 FIFO_ENABLE | 1371 (t->c_ispeed <= 1200 ? FIFO_TRIGGER_1 : FIFO_TRIGGER_8)); 1372 } 1373 } else 1374 bus_space_write_1(iot, ioh, com_lcr, lcr); 1375 1376 /* When not using CRTSCTS, RTS follows DTR. */ 1377 if (!ISSET(t->c_cflag, CRTSCTS)) { 1378 if (ISSET(sc->sc_mcr, MCR_DTR)) { 1379 if (!ISSET(sc->sc_mcr, MCR_RTS)) { 1380 SET(sc->sc_mcr, MCR_RTS); 1381 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1382 } 1383 } else { 1384 if (ISSET(sc->sc_mcr, MCR_RTS)) { 1385 CLR(sc->sc_mcr, MCR_RTS); 1386 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1387 } 1388 } 1389 sc->sc_dtr = MCR_DTR | MCR_RTS; 1390 } else 1391 sc->sc_dtr = MCR_DTR; 1392 1393 /* and copy to tty */ 1394 tp->t_ispeed = t->c_ispeed; 1395 tp->t_ospeed = t->c_ospeed; 1396 oldcflag = tp->t_cflag; 1397 tp->t_cflag = t->c_cflag; 1398 1399 /* 1400 * If DCD is off and MDMBUF is changed, ask the tty layer if we should 1401 * stop the device. 1402 */ 1403 if (!ISSET(sc->sc_msr, MSR_DCD) && 1404 !ISSET(sc->sc_swflags, COM_SW_SOFTCAR) && 1405 ISSET(oldcflag, MDMBUF) != ISSET(tp->t_cflag, MDMBUF) && 1406 (*linesw[tp->t_line].l_modem)(tp, 0) == 0) { 1407 CLR(sc->sc_mcr, sc->sc_dtr); 1408 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1409 } 1410 1411 /* Just to be sure... */ 1412 splx(s); 1413 comstart(tp); 1414 return 0; 1415 } 1416 1417 void 1418 comstart(tp) 1419 struct tty *tp; 1420 { 1421 struct com_softc *sc = com_cd.cd_devs[DEVUNIT(tp->t_dev)]; 1422 bus_space_tag_t iot = sc->sc_iot; 1423 bus_space_handle_t ioh = sc->sc_ioh; 1424 int s; 1425 1426 s = spltty(); 1427 if (ISSET(tp->t_state, TS_BUSY)) 1428 goto out; 1429 if (ISSET(tp->t_state, TS_TIMEOUT | TS_TTSTOP) || sc->sc_halt > 0) 1430 goto stopped; 1431 if (ISSET(tp->t_cflag, CRTSCTS) && !ISSET(sc->sc_msr, MSR_CTS)) 1432 goto stopped; 1433 if (tp->t_outq.c_cc <= tp->t_lowat) { 1434 if (ISSET(tp->t_state, TS_ASLEEP)) { 1435 CLR(tp->t_state, TS_ASLEEP); 1436 wakeup(&tp->t_outq); 1437 } 1438 if (tp->t_outq.c_cc == 0) 1439 goto stopped; 1440 selwakeup(&tp->t_wsel); 1441 } 1442 SET(tp->t_state, TS_BUSY); 1443 1444 if (!ISSET(sc->sc_ier, IER_ETXRDY)) { 1445 SET(sc->sc_ier, IER_ETXRDY); 1446 bus_space_write_1(iot, ioh, com_ier, sc->sc_ier); 1447 } 1448 if (ISSET(sc->sc_hwflags, COM_HW_FIFO)) { 1449 #ifdef COM_HAYESP 1450 u_char buffer[1024]; /* XXX: largest fifo */ 1451 #else 1452 u_char buffer[64]; /* XXX: largest fifo */ 1453 #endif 1454 u_char *cp = buffer; 1455 int n = q_to_b(&tp->t_outq, cp, sc->sc_fifolen); 1456 do { 1457 bus_space_write_1(iot, ioh, com_data, *cp++); 1458 } while (--n); 1459 } else 1460 bus_space_write_1(iot, ioh, com_data, getc(&tp->t_outq)); 1461 out: 1462 splx(s); 1463 return; 1464 stopped: 1465 if (ISSET(sc->sc_ier, IER_ETXRDY)) { 1466 CLR(sc->sc_ier, IER_ETXRDY); 1467 bus_space_write_1(iot, ioh, com_ier, sc->sc_ier); 1468 } 1469 splx(s); 1470 } 1471 1472 /* 1473 * Stop output on a line. 1474 */ 1475 int 1476 comstop(tp, flag) 1477 struct tty *tp; 1478 int flag; 1479 { 1480 int s; 1481 1482 s = spltty(); 1483 if (ISSET(tp->t_state, TS_BUSY)) 1484 if (!ISSET(tp->t_state, TS_TTSTOP)) 1485 SET(tp->t_state, TS_FLUSH); 1486 splx(s); 1487 return 0; 1488 } 1489 1490 void 1491 comdiag(arg) 1492 void *arg; 1493 { 1494 struct com_softc *sc = arg; 1495 int overflows, floods; 1496 int s; 1497 1498 s = spltty(); 1499 sc->sc_errors = 0; 1500 overflows = sc->sc_overflows; 1501 sc->sc_overflows = 0; 1502 floods = sc->sc_floods; 1503 sc->sc_floods = 0; 1504 splx(s); 1505 log(LOG_WARNING, "%s: %d silo overflow%s, %d ibuf overflow%s\n", 1506 sc->sc_dev.dv_xname, 1507 overflows, overflows == 1 ? "" : "s", 1508 floods, floods == 1 ? "" : "s"); 1509 } 1510 1511 void 1512 compoll(arg) 1513 void *arg; 1514 { 1515 int unit; 1516 struct com_softc *sc; 1517 struct tty *tp; 1518 register u_char *ibufp; 1519 u_char *ibufend; 1520 register int c; 1521 int s; 1522 static int lsrmap[8] = { 1523 0, TTY_PE, 1524 TTY_FE, TTY_PE|TTY_FE, 1525 TTY_FE, TTY_PE|TTY_FE, 1526 TTY_FE, TTY_PE|TTY_FE 1527 }; 1528 1529 s = spltty(); 1530 if (comevents == 0) { 1531 splx(s); 1532 goto out; 1533 } 1534 comevents = 0; 1535 splx(s); 1536 1537 for (unit = 0; unit < com_cd.cd_ndevs; unit++) { 1538 sc = com_cd.cd_devs[unit]; 1539 if (sc == 0 || sc->sc_ibufp == sc->sc_ibuf) 1540 continue; 1541 1542 tp = sc->sc_tty; 1543 1544 s = spltty(); 1545 1546 ibufp = sc->sc_ibuf; 1547 ibufend = sc->sc_ibufp; 1548 1549 if (ibufp == ibufend) { 1550 splx(s); 1551 continue; 1552 } 1553 1554 sc->sc_ibufp = sc->sc_ibuf = (ibufp == sc->sc_ibufs[0]) ? 1555 sc->sc_ibufs[1] : sc->sc_ibufs[0]; 1556 sc->sc_ibufhigh = sc->sc_ibuf + COM_IHIGHWATER; 1557 sc->sc_ibufend = sc->sc_ibuf + COM_IBUFSIZE; 1558 1559 if (tp == 0 || !ISSET(tp->t_state, TS_ISOPEN)) { 1560 splx(s); 1561 continue; 1562 } 1563 1564 if (ISSET(tp->t_cflag, CRTSCTS) && 1565 !ISSET(sc->sc_mcr, MCR_RTS)) { 1566 /* XXX */ 1567 SET(sc->sc_mcr, MCR_RTS); 1568 bus_space_write_1(sc->sc_iot, sc->sc_ioh, com_mcr, 1569 sc->sc_mcr); 1570 } 1571 1572 splx(s); 1573 1574 while (ibufp < ibufend) { 1575 c = *ibufp++; 1576 if (ISSET(*ibufp, LSR_OE)) { 1577 sc->sc_overflows++; 1578 if (sc->sc_errors++ == 0) 1579 timeout_add(&sc->sc_diag_tmo, 60 * hz); 1580 } 1581 /* This is ugly, but fast. */ 1582 c |= lsrmap[(*ibufp++ & (LSR_BI|LSR_FE|LSR_PE)) >> 2]; 1583 (*linesw[tp->t_line].l_rint)(c, tp); 1584 } 1585 } 1586 1587 out: 1588 timeout_add(&compoll_to, 1); 1589 } 1590 1591 #ifdef KGDB 1592 1593 /* 1594 * If a line break is set, or data matches one of the characters 1595 * gdb uses to signal a connection, then start up kgdb. Just gobble 1596 * any other data. Done in a stand alone function because comintr 1597 * does tty stuff and we don't have one. 1598 */ 1599 1600 int 1601 kgdbintr(arg) 1602 void *arg; 1603 { 1604 struct com_softc *sc = arg; 1605 bus_space_tag_t iot = sc->sc_iot; 1606 bus_space_handle_t ioh = sc->sc_ioh; 1607 u_char lsr, data, msr, delta; 1608 1609 if (!ISSET(sc->sc_hwflags, COM_HW_KGDB)) 1610 return(0); 1611 1612 for (;;) { 1613 lsr = bus_space_read_1(iot, ioh, com_lsr); 1614 if (ISSET(lsr, LSR_RXRDY)) { 1615 do { 1616 data = bus_space_read_1(iot, ioh, com_data); 1617 if (data == 3 || data == '$' || data == '+' || 1618 ISSET(lsr, LSR_BI)) { 1619 kgdb_connect(1); 1620 data = 0; 1621 } 1622 lsr = bus_space_read_1(iot, ioh, com_lsr); 1623 } while (ISSET(lsr, LSR_RXRDY)); 1624 1625 } 1626 if (ISSET(lsr, LSR_BI|LSR_FE|LSR_PE|LSR_OE)) 1627 printf("weird lsr %02x\n", lsr); 1628 1629 msr = bus_space_read_1(iot, ioh, com_msr); 1630 1631 if (msr != sc->sc_msr) { 1632 delta = msr ^ sc->sc_msr; 1633 sc->sc_msr = msr; 1634 if (ISSET(delta, MSR_DCD)) { 1635 if (!ISSET(sc->sc_swflags, COM_SW_SOFTCAR)) { 1636 CLR(sc->sc_mcr, sc->sc_dtr); 1637 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1638 } 1639 } 1640 } 1641 if (ISSET(bus_space_read_1(iot, ioh, com_iir), IIR_NOPEND)) 1642 return (1); 1643 } 1644 } 1645 #endif /* KGDB */ 1646 1647 int 1648 comintr(arg) 1649 void *arg; 1650 { 1651 struct com_softc *sc = arg; 1652 bus_space_tag_t iot = sc->sc_iot; 1653 bus_space_handle_t ioh = sc->sc_ioh; 1654 struct tty *tp; 1655 u_char lsr, data, msr, delta; 1656 #ifdef PPS_SYNC 1657 struct timeval tv; 1658 long usec; 1659 #endif /* PPS_SYNC */ 1660 #ifdef COM_DEBUG 1661 int n; 1662 struct { 1663 u_char iir, lsr, msr; 1664 } iter[32]; 1665 #endif 1666 1667 if (!sc->sc_tty) 1668 return (0); /* can't do squat. */ 1669 1670 #ifdef COM_DEBUG 1671 n = 0; 1672 if (ISSET(iter[n].iir = bus_space_read_1(iot, ioh, com_iir), IIR_NOPEND)) 1673 return (0); 1674 #else 1675 if (ISSET(bus_space_read_1(iot, ioh, com_iir), IIR_NOPEND)) 1676 return (0); 1677 #endif 1678 1679 tp = sc->sc_tty; 1680 1681 for (;;) { 1682 #ifdef COM_DEBUG 1683 iter[n].lsr = 1684 #endif 1685 lsr = bus_space_read_1(iot, ioh, com_lsr); 1686 1687 if (ISSET(lsr, LSR_RXRDY)) { 1688 register u_char *p = sc->sc_ibufp; 1689 1690 comevents = 1; 1691 do { 1692 data = bus_space_read_1(iot, ioh, com_data); 1693 if (ISSET(lsr, LSR_BI)) { 1694 #ifdef notdef 1695 printf("break %02x %02x %02x %02x\n", 1696 sc->sc_msr, sc->sc_mcr, sc->sc_lcr, 1697 sc->sc_dtr); 1698 #endif 1699 #ifdef DDB 1700 if (ISSET(sc->sc_hwflags, 1701 COM_HW_CONSOLE)) { 1702 if (db_console) 1703 Debugger(); 1704 goto next; 1705 } 1706 #endif 1707 data = 0; 1708 } 1709 if (p >= sc->sc_ibufend) { 1710 sc->sc_floods++; 1711 if (sc->sc_errors++ == 0) 1712 timeout_add(&sc->sc_diag_tmo, 60 * hz); 1713 } else { 1714 *p++ = data; 1715 *p++ = lsr; 1716 if (p == sc->sc_ibufhigh && 1717 ISSET(tp->t_cflag, CRTSCTS)) { 1718 /* XXX */ 1719 CLR(sc->sc_mcr, MCR_RTS); 1720 bus_space_write_1(iot, ioh, com_mcr, 1721 sc->sc_mcr); 1722 } 1723 } 1724 #ifdef DDB 1725 next: 1726 #endif 1727 #ifdef COM_DEBUG 1728 if (++n >= 32) 1729 goto ohfudge; 1730 iter[n].lsr = 1731 #endif 1732 lsr = bus_space_read_1(iot, ioh, com_lsr); 1733 } while (ISSET(lsr, LSR_RXRDY)); 1734 1735 sc->sc_ibufp = p; 1736 } 1737 #ifdef COM_DEBUG 1738 else if (ISSET(lsr, LSR_BI|LSR_FE|LSR_PE|LSR_OE)) 1739 printf("weird lsr %02x\n", lsr); 1740 #endif 1741 1742 #ifdef COM_DEBUG 1743 iter[n].msr = 1744 #endif 1745 msr = bus_space_read_1(iot, ioh, com_msr); 1746 1747 if (msr != sc->sc_msr) { 1748 delta = msr ^ sc->sc_msr; 1749 sc->sc_msr = msr; 1750 if (ISSET(delta, MSR_DCD)) { 1751 #ifdef PPS_SYNC 1752 if (ISSET(sc->sc_swflags, COM_SW_PPS)) { 1753 if (ISSET(msr, MSR_DCD)) { 1754 usec = time.tv_usec; 1755 microtime(&tv); 1756 usec = tv.tv_usec - usec; 1757 if (usec < 0) 1758 usec += 1000000; 1759 hardpps(&tv, usec); 1760 } 1761 } 1762 else 1763 #endif /* PPS_SYNC */ 1764 if (!ISSET(sc->sc_swflags, COM_SW_SOFTCAR) && 1765 (*linesw[tp->t_line].l_modem)(tp, ISSET(msr, MSR_DCD)) == 0) { 1766 CLR(sc->sc_mcr, sc->sc_dtr); 1767 bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr); 1768 } 1769 } 1770 if (ISSET(delta & msr, MSR_CTS) && 1771 ISSET(tp->t_cflag, CRTSCTS)) { 1772 /* the line is up and we want to do rts/cts flow control */ 1773 (*linesw[tp->t_line].l_start)(tp); 1774 } 1775 } 1776 1777 if (ISSET(lsr, LSR_TXRDY) && ISSET(tp->t_state, TS_BUSY)) { 1778 CLR(tp->t_state, TS_BUSY | TS_FLUSH); 1779 if (sc->sc_halt > 0) 1780 wakeup(&tp->t_outq); 1781 (*linesw[tp->t_line].l_start)(tp); 1782 } 1783 1784 #ifdef COM_DEBUG 1785 if (++n >= 32) 1786 goto ohfudge; 1787 if (ISSET(iter[n].iir = bus_space_read_1(iot, ioh, com_iir), IIR_NOPEND)) 1788 return (1); 1789 #else 1790 if (ISSET(bus_space_read_1(iot, ioh, com_iir), IIR_NOPEND)) 1791 return (1); 1792 #endif 1793 } 1794 #ifdef COM_DEBUG 1795 ohfudge: 1796 printf("comintr: too many iterations"); 1797 for (n = 0; n < 32; n++) { 1798 if ((n % 4) == 0) 1799 printf("\ncomintr: iter[%02d]", n); 1800 printf(" %02x %02x %02x", iter[n].iir, iter[n].lsr, iter[n].msr); 1801 } 1802 printf("\n"); 1803 printf("comintr: msr %02x mcr %02x lcr %02x ier %02x\n", 1804 sc->sc_msr, sc->sc_mcr, sc->sc_lcr, sc->sc_ier); 1805 printf("comintr: state %08x cc %d\n", sc->sc_tty->t_state, 1806 sc->sc_tty->t_outq.c_cc); 1807 #endif 1808 } 1809 1810 /* 1811 * Following are all routines needed for COM to act as console 1812 */ 1813 1814 #if defined(arc) || defined(hppa) 1815 #undef CONADDR 1816 extern int CONADDR; 1817 #endif 1818 1819 void 1820 comcnprobe(cp) 1821 struct consdev *cp; 1822 { 1823 /* XXX NEEDS TO BE FIXED XXX */ 1824 #if defined(arc) 1825 bus_space_tag_t iot = &arc_bus_io; 1826 #elif defined(powerpc) 1827 bus_space_tag_t iot = &ppc_isa_io; 1828 #elif defined(hppa) 1829 bus_space_tag_t iot = &hppa_bustag; 1830 #else 1831 bus_space_tag_t iot = 0; 1832 #endif 1833 bus_space_handle_t ioh; 1834 int found; 1835 1836 if(CONADDR == 0) { 1837 cp->cn_pri = CN_DEAD; 1838 return; 1839 } 1840 1841 comconsiot = iot; 1842 if (bus_space_map(iot, CONADDR, COM_NPORTS, 0, &ioh)) { 1843 cp->cn_pri = CN_DEAD; 1844 return; 1845 } 1846 found = comprobe1(iot, ioh); 1847 bus_space_unmap(iot, ioh, COM_NPORTS); 1848 if (!found) { 1849 cp->cn_pri = CN_DEAD; 1850 return; 1851 } 1852 1853 /* locate the major number */ 1854 for (commajor = 0; commajor < nchrdev; commajor++) 1855 if (cdevsw[commajor].d_open == comopen) 1856 break; 1857 1858 /* initialize required fields */ 1859 cp->cn_dev = makedev(commajor, CONUNIT); 1860 #ifdef COMCONSOLE 1861 cp->cn_pri = CN_REMOTE; /* Force a serial port console */ 1862 #else 1863 cp->cn_pri = CN_NORMAL; 1864 #endif 1865 } 1866 1867 /* 1868 * The following functions are polled getc and putc routines, shared 1869 * by the console and kgdb glue. 1870 */ 1871 1872 int 1873 com_common_getc(iot, ioh) 1874 bus_space_tag_t iot; 1875 bus_space_handle_t ioh; 1876 { 1877 int s = splhigh(); 1878 u_char stat, c; 1879 1880 /* block until a character becomes available */ 1881 while (!ISSET(stat = bus_space_read_1(iot, ioh, com_lsr), LSR_RXRDY)) 1882 continue; 1883 1884 c = bus_space_read_1(iot, ioh, com_data); 1885 /* clear any interrupts generated by this transmission */ 1886 stat = bus_space_read_1(iot, ioh, com_iir); 1887 splx(s); 1888 return (c); 1889 } 1890 1891 void 1892 com_common_putc(iot, ioh, c) 1893 bus_space_tag_t iot; 1894 bus_space_handle_t ioh; 1895 int c; 1896 { 1897 int s = splhigh(); 1898 int timo; 1899 1900 /* wait for any pending transmission to finish */ 1901 timo = 150000; 1902 while (!ISSET(bus_space_read_1(iot, ioh, com_lsr), LSR_TXRDY) && --timo) 1903 continue; 1904 1905 bus_space_write_1(iot, ioh, com_data, c); 1906 1907 /* wait for this transmission to complete */ 1908 timo = 1500000; 1909 while (!ISSET(bus_space_read_1(iot, ioh, com_lsr), LSR_TXRDY) && --timo) 1910 continue; 1911 1912 splx(s); 1913 } 1914 1915 /* 1916 * Following are all routines needed for COM to act as console 1917 */ 1918 1919 void 1920 comcninit(cp) 1921 struct consdev *cp; 1922 { 1923 1924 comconsaddr = CONADDR; 1925 1926 if (bus_space_map(comconsiot, comconsaddr, COM_NPORTS, 0, &comconsioh)) 1927 panic("comcninit: mapping failed"); 1928 1929 cominit(comconsiot, comconsioh, comdefaultrate); 1930 comconsinit = 0; 1931 } 1932 1933 void 1934 cominit(iot, ioh, rate) 1935 bus_space_tag_t iot; 1936 bus_space_handle_t ioh; 1937 int rate; 1938 { 1939 int s = splhigh(); 1940 u_char stat; 1941 1942 bus_space_write_1(iot, ioh, com_lcr, LCR_DLAB); 1943 rate = comspeed(COM_FREQ, rate); /* XXX not comdefaultrate? */ 1944 bus_space_write_1(iot, ioh, com_dlbl, rate); 1945 bus_space_write_1(iot, ioh, com_dlbh, rate >> 8); 1946 bus_space_write_1(iot, ioh, com_lcr, LCR_8BITS); 1947 bus_space_write_1(iot, ioh, com_mcr, MCR_DTR | MCR_RTS); 1948 bus_space_write_1(iot, ioh, com_ier, IER_ERXRDY | IER_ETXRDY); 1949 bus_space_write_1(iot, ioh, com_fifo, 1950 FIFO_ENABLE | FIFO_RCV_RST | FIFO_XMT_RST | FIFO_TRIGGER_1); 1951 stat = bus_space_read_1(iot, ioh, com_iir); 1952 splx(s); 1953 } 1954 1955 int 1956 comcnattach(iot, iobase, rate, frequency, cflag) 1957 bus_space_tag_t iot; 1958 int iobase; 1959 int rate, frequency; 1960 tcflag_t cflag; 1961 { 1962 static struct consdev comcons = { 1963 NULL, NULL, comcngetc, comcnputc, comcnpollc, NULL, 1964 NODEV, CN_NORMAL 1965 }; 1966 1967 if (bus_space_map(iot, iobase, COM_NPORTS, 0, &comconsioh)) 1968 return ENOMEM; 1969 1970 cominit(iot, comconsioh, rate); 1971 1972 cn_tab = &comcons; 1973 1974 comconsiot = iot; 1975 comconsaddr = iobase; 1976 comconscflag = cflag; 1977 1978 return (0); 1979 } 1980 1981 int 1982 comcngetc(dev) 1983 dev_t dev; 1984 { 1985 return (com_common_getc(comconsiot, comconsioh)); 1986 } 1987 1988 /* 1989 * Console kernel output character routine. 1990 */ 1991 void 1992 comcnputc(dev, c) 1993 dev_t dev; 1994 int c; 1995 { 1996 #if 0 1997 /* XXX not needed? */ 1998 bus_space_tag_t iot = comconsiot; 1999 bus_space_handle_t ioh = comconsioh; 2000 2001 if (comconsinit == 0) { 2002 cominit(iot, ioh, comdefaultrate); 2003 comconsinit = 1; 2004 } 2005 #endif 2006 com_common_putc(comconsiot, comconsioh, c); 2007 2008 } 2009 2010 void 2011 comcnpollc(dev, on) 2012 dev_t dev; 2013 int on; 2014 { 2015 2016 } 2017 2018 #ifdef KGDB 2019 int 2020 com_kgdb_attach(iot, iobase, rate, frequency, cflag) 2021 bus_space_tag_t iot; 2022 int iobase; 2023 int rate, frequency; 2024 tcflag_t cflag; 2025 { 2026 if (iot == comconsiot && iobase == comconsaddr) { 2027 return (EBUSY); /* cannot share with console */ 2028 } 2029 2030 com_kgdb_iot = iot; 2031 com_kgdb_addr = iobase; 2032 2033 if (bus_space_map(com_kgdb_iot, com_kgdb_addr, COM_NPORTS, 0, 2034 &com_kgdb_ioh)) 2035 panic("com_kgdb_attach: mapping failed"); 2036 2037 /* XXX We currently don't respect KGDBMODE? */ 2038 cominit(com_kgdb_iot, com_kgdb_ioh, rate); 2039 2040 kgdb_attach(com_kgdb_getc, com_kgdb_putc, NULL); 2041 kgdb_dev = 123; /* unneeded, only to satisfy some tests */ 2042 2043 return (0); 2044 } 2045 2046 /* ARGSUSED */ 2047 int 2048 com_kgdb_getc(arg) 2049 void *arg; 2050 { 2051 2052 return (com_common_getc(com_kgdb_iot, com_kgdb_ioh)); 2053 } 2054 2055 /* ARGSUSED */ 2056 void 2057 com_kgdb_putc(arg, c) 2058 void *arg; 2059 int c; 2060 { 2061 2062 return (com_common_putc(com_kgdb_iot, com_kgdb_ioh, c)); 2063 } 2064 #endif /* KGDB */ 2065