1 /* $OpenBSD: cgthree.c,v 1.34 2003/07/03 21:02:13 jason Exp $ */ 2 3 /* 4 * Copyright (c) 2001 Jason L. Wright (jason@thought.net) 5 * 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 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 19 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, 20 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 22 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 24 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 25 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 26 * POSSIBILITY OF SUCH DAMAGE. 27 * 28 * Effort sponsored in part by the Defense Advanced Research Projects 29 * Agency (DARPA) and Air Force Research Laboratory, Air Force 30 * Materiel Command, USAF, under agreement number F30602-01-2-0537. 31 * 32 */ 33 34 #include <sys/param.h> 35 #include <sys/systm.h> 36 #include <sys/kernel.h> 37 #include <sys/errno.h> 38 #include <sys/device.h> 39 #include <sys/ioctl.h> 40 #include <sys/malloc.h> 41 42 #include <machine/bus.h> 43 #include <machine/intr.h> 44 #include <machine/autoconf.h> 45 #include <machine/openfirm.h> 46 47 #include <dev/sbus/sbusvar.h> 48 #include <dev/wscons/wsconsio.h> 49 #include <dev/wscons/wsdisplayvar.h> 50 #include <dev/wscons/wscons_raster.h> 51 #include <dev/rasops/rasops.h> 52 #include <machine/fbvar.h> 53 54 #include <dev/ic/bt458reg.h> 55 56 #define CGTHREE_CTRL_OFFSET 0x400000 57 #define CGTHREE_CTRL_SIZE (sizeof(u_int32_t) * 8) 58 #define CGTHREE_VID_OFFSET 0x800000 59 #define CGTHREE_VID_SIZE (1024 * 1024) 60 61 union bt_cmap { 62 u_int8_t cm_map[256][3]; /* 256 r/b/g entries */ 63 u_int32_t cm_chip[256 * 3 / 4]; /* the way the chip is loaded */ 64 }; 65 66 #define BT_ADDR 0x00 /* map address register */ 67 #define BT_CMAP 0x04 /* colormap data register */ 68 #define BT_CTRL 0x08 /* control register */ 69 #define BT_OMAP 0x0c /* overlay (cursor) map register */ 70 #define CG3_FBC_CTRL 0x10 /* control */ 71 #define CG3_FBC_STAT 0x11 /* status */ 72 #define CG3_FBC_START 0x12 /* cursor start */ 73 #define CG3_FBC_END 0x13 /* cursor end */ 74 #define CG3_FBC_VCTRL 0x14 /* 12 bytes of timing goo */ 75 76 #define BT_WRITE(sc, reg, val) \ 77 bus_space_write_4((sc)->sc_bustag, (sc)->sc_ctrl_regs, (reg), (val)) 78 #define BT_READ(sc, reg) \ 79 bus_space_read_4((sc)->sc_bustag, (sc)->sc_ctrl_regs, (reg)) 80 #define BT_BARRIER(sc,reg,flags) \ 81 bus_space_barrier((sc)->sc_bustag, (sc)->sc_ctrl_regs, (reg), \ 82 sizeof(u_int32_t), (flags)) 83 84 #define BT_D4M3(x) ((((x) >> 2) << 1) + ((x) >> 2)) /* (x / 4) * 3 */ 85 #define BT_D4M4(x) ((x) & ~3) /* (x / 4) * 4 */ 86 87 #define FBC_CTRL_IENAB 0x80 /* interrupt enable */ 88 #define FBC_CTRL_VENAB 0x40 /* video enable */ 89 #define FBC_CTRL_TIME 0x20 /* timing enable */ 90 #define FBC_CTRL_CURS 0x10 /* cursor compare enable */ 91 #define FBC_CTRL_XTAL 0x0c /* xtal select (0,1,2,test): */ 92 #define FBC_CTRL_XTAL_0 0x00 /* 0 */ 93 #define FBC_CTRL_XTAL_1 0x04 /* 0 */ 94 #define FBC_CTRL_XTAL_2 0x08 /* 0 */ 95 #define FBC_CTRL_XTAL_TEST 0x0c /* 0 */ 96 #define FBC_CTRL_DIV 0x03 /* divisor (1,2,3,4): */ 97 #define FBC_CTRL_DIV_1 0x00 /* / 1 */ 98 #define FBC_CTRL_DIV_2 0x01 /* / 2 */ 99 #define FBC_CTRL_DIV_3 0x02 /* / 3 */ 100 #define FBC_CTRL_DIV_4 0x03 /* / 4 */ 101 102 #define FBC_STAT_INTR 0x80 /* interrupt pending */ 103 #define FBC_STAT_RES 0x70 /* monitor sense: */ 104 #define FBC_STAT_RES_1024 0x10 /* 1024x768 */ 105 #define FBC_STAT_RES_1280 0x40 /* 1280x1024 */ 106 #define FBC_STAT_RES_1152 0x30 /* 1152x900 */ 107 #define FBC_STAT_RES_1152A 0x40 /* 1152x900x76, A */ 108 #define FBC_STAT_RES_1600 0x50 /* 1600x1200 */ 109 #define FBC_STAT_RES_1152B 0x60 /* 1152x900x86, B */ 110 #define FBC_STAT_ID 0x0f /* id mask: */ 111 #define FBC_STAT_ID_COLOR 0x01 /* color */ 112 #define FBC_STAT_ID_MONO 0x02 /* monochrome */ 113 #define FBC_STAT_ID_MONOECL 0x03 /* monochrome, ecl */ 114 115 #define FBC_READ(sc, reg) \ 116 bus_space_read_1((sc)->sc_bustag, (sc)->sc_ctrl_regs, (reg)) 117 #define FBC_WRITE(sc, reg, val) \ 118 bus_space_write_1((sc)->sc_bustag, (sc)->sc_ctrl_regs, (reg), (val)) 119 120 struct cgthree_softc { 121 struct sunfb sc_sunfb; 122 struct sbusdev sc_sd; 123 bus_space_tag_t sc_bustag; 124 bus_addr_t sc_paddr; 125 bus_space_handle_t sc_ctrl_regs; 126 bus_space_handle_t sc_vid_regs; 127 int sc_nscreens; 128 union bt_cmap sc_cmap; 129 u_int sc_mode; 130 }; 131 132 struct wsscreen_descr cgthree_stdscreen = { 133 "std", 134 }; 135 136 const struct wsscreen_descr *cgthree_scrlist[] = { 137 &cgthree_stdscreen, 138 /* XXX other formats? */ 139 }; 140 141 struct wsscreen_list cgthree_screenlist = { 142 sizeof(cgthree_scrlist) / sizeof(struct wsscreen_descr *), cgthree_scrlist 143 }; 144 145 int cgthree_ioctl(void *, u_long, caddr_t, int, struct proc *); 146 int cgthree_alloc_screen(void *, const struct wsscreen_descr *, void **, 147 int *, int *, long *); 148 void cgthree_free_screen(void *, void *); 149 int cgthree_show_screen(void *, void *, int, void (*cb)(void *, int, int), 150 void *); 151 paddr_t cgthree_mmap(void *, off_t, int); 152 int cgthree_is_console(int); 153 void cgthree_loadcmap(struct cgthree_softc *, u_int, u_int); 154 int cg3_bt_putcmap(union bt_cmap *, struct wsdisplay_cmap *); 155 int cg3_bt_getcmap(union bt_cmap *, struct wsdisplay_cmap *); 156 void cgthree_setcolor(void *, u_int, u_int8_t, u_int8_t, u_int8_t); 157 void cgthree_burner(void *, u_int, u_int); 158 void cgthree_reset(struct cgthree_softc *); 159 void cgthree_updatecursor(struct rasops_info *); 160 161 struct wsdisplay_accessops cgthree_accessops = { 162 cgthree_ioctl, 163 cgthree_mmap, 164 cgthree_alloc_screen, 165 cgthree_free_screen, 166 cgthree_show_screen, 167 NULL, /* load_font */ 168 NULL, /* scrollback */ 169 NULL, /* getchar */ 170 cgthree_burner, 171 }; 172 173 int cgthreematch(struct device *, void *, void *); 174 void cgthreeattach(struct device *, struct device *, void *); 175 176 struct cfattach cgthree_ca = { 177 sizeof (struct cgthree_softc), cgthreematch, cgthreeattach 178 }; 179 180 struct cfdriver cgthree_cd = { 181 NULL, "cgthree", DV_DULL 182 }; 183 184 #define CG3_TYPE_DEFAULT 0 185 #define CG3_TYPE_76HZ 1 186 #define CG3_TYPE_SMALL 2 187 188 struct cg3_videoctrl { 189 u_int8_t sense; 190 u_int8_t vctrl[12]; 191 u_int8_t ctrl; 192 } cg3_videoctrl[] = { 193 { /* cpd-1790 */ 194 0x31, 195 { 0xbb, 0x2b, 0x04, 0x14, 0xae, 0x03, 196 0xa8, 0x24, 0x01, 0x05, 0xff, 0x01 }, 197 FBC_CTRL_XTAL_0 | FBC_CTRL_DIV_1 198 }, 199 { /* gdm-20e20 */ 200 0x41, 201 { 0xb7, 0x27, 0x03, 0x0f, 0xae, 0x03, 202 0xae, 0x2a, 0x01, 0x09, 0xff, 0x01 }, 203 FBC_CTRL_XTAL_1 | FBC_CTRL_DIV_1 204 }, 205 { /* defaults, should be last */ 206 0xff, 207 { 0xbb, 0x2b, 0x03, 0x0b, 0xb3, 0x03, 208 0xaf, 0x2b, 0x02, 0x0a, 0xff, 0x01 }, 209 0, 210 }, 211 }; 212 213 int 214 cgthreematch(struct device *parent, void *vcf, void *aux) 215 { 216 struct cfdata *cf = vcf; 217 struct sbus_attach_args *sa = aux; 218 219 return (strcmp(cf->cf_driver->cd_name, sa->sa_name) == 0); 220 } 221 222 void 223 cgthreeattach(struct device *parent, struct device *self, void *aux) 224 { 225 struct cgthree_softc *sc = (struct cgthree_softc *)self; 226 struct sbus_attach_args *sa = aux; 227 struct wsemuldisplaydev_attach_args waa; 228 int console, i; 229 230 sc->sc_bustag = sa->sa_bustag; 231 sc->sc_paddr = sbus_bus_addr(sa->sa_bustag, sa->sa_slot, sa->sa_offset); 232 233 fb_setsize(&sc->sc_sunfb, 8, 1152, 900, sa->sa_node, 0); 234 235 if (sa->sa_nreg != 1) { 236 printf(": expected %d registers, got %d\n", 1, sa->sa_nreg); 237 goto fail; 238 } 239 240 /* 241 * Map just CTRL and video RAM. 242 */ 243 if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[0].sbr_slot, 244 sa->sa_reg[0].sbr_offset + CGTHREE_CTRL_OFFSET, 245 CGTHREE_CTRL_SIZE, 0, 0, &sc->sc_ctrl_regs) != 0) { 246 printf(": cannot map ctrl registers\n"); 247 goto fail_ctrl; 248 } 249 250 if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[0].sbr_slot, 251 sa->sa_reg[0].sbr_offset + CGTHREE_VID_OFFSET, 252 sc->sc_sunfb.sf_fbsize, BUS_SPACE_MAP_LINEAR, 253 0, &sc->sc_vid_regs) != 0) { 254 printf(": cannot map vid registers\n"); 255 goto fail_vid; 256 } 257 258 console = cgthree_is_console(sa->sa_node); 259 260 sbus_establish(&sc->sc_sd, &sc->sc_sunfb.sf_dev); 261 262 cgthree_reset(sc); 263 264 BT_WRITE(sc, BT_ADDR, 0); 265 for (i = 0; i < 256 * 3 / 4; i++) 266 sc->sc_cmap.cm_chip[i] = BT_READ(sc, BT_CMAP); 267 268 cgthree_burner(sc, 1, 0); 269 270 sc->sc_sunfb.sf_ro.ri_bits = (void *)bus_space_vaddr(sc->sc_bustag, 271 sc->sc_vid_regs); 272 sc->sc_sunfb.sf_ro.ri_hw = sc; 273 fbwscons_init(&sc->sc_sunfb, console ? 0 : RI_CLEAR); 274 275 cgthree_stdscreen.capabilities = sc->sc_sunfb.sf_ro.ri_caps; 276 cgthree_stdscreen.nrows = sc->sc_sunfb.sf_ro.ri_rows; 277 cgthree_stdscreen.ncols = sc->sc_sunfb.sf_ro.ri_cols; 278 cgthree_stdscreen.textops = &sc->sc_sunfb.sf_ro.ri_ops; 279 280 printf("\n"); 281 282 fbwscons_setcolormap(&sc->sc_sunfb, cgthree_setcolor); 283 284 if (console) { 285 sc->sc_sunfb.sf_ro.ri_updatecursor = cgthree_updatecursor; 286 fbwscons_console_init(&sc->sc_sunfb, &cgthree_stdscreen, -1, 287 cgthree_burner); 288 } 289 290 waa.console = console; 291 waa.scrdata = &cgthree_screenlist; 292 waa.accessops = &cgthree_accessops; 293 waa.accesscookie = sc; 294 config_found(self, &waa, wsemuldisplaydevprint); 295 296 return; 297 298 fail_vid: 299 bus_space_unmap(sa->sa_bustag, sc->sc_ctrl_regs, CGTHREE_CTRL_SIZE); 300 fail_ctrl: 301 fail: 302 ; 303 } 304 305 int 306 cgthree_ioctl(void *v, u_long cmd, caddr_t data, int flags, struct proc *p) 307 { 308 struct cgthree_softc *sc = v; 309 struct wsdisplay_fbinfo *wdf; 310 struct wsdisplay_cmap *cm; 311 int error; 312 313 switch (cmd) { 314 case WSDISPLAYIO_GTYPE: 315 *(u_int *)data = WSDISPLAY_TYPE_SUNCG3; 316 break; 317 case WSDISPLAYIO_SMODE: 318 sc->sc_mode = *(u_int *)data; 319 break; 320 case WSDISPLAYIO_GINFO: 321 wdf = (void *)data; 322 wdf->height = sc->sc_sunfb.sf_height; 323 wdf->width = sc->sc_sunfb.sf_width; 324 wdf->depth = sc->sc_sunfb.sf_depth; 325 wdf->cmsize = 256; 326 break; 327 case WSDISPLAYIO_LINEBYTES: 328 *(u_int *)data = sc->sc_sunfb.sf_linebytes; 329 break; 330 331 case WSDISPLAYIO_GETCMAP: 332 cm = (struct wsdisplay_cmap *)data; 333 error = cg3_bt_getcmap(&sc->sc_cmap, cm); 334 if (error) 335 return (error); 336 break; 337 338 case WSDISPLAYIO_PUTCMAP: 339 cm = (struct wsdisplay_cmap *)data; 340 error = cg3_bt_putcmap(&sc->sc_cmap, cm); 341 if (error) 342 return (error); 343 cgthree_loadcmap(sc, cm->index, cm->count); 344 break; 345 346 case WSDISPLAYIO_SVIDEO: 347 case WSDISPLAYIO_GVIDEO: 348 case WSDISPLAYIO_GCURPOS: 349 case WSDISPLAYIO_SCURPOS: 350 case WSDISPLAYIO_GCURMAX: 351 case WSDISPLAYIO_GCURSOR: 352 case WSDISPLAYIO_SCURSOR: 353 default: 354 return -1; /* not supported yet */ 355 } 356 357 return (0); 358 } 359 360 int 361 cgthree_alloc_screen(void *v, const struct wsscreen_descr *type, 362 void **cookiep, int *curxp, int *curyp, long *attrp) 363 { 364 struct cgthree_softc *sc = v; 365 366 if (sc->sc_nscreens > 0) 367 return (ENOMEM); 368 369 *cookiep = &sc->sc_sunfb.sf_ro; 370 *curyp = 0; 371 *curxp = 0; 372 sc->sc_sunfb.sf_ro.ri_ops.alloc_attr(&sc->sc_sunfb.sf_ro, 373 WSCOL_BLACK, WSCOL_WHITE, WSATTR_WSCOLORS, attrp); 374 sc->sc_nscreens++; 375 return (0); 376 } 377 378 void 379 cgthree_free_screen(void *v, void *cookie) 380 { 381 struct cgthree_softc *sc = v; 382 383 sc->sc_nscreens--; 384 } 385 386 int 387 cgthree_show_screen(void *v, void *cookie, int waitok, 388 void (*cb)(void *, int, int), void *cbarg) 389 { 390 return (0); 391 } 392 393 #define START (128 * 1024 + 128 * 1024) 394 #define NOOVERLAY (0x04000000) 395 396 paddr_t 397 cgthree_mmap(void *v, off_t offset, int prot) 398 { 399 struct cgthree_softc *sc = v; 400 401 if (offset & PGOFSET || offset < 0) 402 return (-1); 403 404 switch (sc->sc_mode) { 405 case WSDISPLAYIO_MODE_MAPPED: 406 if (offset >= NOOVERLAY) 407 offset -= NOOVERLAY; 408 else if (offset >= START) 409 offset -= START; 410 else 411 offset = 0; 412 if (offset >= sc->sc_sunfb.sf_fbsize) 413 return (-1); 414 return (bus_space_mmap(sc->sc_bustag, sc->sc_paddr, 415 CGTHREE_VID_OFFSET + offset, prot, BUS_SPACE_MAP_LINEAR)); 416 case WSDISPLAYIO_MODE_DUMBFB: 417 if (offset < sc->sc_sunfb.sf_fbsize) 418 return (bus_space_mmap(sc->sc_bustag, sc->sc_paddr, 419 CGTHREE_VID_OFFSET + offset, prot, 420 BUS_SPACE_MAP_LINEAR)); 421 break; 422 } 423 return (-1); 424 } 425 426 int 427 cgthree_is_console(int node) 428 { 429 extern int fbnode; 430 431 return (fbnode == node); 432 } 433 434 void 435 cgthree_setcolor(void *v, u_int index, u_int8_t r, u_int8_t g, u_int8_t b) 436 { 437 struct cgthree_softc *sc = v; 438 union bt_cmap *bcm = &sc->sc_cmap; 439 440 bcm->cm_map[index][0] = r; 441 bcm->cm_map[index][1] = g; 442 bcm->cm_map[index][2] = b; 443 cgthree_loadcmap(sc, index, 1); 444 } 445 446 void 447 cgthree_loadcmap(struct cgthree_softc *sc, u_int start, u_int ncolors) 448 { 449 u_int cstart; 450 int count; 451 452 cstart = BT_D4M3(start); 453 count = BT_D4M3(start + ncolors - 1) - BT_D4M3(start) + 3; 454 BT_WRITE(sc, BT_ADDR, BT_D4M4(start)); 455 while (--count >= 0) { 456 BT_WRITE(sc, BT_CMAP, sc->sc_cmap.cm_chip[cstart]); 457 cstart++; 458 } 459 } 460 461 int 462 cg3_bt_getcmap(union bt_cmap *bcm, struct wsdisplay_cmap *rcm) 463 { 464 u_int index = rcm->index, count = rcm->count, i; 465 int error; 466 467 if (index >= 256 || count > 256 - index) 468 return (EINVAL); 469 for (i = 0; i < count; i++) { 470 if ((error = copyout(&bcm->cm_map[index + i][0], 471 &rcm->red[i], 1)) != 0) 472 return (error); 473 if ((error = copyout(&bcm->cm_map[index + i][1], 474 &rcm->green[i], 1)) != 0) 475 return (error); 476 if ((error = copyout(&bcm->cm_map[index + i][2], 477 &rcm->blue[i], 1)) != 0) 478 return (error); 479 } 480 return (0); 481 } 482 483 int 484 cg3_bt_putcmap(union bt_cmap *bcm, struct wsdisplay_cmap *rcm) 485 { 486 u_int index = rcm->index, count = rcm->count, i; 487 int error; 488 489 if (index >= 256 || count > 256 - index) 490 return (EINVAL); 491 for (i = 0; i < count; i++) { 492 if ((error = copyin(&rcm->red[i], 493 &bcm->cm_map[index + i][0], 1)) != 0) 494 return (error); 495 if ((error = copyin(&rcm->green[i], 496 &bcm->cm_map[index + i][1], 1)) != 0) 497 return (error); 498 if ((error = copyin(&rcm->blue[i], 499 &bcm->cm_map[index + i][2], 1)) != 0) 500 return (error); 501 } 502 return (0); 503 } 504 505 void 506 cgthree_reset(struct cgthree_softc *sc) 507 { 508 int i, j; 509 u_int8_t sts, ctrl; 510 511 sts = FBC_READ(sc, CG3_FBC_STAT); 512 ctrl = FBC_READ(sc, CG3_FBC_CTRL); 513 514 if (ctrl & FBC_CTRL_TIME) { 515 /* already initialized */ 516 return; 517 } 518 519 for (i = 0; i < sizeof(cg3_videoctrl)/sizeof(cg3_videoctrl[0]); i++) { 520 if (cg3_videoctrl[i].sense == 0xff || 521 (cg3_videoctrl[i].sense == 522 (sts & (FBC_STAT_RES | FBC_STAT_ID)))) { 523 for (j = 0; j < 12; j++) 524 FBC_WRITE(sc, CG3_FBC_VCTRL + j, 525 cg3_videoctrl[i].vctrl[j]); 526 ctrl &= ~(FBC_CTRL_XTAL | FBC_CTRL_DIV); 527 ctrl |= cg3_videoctrl[i].ctrl | 528 FBC_CTRL_TIME; 529 FBC_WRITE(sc, CG3_FBC_CTRL, ctrl); 530 break; 531 } 532 } 533 534 /* enable all the bit planes */ 535 BT_WRITE(sc, BT_ADDR, BT_RMR); 536 BT_BARRIER(sc, BT_ADDR, BUS_SPACE_BARRIER_WRITE); 537 BT_WRITE(sc, BT_CTRL, 0xff); 538 BT_BARRIER(sc, BT_CTRL, BUS_SPACE_BARRIER_WRITE); 539 540 /* no plane should blink */ 541 BT_WRITE(sc, BT_ADDR, BT_BMR); 542 BT_BARRIER(sc, BT_ADDR, BUS_SPACE_BARRIER_WRITE); 543 BT_WRITE(sc, BT_CTRL, 0x00); 544 BT_BARRIER(sc, BT_CTRL, BUS_SPACE_BARRIER_WRITE); 545 546 /* 547 * enable the RAMDAC, disable blink, disable overlay 0 and 1, 548 * use 4:1 multiplexor. 549 */ 550 BT_WRITE(sc, BT_ADDR, BT_CR); 551 BT_BARRIER(sc, BT_ADDR, BUS_SPACE_BARRIER_WRITE); 552 BT_WRITE(sc, BT_CTRL, 553 (BTCR_MPLX_4 | BTCR_RAMENA | BTCR_BLINK_6464)); 554 BT_BARRIER(sc, BT_CTRL, BUS_SPACE_BARRIER_WRITE); 555 556 /* disable the D/A read pins */ 557 BT_WRITE(sc, BT_ADDR, BT_CTR); 558 BT_BARRIER(sc, BT_ADDR, BUS_SPACE_BARRIER_WRITE); 559 BT_WRITE(sc, BT_CTRL, 0x00); 560 BT_BARRIER(sc, BT_CTRL, BUS_SPACE_BARRIER_WRITE); 561 } 562 563 void 564 cgthree_burner(void *vsc, u_int on, u_int flags) 565 { 566 struct cgthree_softc *sc = vsc; 567 int s; 568 u_int8_t fbc; 569 570 s = splhigh(); 571 fbc = FBC_READ(sc, CG3_FBC_CTRL); 572 if (on) 573 fbc |= FBC_CTRL_VENAB | FBC_CTRL_TIME; 574 else { 575 fbc &= ~FBC_CTRL_VENAB; 576 if (flags & WSDISPLAY_BURN_VBLANK) 577 fbc &= ~FBC_CTRL_TIME; 578 } 579 FBC_WRITE(sc, CG3_FBC_CTRL, fbc); 580 splx(s); 581 } 582 583 void 584 cgthree_updatecursor(struct rasops_info *ri) 585 { 586 struct cgthree_softc *sc = ri->ri_hw; 587 588 if (sc->sc_sunfb.sf_crowp != NULL) 589 *sc->sc_sunfb.sf_crowp = ri->ri_crow; 590 if (sc->sc_sunfb.sf_ccolp != NULL) 591 *sc->sc_sunfb.sf_ccolp = ri->ri_ccol; 592 } 593