1 /* $NetBSD: zs.c,v 1.37 2007/12/03 15:33:59 ad Exp $ */ 2 3 /*- 4 * Copyright (c) 1996 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Gordon W. Ross. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 3. All advertising materials mentioning features or use of this software 19 * must display the following acknowledgement: 20 * This product includes software developed by the NetBSD 21 * Foundation, Inc. and its contributors. 22 * 4. Neither the name of The NetBSD Foundation nor the names of its 23 * contributors may be used to endorse or promote products derived 24 * from this software without specific prior written permission. 25 * 26 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 27 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 28 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 29 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 30 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 36 * POSSIBILITY OF SUCH DAMAGE. 37 */ 38 39 /* 40 * Zilog Z8530 Dual UART driver (machine-dependent part) 41 * 42 * Runs two serial lines per chip using slave drivers. 43 * Plain tty/async lines use the zs_async slave. 44 * 45 * Modified for NetBSD/mvme68k by Jason R. Thorpe <thorpej@NetBSD.org> 46 */ 47 48 #include <sys/cdefs.h> 49 __KERNEL_RCSID(0, "$NetBSD: zs.c,v 1.37 2007/12/03 15:33:59 ad Exp $"); 50 51 #include <sys/param.h> 52 #include <sys/systm.h> 53 #include <sys/conf.h> 54 #include <sys/device.h> 55 #include <sys/file.h> 56 #include <sys/ioctl.h> 57 #include <sys/kernel.h> 58 #include <sys/proc.h> 59 #include <sys/tty.h> 60 #include <sys/time.h> 61 #include <sys/syslog.h> 62 #include <sys/cpu.h> 63 #include <sys/bus.h> 64 #include <sys/intr.h> 65 66 #include <dev/cons.h> 67 #include <dev/ic/z8530reg.h> 68 #include <machine/z8530var.h> 69 70 #include <mvme68k/dev/zsvar.h> 71 72 /* 73 * Some warts needed by z8530tty.c - 74 * The default parity REALLY needs to be the same as the PROM uses, 75 * or you can not see messages done with printf during boot-up... 76 */ 77 int zs_def_cflag = (CREAD | CS8 | HUPCL); 78 79 /* Flags from zscnprobe() */ 80 static int zs_hwflags[NZSC][2]; 81 82 /* Default speed for each channel */ 83 static int zs_defspeed[NZSC][2] = { 84 { 9600, /* port 1 */ 85 9600 }, /* port 2 */ 86 { 9600, /* port 3 */ 87 9600 }, /* port 4 */ 88 }; 89 90 static struct zs_chanstate zs_conschan_store; 91 static struct zs_chanstate *zs_conschan; 92 93 u_char zs_init_reg[16] = { 94 0, /* 0: CMD (reset, etc.) */ 95 0, /* 1: No interrupts yet. */ 96 0x18 + ZSHARD_PRI, /* IVECT */ 97 ZSWR3_RX_8 | ZSWR3_RX_ENABLE, 98 ZSWR4_CLK_X16 | ZSWR4_ONESB | ZSWR4_EVENP, 99 ZSWR5_TX_8 | ZSWR5_TX_ENABLE, 100 0, /* 6: TXSYNC/SYNCLO */ 101 0, /* 7: RXSYNC/SYNCHI */ 102 0, /* 8: alias for data port */ 103 ZSWR9_MASTER_IE, 104 0, /*10: Misc. TX/RX control bits */ 105 ZSWR11_TXCLK_BAUD | ZSWR11_RXCLK_BAUD, 106 0, /*12: BAUDLO (default=9600) */ 107 0, /*13: BAUDHI (default=9600) */ 108 ZSWR14_BAUD_ENA | ZSWR14_BAUD_FROM_PCLK, 109 ZSWR15_BREAK_IE, 110 }; 111 112 113 /**************************************************************** 114 * Autoconfig 115 ****************************************************************/ 116 117 /* Definition of the driver for autoconfig. */ 118 static int zsc_print __P((void *, const char *name)); 119 int zs_getc __P((void *)); 120 void zs_putc __P((void *, int)); 121 122 #if 0 123 static int zs_get_speed __P((struct zs_chanstate *)); 124 #endif 125 126 extern struct cfdriver zsc_cd; 127 128 cons_decl(zsc_pcc); 129 130 131 /* 132 * Configure children of an SCC. 133 */ 134 void 135 zs_config(zsc, zs, vector, pclk) 136 struct zsc_softc *zsc; 137 struct zsdevice *zs; 138 int vector, pclk; 139 { 140 struct zsc_attach_args zsc_args; 141 volatile struct zschan *zc; 142 struct zs_chanstate *cs; 143 int zsc_unit, channel, s; 144 145 zsc_unit = device_unit(&zsc->zsc_dev); 146 printf(": Zilog 8530 SCC at vector 0x%x\n", vector); 147 148 /* 149 * Initialize software state for each channel. 150 */ 151 for (channel = 0; channel < 2; channel++) { 152 zsc_args.channel = channel; 153 zsc_args.hwflags = zs_hwflags[zsc_unit][channel]; 154 cs = &zsc->zsc_cs_store[channel]; 155 zsc->zsc_cs[channel] = cs; 156 zs_lock_init(cs); 157 158 /* 159 * If we're the console, copy the channel state, and 160 * adjust the console channel pointer. 161 */ 162 if (zsc_args.hwflags & ZS_HWFLAG_CONSOLE) { 163 memcpy(cs, zs_conschan, sizeof(struct zs_chanstate)); 164 zs_conschan = cs; 165 } else { 166 zc = (channel == 0) ? &zs->zs_chan_a : &zs->zs_chan_b; 167 cs->cs_reg_csr = zc->zc_csr; 168 cs->cs_reg_data = zc->zc_data; 169 memcpy(cs->cs_creg, zs_init_reg, 16); 170 memcpy(cs->cs_preg, zs_init_reg, 16); 171 cs->cs_defspeed = zs_defspeed[zsc_unit][channel]; 172 } 173 174 cs->cs_brg_clk = pclk / 16; 175 cs->cs_creg[2] = cs->cs_preg[2] = vector; 176 zs_set_speed(cs, cs->cs_defspeed); 177 cs->cs_creg[12] = cs->cs_preg[12]; 178 cs->cs_creg[13] = cs->cs_preg[13]; 179 cs->cs_defcflag = zs_def_cflag; 180 181 /* Make these correspond to cs_defcflag (-crtscts) */ 182 cs->cs_rr0_dcd = ZSRR0_DCD; 183 cs->cs_rr0_cts = 0; 184 cs->cs_wr5_dtr = ZSWR5_DTR | ZSWR5_RTS; 185 cs->cs_wr5_rts = 0; 186 187 cs->cs_channel = channel; 188 cs->cs_private = NULL; 189 cs->cs_ops = &zsops_null; 190 191 /* 192 * Clear the master interrupt enable. 193 * The INTENA is common to both channels, 194 * so just do it on the A channel. 195 * Write the interrupt vector while we're at it. 196 */ 197 if (channel == 0) { 198 zs_write_reg(cs, 9, 0); 199 zs_write_reg(cs, 2, vector); 200 } 201 202 /* 203 * Look for a child driver for this channel. 204 * The child attach will setup the hardware. 205 */ 206 if (!config_found(&zsc->zsc_dev, (void *)&zsc_args, zsc_print)) { 207 /* No sub-driver. Just reset it. */ 208 u_char reset = (channel == 0) ? 209 ZSWR9_A_RESET : ZSWR9_B_RESET; 210 s = splzs(); 211 zs_write_reg(cs, 9, reset); 212 splx(s); 213 } 214 } 215 216 /* 217 * Allocate a software interrupt cookie. 218 */ 219 zsc->zsc_softintr_cookie = softint_establish(SOFTINT_SERIAL, 220 (void (*)(void *)) zsc_intr_soft, zsc); 221 #ifdef DEBUG 222 assert(zsc->zsc_softintr_cookie); 223 #endif 224 } 225 226 static int 227 zsc_print(aux, name) 228 void *aux; 229 const char *name; 230 { 231 struct zsc_attach_args *args = aux; 232 233 if (name != NULL) 234 aprint_normal("%s: ", name); 235 236 if (args->channel != -1) 237 aprint_normal(" channel %d", args->channel); 238 239 return UNCONF; 240 } 241 242 #if defined(MVME162) || defined(MVME172) 243 /* 244 * Our ZS chips each have their own interrupt vector. 245 */ 246 int 247 zshard_unshared(arg) 248 void *arg; 249 { 250 struct zsc_softc *zsc = arg; 251 int rval; 252 253 rval = zsc_intr_hard(zsc); 254 255 if (rval) { 256 if ((zsc->zsc_cs[0]->cs_softreq) || 257 (zsc->zsc_cs[1]->cs_softreq)) 258 softint_schedule(zsc->zsc_softintr_cookie); 259 zsc->zsc_evcnt.ev_count++; 260 } 261 262 return (rval); 263 } 264 #endif 265 266 #ifdef MVME147 267 /* 268 * Our ZS chips all share a common, PCC-vectored interrupt, 269 * so we have to look at all of them on each interrupt. 270 */ 271 int 272 zshard_shared(arg) 273 void *arg; 274 { 275 struct zsc_softc *zsc; 276 int unit, rval; 277 278 rval = 0; 279 for (unit = 0; unit < zsc_cd.cd_ndevs; unit++) { 280 zsc = zsc_cd.cd_devs[unit]; 281 if (zsc != NULL && zsc_intr_hard(zsc)) { 282 if ((zsc->zsc_cs[0]->cs_softreq) || 283 (zsc->zsc_cs[1]->cs_softreq)) 284 softint_schedule(zsc->zsc_softintr_cookie); 285 zsc->zsc_evcnt.ev_count++; 286 rval++; 287 } 288 } 289 return (rval); 290 } 291 #endif 292 293 294 #if 0 295 /* 296 * Compute the current baud rate given a ZSCC channel. 297 */ 298 static int 299 zs_get_speed(cs) 300 struct zs_chanstate *cs; 301 { 302 int tconst; 303 304 tconst = zs_read_reg(cs, 12); 305 tconst |= zs_read_reg(cs, 13) << 8; 306 return (TCONST_TO_BPS(cs->cs_brg_clk, tconst)); 307 } 308 #endif 309 310 /* 311 * MD functions for setting the baud rate and control modes. 312 */ 313 int 314 zs_set_speed(cs, bps) 315 struct zs_chanstate *cs; 316 int bps; /* bits per second */ 317 { 318 int tconst, real_bps; 319 320 if (bps == 0) 321 return (0); 322 323 #ifdef DIAGNOSTIC 324 if (cs->cs_brg_clk == 0) 325 panic("zs_set_speed"); 326 #endif 327 328 tconst = BPS_TO_TCONST(cs->cs_brg_clk, bps); 329 if (tconst < 0) 330 return (EINVAL); 331 332 /* Convert back to make sure we can do it. */ 333 real_bps = TCONST_TO_BPS(cs->cs_brg_clk, tconst); 334 335 /* Allow 2% tolerance WRT the required bps */ 336 if (((abs(real_bps - bps) * 1000) / bps) > 20) 337 return (EINVAL); 338 339 cs->cs_preg[12] = tconst; 340 cs->cs_preg[13] = tconst >> 8; 341 342 /* Caller will stuff the pending registers. */ 343 return (0); 344 } 345 346 int 347 zs_set_modes(cs, cflag) 348 struct zs_chanstate *cs; 349 int cflag; /* bits per second */ 350 { 351 int s; 352 353 /* 354 * Output hardware flow control on the chip is horrendous: 355 * if carrier detect drops, the receiver is disabled, and if 356 * CTS drops, the transmitter is stoped IN MID CHARACTER! 357 * Therefore, NEVER set the HFC bit, and instead use the 358 * status interrupt to detect CTS changes. 359 */ 360 s = splzs(); 361 cs->cs_rr0_pps = 0; 362 if ((cflag & (CLOCAL | MDMBUF)) != 0) { 363 cs->cs_rr0_dcd = 0; 364 if ((cflag & MDMBUF) == 0) 365 cs->cs_rr0_pps = ZSRR0_DCD; 366 } else 367 cs->cs_rr0_dcd = ZSRR0_DCD; 368 if ((cflag & CRTSCTS) != 0) { 369 cs->cs_wr5_dtr = ZSWR5_DTR; 370 cs->cs_wr5_rts = ZSWR5_RTS; 371 cs->cs_rr0_cts = ZSRR0_CTS; 372 } else if ((cflag & MDMBUF) != 0) { 373 cs->cs_wr5_dtr = 0; 374 cs->cs_wr5_rts = ZSWR5_DTR; 375 cs->cs_rr0_cts = ZSRR0_DCD; 376 } else { 377 cs->cs_wr5_dtr = ZSWR5_DTR | ZSWR5_RTS; 378 cs->cs_wr5_rts = 0; 379 cs->cs_rr0_cts = 0; 380 } 381 splx(s); 382 383 /* Caller will stuff the pending registers. */ 384 return (0); 385 } 386 387 388 /* 389 * Read or write the chip with suitable delays. 390 */ 391 392 u_char 393 zs_read_reg(cs, reg) 394 struct zs_chanstate *cs; 395 u_char reg; 396 { 397 u_char val; 398 399 *cs->cs_reg_csr = reg; 400 ZS_DELAY(); 401 val = *cs->cs_reg_csr; 402 ZS_DELAY(); 403 return val; 404 } 405 406 void 407 zs_write_reg(cs, reg, val) 408 struct zs_chanstate *cs; 409 u_char reg, val; 410 { 411 *cs->cs_reg_csr = reg; 412 ZS_DELAY(); 413 *cs->cs_reg_csr = val; 414 ZS_DELAY(); 415 } 416 417 u_char zs_read_csr(cs) 418 struct zs_chanstate *cs; 419 { 420 u_char val; 421 422 val = *cs->cs_reg_csr; 423 ZS_DELAY(); 424 return val; 425 } 426 427 void zs_write_csr(cs, val) 428 struct zs_chanstate *cs; 429 u_char val; 430 { 431 *cs->cs_reg_csr = val; 432 ZS_DELAY(); 433 } 434 435 u_char zs_read_data(cs) 436 struct zs_chanstate *cs; 437 { 438 u_char val; 439 440 val = *cs->cs_reg_data; 441 ZS_DELAY(); 442 return val; 443 } 444 445 void zs_write_data(cs, val) 446 struct zs_chanstate *cs; 447 u_char val; 448 { 449 *cs->cs_reg_data = val; 450 ZS_DELAY(); 451 } 452 453 /**************************************************************** 454 * Console support functions (MVME specific!) 455 ****************************************************************/ 456 457 /* 458 * Polled input char. 459 */ 460 int 461 zs_getc(arg) 462 void *arg; 463 { 464 struct zs_chanstate *cs = arg; 465 int s, c, rr0, stat; 466 467 s = splhigh(); 468 top: 469 /* Wait for a character to arrive. */ 470 do { 471 rr0 = *cs->cs_reg_csr; 472 ZS_DELAY(); 473 } while ((rr0 & ZSRR0_RX_READY) == 0); 474 475 /* Read error register. */ 476 stat = zs_read_reg(cs, 1) & (ZSRR1_FE | ZSRR1_DO | ZSRR1_PE); 477 if (stat) { 478 zs_write_csr(cs, ZSM_RESET_ERR); 479 goto top; 480 } 481 482 /* Read character. */ 483 c = *cs->cs_reg_data; 484 ZS_DELAY(); 485 splx(s); 486 487 return (c); 488 } 489 490 /* 491 * Polled output char. 492 */ 493 void 494 zs_putc(arg, c) 495 void *arg; 496 int c; 497 { 498 struct zs_chanstate *cs = arg; 499 int s, rr0; 500 501 s = splhigh(); 502 /* Wait for transmitter to become ready. */ 503 do { 504 rr0 = *cs->cs_reg_csr; 505 ZS_DELAY(); 506 } while ((rr0 & ZSRR0_TX_READY) == 0); 507 508 *cs->cs_reg_data = c; 509 ZS_DELAY(); 510 splx(s); 511 } 512 513 /* 514 * Common parts of console init. 515 */ 516 void 517 zs_cnconfig(zsc_unit, channel, zs, pclk) 518 int zsc_unit, channel; 519 struct zsdevice *zs; 520 int pclk; 521 { 522 struct zs_chanstate *cs; 523 struct zschan *zc; 524 525 zc = (channel == 0) ? &zs->zs_chan_a : &zs->zs_chan_b; 526 527 /* 528 * Pointer to channel state. Later, the console channel 529 * state is copied into the softc, and the console channel 530 * pointer adjusted to point to the new copy. 531 */ 532 zs_conschan = cs = &zs_conschan_store; 533 zs_hwflags[zsc_unit][channel] = ZS_HWFLAG_CONSOLE; 534 535 /* Setup temporary chanstate. */ 536 cs->cs_brg_clk = pclk / 16; 537 cs->cs_reg_csr = zc->zc_csr; 538 cs->cs_reg_data = zc->zc_data; 539 540 /* Initialize the pending registers. */ 541 memcpy(cs->cs_preg, zs_init_reg, 16); 542 cs->cs_preg[5] |= (ZSWR5_DTR | ZSWR5_RTS); 543 544 #if 0 545 /* XXX: Preserve BAUD rate from boot loader. */ 546 /* XXX: Also, why reset the chip here? -gwr */ 547 cs->cs_defspeed = zs_get_speed(cs); 548 #else 549 cs->cs_defspeed = 9600; /* XXX */ 550 #endif 551 zs_set_speed(cs, cs->cs_defspeed); 552 cs->cs_creg[12] = cs->cs_preg[12]; 553 cs->cs_creg[13] = cs->cs_preg[13]; 554 555 /* Clear the master interrupt enable. */ 556 zs_write_reg(cs, 9, 0); 557 558 /* Reset the whole SCC chip. */ 559 zs_write_reg(cs, 9, ZSWR9_HARD_RESET); 560 561 /* Copy "pending" to "current" and H/W. */ 562 zs_loadchannelregs(cs); 563 } 564 565 /* 566 * Polled console input putchar. 567 */ 568 int 569 zsc_pcccngetc(dev) 570 dev_t dev; 571 { 572 struct zs_chanstate *cs = zs_conschan; 573 int c; 574 575 c = zs_getc(cs); 576 return (c); 577 } 578 579 /* 580 * Polled console output putchar. 581 */ 582 void 583 zsc_pcccnputc(dev, c) 584 dev_t dev; 585 int c; 586 { 587 struct zs_chanstate *cs = zs_conschan; 588 589 zs_putc(cs, c); 590 } 591 592 /* 593 * Handle user request to enter kernel debugger. 594 */ 595 void 596 zs_abort(cs) 597 struct zs_chanstate *cs; 598 { 599 int rr0; 600 601 /* Wait for end of break to avoid PROM abort. */ 602 /* XXX - Limit the wait? */ 603 do { 604 rr0 = *cs->cs_reg_csr; 605 ZS_DELAY(); 606 } while (rr0 & ZSRR0_BREAK); 607 608 mvme68k_abort("SERIAL LINE ABORT"); 609 } 610