1 /* $NetBSD: radeonfb.c,v 1.29 2008/06/01 16:43:53 macallan Exp $ */ 2 3 /*- 4 * Copyright (c) 2006 Itronix Inc. 5 * All rights reserved. 6 * 7 * Written by Garrett D'Amore for Itronix Inc. 8 * 9 * Redistribution and use in source and binary forms, with or without 10 * modification, are permitted provided that the following conditions 11 * are met: 12 * 1. Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * 2. Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in the 16 * documentation and/or other materials provided with the distribution. 17 * 3. The name of Itronix Inc. may not be used to endorse 18 * or promote products derived from this software without specific 19 * prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY ITRONIX INC. ``AS IS'' AND ANY EXPRESS 22 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 23 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24 * ARE DISCLAIMED. IN NO EVENT SHALL ITRONIX INC. BE LIABLE FOR ANY 25 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE 27 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 29 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 30 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 31 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32 */ 33 34 /* 35 * ATI Technologies Inc. ("ATI") has not assisted in the creation of, and 36 * does not endorse, this software. ATI will not be responsible or liable 37 * for any actual or alleged damage or loss caused by or in connection with 38 * the use of or reliance on this software. 39 */ 40 41 /* 42 * Portions of this code were taken from XFree86's Radeon driver, which bears 43 * this notice: 44 * 45 * Copyright 2000 ATI Technologies Inc., Markham, Ontario, and 46 * VA Linux Systems Inc., Fremont, California. 47 * 48 * All Rights Reserved. 49 * 50 * Permission is hereby granted, free of charge, to any person obtaining 51 * a copy of this software and associated documentation files (the 52 * "Software"), to deal in the Software without restriction, including 53 * without limitation on the rights to use, copy, modify, merge, 54 * publish, distribute, sublicense, and/or sell copies of the Software, 55 * and to permit persons to whom the Software is furnished to do so, 56 * subject to the following conditions: 57 * 58 * The above copyright notice and this permission notice (including the 59 * next paragraph) shall be included in all copies or substantial 60 * portions of the Software. 61 * 62 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 63 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 64 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 65 * NON-INFRINGEMENT. IN NO EVENT SHALL ATI, VA LINUX SYSTEMS AND/OR 66 * THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, 67 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 68 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 69 * DEALINGS IN THE SOFTWARE. 70 */ 71 72 #include <sys/cdefs.h> 73 __KERNEL_RCSID(0, "$NetBSD: radeonfb.c,v 1.29 2008/06/01 16:43:53 macallan Exp $"); 74 75 #define RADEONFB_DEFAULT_DEPTH 32 76 77 #include <sys/param.h> 78 #include <sys/systm.h> 79 #include <sys/device.h> 80 #include <sys/malloc.h> 81 #include <sys/bus.h> 82 #include <sys/kernel.h> 83 #include <sys/lwp.h> 84 #include <sys/kauth.h> 85 86 #include <dev/wscons/wsdisplayvar.h> 87 #include <dev/wscons/wsconsio.h> 88 #include <dev/wsfont/wsfont.h> 89 #include <dev/rasops/rasops.h> 90 #include <dev/videomode/videomode.h> 91 #include <dev/videomode/edidvar.h> 92 #include <dev/wscons/wsdisplay_vconsvar.h> 93 94 #include <dev/pci/pcidevs.h> 95 #include <dev/pci/pcireg.h> 96 #include <dev/pci/pcivar.h> 97 #include <dev/pci/pciio.h> 98 #include <dev/pci/radeonfbreg.h> 99 #include <dev/pci/radeonfbvar.h> 100 #include "opt_radeonfb.h" 101 102 static int radeonfb_match(struct device *, struct cfdata *, void *); 103 static void radeonfb_attach(struct device *, struct device *, void *); 104 static int radeonfb_ioctl(void *, void *, unsigned long, void *, int, 105 struct lwp *); 106 static paddr_t radeonfb_mmap(void *, void *, off_t, int); 107 static int radeonfb_scratch_test(struct radeonfb_softc *, int, uint32_t); 108 static void radeonfb_loadbios(struct radeonfb_softc *, 109 struct pci_attach_args *); 110 111 static uintmax_t radeonfb_getprop_num(struct radeonfb_softc *, const char *, 112 uintmax_t); 113 static int radeonfb_getclocks(struct radeonfb_softc *); 114 static int radeonfb_gettmds(struct radeonfb_softc *); 115 static int radeonfb_calc_dividers(struct radeonfb_softc *, uint32_t, 116 uint32_t *, uint32_t *); 117 static int radeonfb_getconnectors(struct radeonfb_softc *); 118 static const struct videomode *radeonfb_modelookup(const char *); 119 static void radeonfb_init_screen(void *, struct vcons_screen *, int, long *); 120 static void radeonfb_pllwriteupdate(struct radeonfb_softc *, int); 121 static void radeonfb_pllwaitatomicread(struct radeonfb_softc *, int); 122 static void radeonfb_program_vclk(struct radeonfb_softc *, int, int); 123 static void radeonfb_modeswitch(struct radeonfb_display *); 124 static void radeonfb_setcrtc(struct radeonfb_display *, int); 125 static void radeonfb_init_misc(struct radeonfb_softc *); 126 static void radeonfb_set_fbloc(struct radeonfb_softc *); 127 static void radeonfb_init_palette(struct radeonfb_softc *, int); 128 static void radeonfb_r300cg_workaround(struct radeonfb_softc *); 129 130 static int radeonfb_isblank(struct radeonfb_display *); 131 static void radeonfb_blank(struct radeonfb_display *, int); 132 static int radeonfb_set_cursor(struct radeonfb_display *, 133 struct wsdisplay_cursor *); 134 static int radeonfb_set_curpos(struct radeonfb_display *, 135 struct wsdisplay_curpos *); 136 137 /* acceleration support */ 138 static void radeonfb_rectfill(struct radeonfb_display *, int dstx, int dsty, 139 int width, int height, uint32_t color); 140 static void radeonfb_bitblt(struct radeonfb_display *, int srcx, int srcy, 141 int dstx, int dsty, int width, int height, int rop, uint32_t mask); 142 static void radeonfb_feed_bytes(struct radeonfb_display *, int, uint8_t *); 143 static void radeonfb_setup_mono(struct radeonfb_display *, int, int, int, 144 int, uint32_t, uint32_t); 145 146 /* hw cursor support */ 147 static void radeonfb_cursor_cmap(struct radeonfb_display *); 148 static void radeonfb_cursor_shape(struct radeonfb_display *); 149 static void radeonfb_cursor_position(struct radeonfb_display *); 150 static void radeonfb_cursor_visible(struct radeonfb_display *); 151 static void radeonfb_cursor_update(struct radeonfb_display *, unsigned); 152 153 static void radeonfb_wait_fifo(struct radeonfb_softc *, int); 154 static void radeonfb_engine_idle(struct radeonfb_softc *); 155 static void radeonfb_engine_flush(struct radeonfb_softc *); 156 static void radeonfb_engine_reset(struct radeonfb_softc *); 157 static void radeonfb_engine_init(struct radeonfb_display *); 158 static inline void radeonfb_unclip(struct radeonfb_softc *); 159 160 static void radeonfb_eraserows(void *, int, int, long); 161 static void radeonfb_erasecols(void *, int, int, int, long); 162 static void radeonfb_copyrows(void *, int, int, int); 163 static void radeonfb_copycols(void *, int, int, int, int); 164 static void radeonfb_cursor(void *, int, int, int); 165 static void radeonfb_putchar(void *, int, int, unsigned, long); 166 static int radeonfb_allocattr(void *, int, int, int, long *); 167 168 static int radeonfb_get_backlight(struct radeonfb_display *); 169 static int radeonfb_set_backlight(struct radeonfb_display *, int); 170 static void radeonfb_lvds_callout(void *); 171 172 static struct videomode *radeonfb_best_refresh(struct videomode *, 173 struct videomode *); 174 static void radeonfb_pickres(struct radeonfb_display *, uint16_t *, 175 uint16_t *, int); 176 static const struct videomode *radeonfb_port_mode(struct radeonfb_softc *, 177 struct radeonfb_port *, int, int); 178 179 static int radeonfb_drm_print(void *, const char *); 180 181 #ifdef RADEON_DEBUG 182 int radeon_debug = 1; 183 #define DPRINTF(x) \ 184 if (radeon_debug) printf x 185 #define PRINTREG(r) DPRINTF((#r " = %08x\n", GET32(sc, r))) 186 #define PRINTPLL(r) DPRINTF((#r " = %08x\n", GETPLL(sc, r))) 187 #else 188 #define DPRINTF(x) 189 #define PRINTREG(r) 190 #define PRINTPLL(r) 191 #endif 192 193 #define ROUNDUP(x,y) (((x) + ((y) - 1)) & ~((y) - 1)) 194 195 #ifndef RADEON_DEFAULT_MODE 196 /* any reasonably modern display should handle this */ 197 #define RADEON_DEFAULT_MODE "1024x768x60" 198 #endif 199 200 const char *radeonfb_default_mode = RADEON_DEFAULT_MODE; 201 202 static struct { 203 int size; /* minimum memory size (MB) */ 204 int maxx; /* maximum x dimension */ 205 int maxy; /* maximum y dimension */ 206 int maxbpp; /* maximum bpp */ 207 int maxdisp; /* maximum logical display count */ 208 } radeonfb_limits[] = { 209 { 32, 2048, 1536, 32, 2 }, 210 { 16, 1600, 1200, 32, 2 }, 211 { 8, 1600, 1200, 32, 1 }, 212 { 0, 0, 0, 0, 0 }, 213 }; 214 215 static struct wsscreen_descr radeonfb_stdscreen = { 216 "fb", /* name */ 217 0, 0, /* ncols, nrows */ 218 NULL, /* textops */ 219 8, 16, /* fontwidth, fontheight */ 220 WSSCREEN_WSCOLORS, /* capabilities */ 221 0, /* modecookie */ 222 }; 223 224 struct wsdisplay_accessops radeonfb_accessops = { 225 radeonfb_ioctl, 226 radeonfb_mmap, 227 NULL, /* vcons_alloc_screen */ 228 NULL, /* vcons_free_screen */ 229 NULL, /* vcons_show_screen */ 230 NULL, /* load_font */ 231 NULL, /* pollc */ 232 NULL, /* scroll */ 233 }; 234 235 static struct { 236 uint16_t devid; 237 uint16_t family; 238 uint16_t flags; 239 } radeonfb_devices[] = 240 { 241 /* R100 family */ 242 { PCI_PRODUCT_ATI_RADEON_R100_QD, RADEON_R100, 0 }, 243 { PCI_PRODUCT_ATI_RADEON_R100_QE, RADEON_R100, 0 }, 244 { PCI_PRODUCT_ATI_RADEON_R100_QF, RADEON_R100, 0 }, 245 { PCI_PRODUCT_ATI_RADEON_R100_QG, RADEON_R100, 0 }, 246 247 /* RV100 family */ 248 { PCI_PRODUCT_ATI_RADEON_RV100_LY, RADEON_RV100, RFB_MOB }, 249 { PCI_PRODUCT_ATI_RADEON_RV100_LZ, RADEON_RV100, RFB_MOB }, 250 { PCI_PRODUCT_ATI_RADEON_RV100_QY, RADEON_RV100, 0 }, 251 { PCI_PRODUCT_ATI_RADEON_RV100_QZ, RADEON_RV100, 0 }, 252 253 /* RS100 family */ 254 { PCI_PRODUCT_ATI_RADEON_RS100_4136, RADEON_RS100, 0 }, 255 { PCI_PRODUCT_ATI_RADEON_RS100_4336, RADEON_RS100, RFB_MOB }, 256 257 /* RS200/RS250 family */ 258 { PCI_PRODUCT_ATI_RADEON_RS200_4337, RADEON_RS200, RFB_MOB }, 259 { PCI_PRODUCT_ATI_RADEON_RS200_A7, RADEON_RS200, 0 }, 260 { PCI_PRODUCT_ATI_RADEON_RS250_B7, RADEON_RS200, RFB_MOB }, 261 { PCI_PRODUCT_ATI_RADEON_RS250_D7, RADEON_RS200, 0 }, 262 263 /* R200 family */ 264 /* add more R200 products? , 5148 */ 265 { PCI_PRODUCT_ATI_RADEON_R200_BB, RADEON_R200, 0 }, 266 { PCI_PRODUCT_ATI_RADEON_R200_BC, RADEON_R200, 0 }, 267 { PCI_PRODUCT_ATI_RADEON_R200_QH, RADEON_R200, 0 }, 268 { PCI_PRODUCT_ATI_RADEON_R200_QL, RADEON_R200, 0 }, 269 { PCI_PRODUCT_ATI_RADEON_R200_QM, RADEON_R200, 0 }, 270 271 /* RV200 family */ 272 { PCI_PRODUCT_ATI_RADEON_RV200_LW, RADEON_RV200, RFB_MOB }, 273 { PCI_PRODUCT_ATI_RADEON_RV200_LX, RADEON_RV200, RFB_MOB }, 274 { PCI_PRODUCT_ATI_RADEON_RV200_QW, RADEON_RV200, 0 }, 275 { PCI_PRODUCT_ATI_RADEON_RV200_QX, RADEON_RV200, 0 }, 276 277 /* RV250 family */ 278 { PCI_PRODUCT_ATI_RADEON_RV250_4966, RADEON_RV250, 0 }, 279 { PCI_PRODUCT_ATI_RADEON_RV250_4967, RADEON_RV250, 0 }, 280 { PCI_PRODUCT_ATI_RADEON_RV250_4C64, RADEON_RV250, RFB_MOB }, 281 { PCI_PRODUCT_ATI_RADEON_RV250_4C66, RADEON_RV250, RFB_MOB }, 282 { PCI_PRODUCT_ATI_RADEON_RV250_4C67, RADEON_RV250, RFB_MOB }, 283 284 /* RS300 family */ 285 { PCI_PRODUCT_ATI_RADEON_RS300_X5, RADEON_RS300, 0 }, 286 { PCI_PRODUCT_ATI_RADEON_RS300_X4, RADEON_RS300, 0 }, 287 { PCI_PRODUCT_ATI_RADEON_RS300_7834, RADEON_RS300, 0 }, 288 { PCI_PRODUCT_ATI_RADEON_RS300_7835, RADEON_RS300, RFB_MOB }, 289 290 /* RV280 family */ 291 { PCI_PRODUCT_ATI_RADEON_RV280_5960, RADEON_RV280, 0 }, 292 { PCI_PRODUCT_ATI_RADEON_RV280_5961, RADEON_RV280, 0 }, 293 { PCI_PRODUCT_ATI_RADEON_RV280_5962, RADEON_RV280, 0 }, 294 { PCI_PRODUCT_ATI_RADEON_RV280_5963, RADEON_RV280, 0 }, 295 { PCI_PRODUCT_ATI_RADEON_RV280_5964, RADEON_RV280, 0 }, 296 { PCI_PRODUCT_ATI_RADEON_RV280_5C61, RADEON_RV280, RFB_MOB }, 297 { PCI_PRODUCT_ATI_RADEON_RV280_5C63, RADEON_RV280, RFB_MOB }, 298 299 /* R300 family */ 300 { PCI_PRODUCT_ATI_RADEON_R300_AD, RADEON_R300, 0 }, 301 { PCI_PRODUCT_ATI_RADEON_R300_AE, RADEON_R300, 0 }, 302 { PCI_PRODUCT_ATI_RADEON_R300_AF, RADEON_R300, 0 }, 303 { PCI_PRODUCT_ATI_RADEON_R300_AG, RADEON_R300, 0 }, 304 { PCI_PRODUCT_ATI_RADEON_R300_ND, RADEON_R300, 0 }, 305 { PCI_PRODUCT_ATI_RADEON_R300_NE, RADEON_R300, 0 }, 306 { PCI_PRODUCT_ATI_RADEON_R300_NF, RADEON_R300, 0 }, 307 { PCI_PRODUCT_ATI_RADEON_R300_NG, RADEON_R300, 0 }, 308 309 /* RV350/RV360 family */ 310 { PCI_PRODUCT_ATI_RADEON_RV350_AP, RADEON_RV350, 0 }, 311 { PCI_PRODUCT_ATI_RADEON_RV350_AQ, RADEON_RV350, 0 }, 312 { PCI_PRODUCT_ATI_RADEON_RV360_AR, RADEON_RV350, 0 }, 313 { PCI_PRODUCT_ATI_RADEON_RV350_AS, RADEON_RV350, 0 }, 314 { PCI_PRODUCT_ATI_RADEON_RV350_AT, RADEON_RV350, 0 }, 315 { PCI_PRODUCT_ATI_RADEON_RV350_AV, RADEON_RV350, 0 }, 316 { PCI_PRODUCT_ATI_RADEON_RV350_NP, RADEON_RV350, RFB_MOB }, 317 { PCI_PRODUCT_ATI_RADEON_RV350_NQ, RADEON_RV350, RFB_MOB }, 318 { PCI_PRODUCT_ATI_RADEON_RV350_NR, RADEON_RV350, RFB_MOB }, 319 { PCI_PRODUCT_ATI_RADEON_RV350_NS, RADEON_RV350, RFB_MOB }, 320 { PCI_PRODUCT_ATI_RADEON_RV350_NT, RADEON_RV350, RFB_MOB }, 321 { PCI_PRODUCT_ATI_RADEON_RV350_NV, RADEON_RV350, RFB_MOB }, 322 323 /* R350/R360 family */ 324 { PCI_PRODUCT_ATI_RADEON_R350_AH, RADEON_R350, 0 }, 325 { PCI_PRODUCT_ATI_RADEON_R350_AI, RADEON_R350, 0 }, 326 { PCI_PRODUCT_ATI_RADEON_R350_AJ, RADEON_R350, 0 }, 327 { PCI_PRODUCT_ATI_RADEON_R350_AK, RADEON_R350, 0 }, 328 { PCI_PRODUCT_ATI_RADEON_R350_NH, RADEON_R350, 0 }, 329 { PCI_PRODUCT_ATI_RADEON_R350_NI, RADEON_R350, 0 }, 330 { PCI_PRODUCT_ATI_RADEON_R350_NK, RADEON_R350, 0 }, 331 { PCI_PRODUCT_ATI_RADEON_R360_NJ, RADEON_R350, 0 }, 332 333 /* RV380/RV370 family */ 334 { PCI_PRODUCT_ATI_RADEON_RV380_3150, RADEON_RV380, RFB_MOB }, 335 { PCI_PRODUCT_ATI_RADEON_RV380_3154, RADEON_RV380, RFB_MOB }, 336 { PCI_PRODUCT_ATI_RADEON_RV380_3E50, RADEON_RV380, 0 }, 337 { PCI_PRODUCT_ATI_RADEON_RV380_3E54, RADEON_RV380, 0 }, 338 { PCI_PRODUCT_ATI_RADEON_RV370_5460, RADEON_RV380, RFB_MOB }, 339 { PCI_PRODUCT_ATI_RADEON_RV370_5464, RADEON_RV380, RFB_MOB }, 340 { PCI_PRODUCT_ATI_RADEON_RV370_5B60, RADEON_RV380, 0 }, 341 { PCI_PRODUCT_ATI_RADEON_RV370_5B64, RADEON_RV380, 0 }, 342 { PCI_PRODUCT_ATI_RADEON_RV370_5B65, RADEON_RV380, 0 }, 343 344 /* R420/R423 family */ 345 { PCI_PRODUCT_ATI_RADEON_R420_JH, RADEON_R420, 0 }, 346 { PCI_PRODUCT_ATI_RADEON_R420_JI, RADEON_R420, 0 }, 347 { PCI_PRODUCT_ATI_RADEON_R420_JJ, RADEON_R420, 0 }, 348 { PCI_PRODUCT_ATI_RADEON_R420_JK, RADEON_R420, 0 }, 349 { PCI_PRODUCT_ATI_RADEON_R420_JL, RADEON_R420, 0 }, 350 { PCI_PRODUCT_ATI_RADEON_R420_JM, RADEON_R420, 0 }, 351 { PCI_PRODUCT_ATI_RADEON_R420_JN, RADEON_R420, RFB_MOB }, 352 { PCI_PRODUCT_ATI_RADEON_R420_JP, RADEON_R420, 0 }, 353 { PCI_PRODUCT_ATI_RADEON_R423_UH, RADEON_R420, 0 }, 354 { PCI_PRODUCT_ATI_RADEON_R423_UI, RADEON_R420, 0 }, 355 { PCI_PRODUCT_ATI_RADEON_R423_UJ, RADEON_R420, 0 }, 356 { PCI_PRODUCT_ATI_RADEON_R423_UK, RADEON_R420, 0 }, 357 { PCI_PRODUCT_ATI_RADEON_R423_UQ, RADEON_R420, 0 }, 358 { PCI_PRODUCT_ATI_RADEON_R423_UR, RADEON_R420, 0 }, 359 { PCI_PRODUCT_ATI_RADEON_R423_UT, RADEON_R420, 0 }, 360 { PCI_PRODUCT_ATI_RADEON_R423_5D57, RADEON_R420, 0 }, 361 { PCI_PRODUCT_ATI_RADEON_R430_554F, RADEON_R420, 0 }, 362 363 { 0, 0, 0 } 364 }; 365 366 static struct { 367 int divider; 368 int mask; 369 } radeonfb_dividers[] = { 370 { 1, 0 }, 371 { 2, 1 }, 372 { 3, 4 }, 373 { 4, 2 }, 374 { 6, 6 }, 375 { 8, 3 }, 376 { 12, 7 }, 377 { 0, 0 } 378 }; 379 380 /* 381 * This table taken from X11. 382 */ 383 static const struct { 384 int family; 385 struct radeon_tmds_pll plls[4]; 386 } radeonfb_tmds_pll[] = { 387 { RADEON_R100, {{12000, 0xa1b}, {-1, 0xa3f}}}, 388 { RADEON_RV100, {{12000, 0xa1b}, {-1, 0xa3f}}}, 389 { RADEON_RS100, {{0, 0}}}, 390 { RADEON_RV200, {{15000, 0xa1b}, {-1, 0xa3f}}}, 391 { RADEON_RS200, {{15000, 0xa1b}, {-1, 0xa3f}}}, 392 { RADEON_R200, {{15000, 0xa1b}, {-1, 0xa3f}}}, 393 { RADEON_RV250, {{15500, 0x81b}, {-1, 0x83f}}}, 394 { RADEON_RS300, {{0, 0}}}, 395 { RADEON_RV280, {{13000, 0x400f4}, {15000, 0x400f7}}}, 396 { RADEON_R300, {{-1, 0xb01cb}}}, 397 { RADEON_R350, {{-1, 0xb01cb}}}, 398 { RADEON_RV350, {{15000, 0xb0155}, {-1, 0xb01cb}}}, 399 { RADEON_RV380, {{15000, 0xb0155}, {-1, 0xb01cb}}}, 400 { RADEON_R420, {{-1, 0xb01cb}}}, 401 }; 402 403 #define RADEONFB_BACKLIGHT_MAX 255 /* Maximum backlight level. */ 404 405 406 CFATTACH_DECL(radeonfb, sizeof (struct radeonfb_softc), 407 radeonfb_match, radeonfb_attach, NULL, NULL); 408 409 static int 410 radeonfb_match(struct device *parent, struct cfdata *match, void *aux) 411 { 412 struct pci_attach_args *pa = aux; 413 int i; 414 415 if (PCI_VENDOR(pa->pa_id) != PCI_VENDOR_ATI) 416 return 0; 417 418 for (i = 0; radeonfb_devices[i].devid; i++) { 419 if (PCI_PRODUCT(pa->pa_id) == radeonfb_devices[i].devid) 420 return 100; /* high to defeat VGA/VESA */ 421 } 422 423 return 0; 424 } 425 426 static void 427 radeonfb_attach(struct device *parent, struct device *dev, void *aux) 428 { 429 struct radeonfb_softc *sc = (struct radeonfb_softc *)dev; 430 struct pci_attach_args *pa = aux; 431 const char *mptr; 432 bus_size_t bsz; 433 pcireg_t screg; 434 int i, j, fg, bg, ul; 435 uint32_t v; 436 437 sc->sc_id = pa->pa_id; 438 for (i = 0; radeonfb_devices[i].devid; i++) { 439 if (PCI_PRODUCT(sc->sc_id) == radeonfb_devices[i].devid) 440 break; 441 } 442 443 pci_devinfo(sc->sc_id, pa->pa_class, 0, sc->sc_devinfo, 444 sizeof(sc->sc_devinfo)); 445 446 aprint_naive("\n"); 447 aprint_normal(": %s\n", sc->sc_devinfo); 448 449 DPRINTF((prop_dictionary_externalize(device_properties(dev)))); 450 451 KASSERT(radeonfb_devices[i].devid != 0); 452 sc->sc_pt = pa->pa_tag; 453 sc->sc_iot = pa->pa_iot; 454 sc->sc_pc = pa->pa_pc; 455 sc->sc_family = radeonfb_devices[i].family; 456 sc->sc_flags = radeonfb_devices[i].flags; 457 458 /* enable memory and IO access */ 459 screg = pci_conf_read(sc->sc_pc, sc->sc_pt, PCI_COMMAND_STATUS_REG); 460 screg |= PCI_FLAGS_IO_ENABLED | PCI_FLAGS_MEM_ENABLED; 461 pci_conf_write(sc->sc_pc, sc->sc_pt, PCI_COMMAND_STATUS_REG, screg); 462 463 /* 464 * Some flags are general to entire chip families, and rather 465 * than clutter up the table with them, we go ahead and set 466 * them here. 467 */ 468 switch (sc->sc_family) { 469 case RADEON_RS100: 470 case RADEON_RS200: 471 sc->sc_flags |= RFB_IGP | RFB_RV100; 472 break; 473 474 case RADEON_RV100: 475 case RADEON_RV200: 476 case RADEON_RV250: 477 case RADEON_RV280: 478 sc->sc_flags |= RFB_RV100; 479 break; 480 481 case RADEON_RS300: 482 sc->sc_flags |= RFB_SDAC | RFB_IGP | RFB_RV100; 483 break; 484 485 case RADEON_R300: 486 case RADEON_RV350: 487 case RADEON_R350: 488 case RADEON_RV380: 489 case RADEON_R420: 490 /* newer chips */ 491 sc->sc_flags |= RFB_R300; 492 break; 493 494 case RADEON_R100: 495 sc->sc_flags |= RFB_NCRTC2; 496 break; 497 } 498 499 if ((sc->sc_family == RADEON_RV200) || 500 (sc->sc_family == RADEON_RV250) || 501 (sc->sc_family == RADEON_RV280) || 502 (sc->sc_family == RADEON_RV350)) { 503 bool inverted = 0; 504 /* backlight level is linear */ 505 DPRINTF(("found RV* chip, backlight is supposedly linear\n")); 506 prop_dictionary_get_bool(device_properties(&sc->sc_dev), 507 "backlight_level_reverted", &inverted); 508 if (inverted) { 509 DPRINTF(("nope, it's inverted\n")); 510 sc->sc_flags |= RFB_INV_BLIGHT; 511 } 512 } else 513 sc->sc_flags |= RFB_INV_BLIGHT; 514 515 /* 516 * XXX: to support true multihead, this must change. 517 */ 518 sc->sc_ndisplays = 1; 519 520 /* XXX: */ 521 if (!HAS_CRTC2(sc)) { 522 sc->sc_ndisplays = 1; 523 } 524 525 if (pci_mapreg_map(pa, RADEON_MAPREG_MMIO, PCI_MAPREG_TYPE_MEM, 0, 526 &sc->sc_regt, &sc->sc_regh, &sc->sc_regaddr, 527 &sc->sc_regsz) != 0) { 528 aprint_error("%s: unable to map registers!\n", XNAME(sc)); 529 goto error; 530 } 531 532 /* scratch register test... */ 533 if (radeonfb_scratch_test(sc, RADEON_BIOS_0_SCRATCH, 0x55555555) || 534 radeonfb_scratch_test(sc, RADEON_BIOS_0_SCRATCH, 0xaaaaaaaa)) { 535 aprint_error("%s: scratch register test failed!\n", XNAME(sc)); 536 goto error; 537 } 538 539 PRINTREG(RADEON_BIOS_4_SCRATCH); 540 PRINTREG(RADEON_FP_GEN_CNTL); 541 PRINTREG(RADEON_FP2_GEN_CNTL); 542 PRINTREG(RADEON_TMDS_CNTL); 543 PRINTREG(RADEON_TMDS_TRANSMITTER_CNTL); 544 PRINTREG(RADEON_TMDS_PLL_CNTL); 545 PRINTREG(RADEON_LVDS_GEN_CNTL); 546 PRINTREG(RADEON_FP_HORZ_STRETCH); 547 PRINTREG(RADEON_FP_VERT_STRETCH); 548 549 /* XXX: RV100 specific */ 550 PUT32(sc, RADEON_TMDS_PLL_CNTL, 0xa27); 551 552 PATCH32(sc, RADEON_TMDS_TRANSMITTER_CNTL, 553 RADEON_TMDS_TRANSMITTER_PLLEN, 554 RADEON_TMDS_TRANSMITTER_PLLEN | RADEON_TMDS_TRANSMITTER_PLLRST); 555 556 radeonfb_i2c_init(sc); 557 558 radeonfb_loadbios(sc, pa); 559 560 #ifdef RADEON_BIOS_INIT 561 if (radeonfb_bios_init(sc)) { 562 aprint_error("%s: BIOS inititialization failed\n", XNAME(sc)); 563 goto error; 564 } 565 #endif 566 567 if (radeonfb_getclocks(sc)) { 568 aprint_error("%s: Unable to get reference clocks from BIOS\n", 569 XNAME(sc)); 570 goto error; 571 } 572 573 if (radeonfb_gettmds(sc)) { 574 aprint_error("%s: Unable to identify TMDS PLL settings\n", 575 XNAME(sc)); 576 goto error; 577 } 578 579 aprint_verbose("%s: refclk = %d.%03d MHz, refdiv = %d " 580 "minpll = %d, maxpll = %d\n", XNAME(sc), 581 (int)sc->sc_refclk / 1000, (int)sc->sc_refclk % 1000, 582 (int)sc->sc_refdiv, (int)sc->sc_minpll, (int)sc->sc_maxpll); 583 584 radeonfb_getconnectors(sc); 585 586 radeonfb_set_fbloc(sc); 587 588 for (i = 0; radeonfb_limits[i].size; i++) { 589 if (sc->sc_memsz >= radeonfb_limits[i].size) { 590 sc->sc_maxx = radeonfb_limits[i].maxx; 591 sc->sc_maxy = radeonfb_limits[i].maxy; 592 sc->sc_maxbpp = radeonfb_limits[i].maxbpp; 593 /* framebuffer offset, start at a 4K page */ 594 sc->sc_fboffset = sc->sc_memsz / 595 radeonfb_limits[i].maxdisp; 596 /* 597 * we use the fbsize to figure out where we can store 598 * things like cursor data. 599 */ 600 sc->sc_fbsize = 601 ROUNDUP(ROUNDUP(sc->sc_maxx * sc->sc_maxbpp / 8 , 602 RADEON_STRIDEALIGN) * sc->sc_maxy, 603 4096); 604 break; 605 } 606 } 607 608 609 radeonfb_init_misc(sc); 610 radeonfb_init_palette(sc, 0); 611 if (HAS_CRTC2(sc)) 612 radeonfb_init_palette(sc, 1); 613 614 /* program the DAC wirings */ 615 for (i = 0; i < (HAS_CRTC2(sc) ? 2 : 1); i++) { 616 switch (sc->sc_ports[i].rp_dac_type) { 617 case RADEON_DAC_PRIMARY: 618 PATCH32(sc, RADEON_DAC_CNTL2, 619 i ? RADEON_DAC2_DAC_CLK_SEL : 0, 620 ~RADEON_DAC2_DAC_CLK_SEL); 621 break; 622 case RADEON_DAC_TVDAC: 623 /* we always use the TVDAC to drive a secondary analog 624 * CRT for now. if we ever support TV-out this will 625 * have to change. 626 */ 627 SET32(sc, RADEON_DAC_CNTL2, 628 RADEON_DAC2_DAC2_CLK_SEL); 629 PATCH32(sc, RADEON_DISP_HW_DEBUG, 630 i ? 0 : RADEON_CRT2_DISP1_SEL, 631 ~RADEON_CRT2_DISP1_SEL); 632 break; 633 } 634 } 635 PRINTREG(RADEON_DAC_CNTL2); 636 PRINTREG(RADEON_DISP_HW_DEBUG); 637 638 /* other DAC programming */ 639 v = GET32(sc, RADEON_DAC_CNTL); 640 v &= (RADEON_DAC_RANGE_CNTL_MASK | RADEON_DAC_BLANKING); 641 v |= RADEON_DAC_MASK_ALL | RADEON_DAC_8BIT_EN; 642 PUT32(sc, RADEON_DAC_CNTL, v); 643 PRINTREG(RADEON_DAC_CNTL); 644 645 /* XXX: this may need more investigation */ 646 PUT32(sc, RADEON_TV_DAC_CNTL, 0x00280203); 647 PRINTREG(RADEON_TV_DAC_CNTL); 648 649 /* enable TMDS */ 650 SET32(sc, RADEON_FP_GEN_CNTL, 651 RADEON_FP_TMDS_EN | 652 RADEON_FP_CRTC_DONT_SHADOW_VPAR | 653 RADEON_FP_CRTC_DONT_SHADOW_HEND); 654 CLR32(sc, RADEON_FP_GEN_CNTL, RADEON_FP_SEL_CRTC2); 655 if (HAS_CRTC2(sc)) 656 SET32(sc, RADEON_FP2_GEN_CNTL, RADEON_FP2_SRC_SEL_CRTC2); 657 658 /* 659 * we use bus_space_map instead of pci_mapreg, because we don't 660 * need the full aperature space. no point in wasting virtual 661 * address space we don't intend to use, right? 662 */ 663 if ((sc->sc_memsz < (4096 * 1024)) || 664 (pci_mapreg_info(sc->sc_pc, sc->sc_pt, RADEON_MAPREG_VRAM, 665 PCI_MAPREG_TYPE_MEM, &sc->sc_memaddr, &bsz, NULL) != 0) || 666 (bsz < sc->sc_memsz)) { 667 sc->sc_memsz = 0; 668 aprint_error("%s: Bad frame buffer configuration\n", 669 XNAME(sc)); 670 goto error; 671 } 672 673 /* 64 MB should be enough -- more just wastes map entries */ 674 if (sc->sc_memsz > (64 << 20)) 675 sc->sc_memsz = (64 << 20); 676 677 sc->sc_memt = pa->pa_memt; 678 if (bus_space_map(sc->sc_memt, sc->sc_memaddr, sc->sc_memsz, 679 BUS_SPACE_MAP_LINEAR, &sc->sc_memh) != 0) { 680 sc->sc_memsz = 0; 681 aprint_error("%s: Unable to map frame buffer\n", XNAME(sc)); 682 goto error; 683 } 684 685 aprint_normal("%s: %d MB aperture at 0x%08x, " 686 "%d KB registers at 0x%08x\n", XNAME(sc), 687 (int)sc->sc_memsz >> 20, (unsigned)sc->sc_memaddr, 688 (int)sc->sc_regsz >> 10, (unsigned)sc->sc_regaddr); 689 690 /* setup default video mode from devprop (allows PROM override) */ 691 sc->sc_defaultmode = radeonfb_default_mode; 692 if (prop_dictionary_get_cstring_nocopy(device_properties(&sc->sc_dev), 693 "videomode", &mptr)) { 694 695 strncpy(sc->sc_modebuf, mptr, sizeof(sc->sc_modebuf)); 696 sc->sc_defaultmode = sc->sc_modebuf; 697 } 698 699 /* initialize some basic display parameters */ 700 for (i = 0; i < sc->sc_ndisplays; i++) { 701 struct radeonfb_display *dp = &sc->sc_displays[i]; 702 struct rasops_info *ri; 703 long defattr; 704 struct wsemuldisplaydev_attach_args aa; 705 706 /* 707 * Figure out how many "displays" (desktops) we are going to 708 * support. If more than one, then each CRTC gets its own 709 * programming. 710 * 711 * XXX: this code needs to change to support mergedfb. 712 * XXX: would be nice to allow this to be overridden 713 */ 714 if (HAS_CRTC2(sc) && (sc->sc_ndisplays == 1)) { 715 DPRINTF(("dual crtcs!\n")); 716 dp->rd_ncrtcs = 2; 717 dp->rd_crtcs[0].rc_number = 0; 718 dp->rd_crtcs[1].rc_number = 1; 719 } else { 720 dp->rd_ncrtcs = 1; 721 dp->rd_crtcs[0].rc_number = i; 722 } 723 724 /* set up port pointer */ 725 for (j = 0; j < dp->rd_ncrtcs; j++) { 726 dp->rd_crtcs[j].rc_port = 727 &sc->sc_ports[dp->rd_crtcs[j].rc_number]; 728 } 729 730 dp->rd_softc = sc; 731 dp->rd_wsmode = WSDISPLAYIO_MODE_EMUL; 732 dp->rd_bg = WS_DEFAULT_BG; 733 #if 0 734 dp->rd_bpp = sc->sc_maxbpp; /* XXX: for now */ 735 #else 736 dp->rd_bpp = RADEONFB_DEFAULT_DEPTH; /* XXX */ 737 #endif 738 /* for text mode, we pick a resolution that won't 739 * require panning */ 740 radeonfb_pickres(dp, &dp->rd_virtx, &dp->rd_virty, 0); 741 742 aprint_normal("%s: display %d: " 743 "initial virtual resolution %dx%d at %d bpp\n", 744 XNAME(sc), i, dp->rd_virtx, dp->rd_virty, dp->rd_bpp); 745 746 /* now select the *video mode* that we will use */ 747 for (j = 0; j < dp->rd_ncrtcs; j++) { 748 const struct videomode *vmp; 749 vmp = radeonfb_port_mode(sc, dp->rd_crtcs[j].rc_port, 750 dp->rd_virtx, dp->rd_virty); 751 752 /* 753 * virtual resolution should be at least as high as 754 * physical 755 */ 756 if (dp->rd_virtx < vmp->hdisplay || 757 dp->rd_virty < vmp->vdisplay) { 758 dp->rd_virtx = vmp->hdisplay; 759 dp->rd_virty = vmp->vdisplay; 760 } 761 762 dp->rd_crtcs[j].rc_videomode = *vmp; 763 printf("%s: port %d: physical %dx%d %dHz\n", 764 XNAME(sc), j, vmp->hdisplay, vmp->vdisplay, 765 DIVIDE(DIVIDE(vmp->dot_clock * 1000, 766 vmp->htotal), vmp->vtotal)); 767 } 768 769 /* N.B.: radeon wants 64-byte aligned stride */ 770 dp->rd_stride = dp->rd_virtx * dp->rd_bpp / 8; 771 dp->rd_stride = ROUNDUP(dp->rd_stride, RADEON_STRIDEALIGN); 772 773 dp->rd_offset = sc->sc_fboffset * i; 774 dp->rd_fbptr = (vaddr_t)bus_space_vaddr(sc->sc_memt, 775 sc->sc_memh) + dp->rd_offset; 776 dp->rd_curoff = sc->sc_fbsize; 777 dp->rd_curptr = dp->rd_fbptr + dp->rd_curoff; 778 779 DPRINTF(("fpbtr = %p\n", (void *)dp->rd_fbptr)); 780 781 switch (dp->rd_bpp) { 782 case 8: 783 dp->rd_format = 2; 784 break; 785 case 32: 786 dp->rd_format = 6; 787 break; 788 default: 789 aprint_error("%s: bad depth %d\n", XNAME(sc), 790 dp->rd_bpp); 791 goto error; 792 } 793 794 printf("init engine\n"); 795 /* XXX: this seems suspicious - per display engine 796 initialization? */ 797 radeonfb_engine_init(dp); 798 799 /* copy the template into place */ 800 dp->rd_wsscreens_storage[0] = radeonfb_stdscreen; 801 dp->rd_wsscreens = dp->rd_wsscreens_storage; 802 803 /* and make up the list */ 804 dp->rd_wsscreenlist.nscreens = 1; 805 dp->rd_wsscreenlist.screens = 806 (const struct wsscreen_descr **)&dp->rd_wsscreens; 807 808 vcons_init(&dp->rd_vd, dp, dp->rd_wsscreens, 809 &radeonfb_accessops); 810 811 dp->rd_vd.init_screen = radeonfb_init_screen; 812 813 dp->rd_console = 1; 814 815 dp->rd_vscreen.scr_flags |= VCONS_SCREEN_IS_STATIC; 816 817 818 vcons_init_screen(&dp->rd_vd, &dp->rd_vscreen, 819 dp->rd_console, &defattr); 820 821 ri = &dp->rd_vscreen.scr_ri; 822 823 /* clear the screen */ 824 rasops_unpack_attr(defattr, &fg, &bg, &ul); 825 radeonfb_rectfill(dp, 0, 0, ri->ri_width, ri->ri_height, 826 ri->ri_devcmap[bg & 0xf]); 827 828 dp->rd_wsscreens->textops = &ri->ri_ops; 829 dp->rd_wsscreens->capabilities = ri->ri_caps; 830 dp->rd_wsscreens->nrows = ri->ri_rows; 831 dp->rd_wsscreens->ncols = ri->ri_cols; 832 833 #ifdef SPLASHSCREEN 834 dp->rd_splash.si_depth = ri->ri_depth; 835 dp->rd_splash.si_bits = ri->ri_bits; 836 dp->rd_splash.si_hwbits = ri->ri_hwbits; 837 dp->rd_splash.si_width = ri->ri_width; 838 dp->rd_splash.si_height = ri->ri_height; 839 dp->rd_splash.si_stride = ri->ri_stride; 840 dp->rd_splash.si_fillrect = NULL; 841 #endif 842 if (dp->rd_console) { 843 844 wsdisplay_cnattach(dp->rd_wsscreens, ri, 0, 0, 845 defattr); 846 #ifdef SPLASHSCREEN 847 splash_render(&dp->rd_splash, 848 SPLASH_F_CENTER|SPLASH_F_FILL); 849 #endif 850 851 #ifdef SPLASHSCREEN_PROGRESS 852 dp->rd_progress.sp_top = (dp->rd_virty / 8) * 7; 853 dp->rd_progress.sp_width = (dp->rd_virtx / 4) * 3; 854 dp->rd_progress.sp_left = (dp->rd_virtx - 855 dp->rd_progress.sp_width) / 2; 856 dp->rd_progress.sp_height = 20; 857 dp->rd_progress.sp_state = -1; 858 dp->rd_progress.sp_si = &dp->rd_splash; 859 splash_progress_init(&dp->rd_progress); 860 SCREEN_DISABLE_DRAWING(&dp->rd_vscreen); 861 #endif 862 863 } else { 864 865 /* 866 * since we're not the console we can postpone 867 * the rest until someone actually allocates a 868 * screen for us. but we do clear the screen 869 * at least. 870 */ 871 memset(ri->ri_bits, 0, 1024); 872 873 radeonfb_modeswitch(dp); 874 #ifdef SPLASHSCREEN 875 splash_render(&dp->rd_splash, 876 SPLASH_F_CENTER|SPLASH_F_FILL); 877 SCREEN_DISABLE_DRAWING(&dp->rd_vscreen); 878 #endif 879 } 880 881 aa.console = dp->rd_console; 882 aa.scrdata = &dp->rd_wsscreenlist; 883 aa.accessops = &radeonfb_accessops; 884 aa.accesscookie = &dp->rd_vd; 885 886 config_found(&sc->sc_dev, &aa, wsemuldisplaydevprint); 887 radeonfb_blank(dp, 0); 888 889 /* Initialise delayed lvds operations for backlight. */ 890 callout_init(&dp->rd_bl_lvds_co, 0); 891 callout_setfunc(&dp->rd_bl_lvds_co, 892 radeonfb_lvds_callout, dp); 893 } 894 895 config_found_ia(dev, "drm", aux, radeonfb_drm_print); 896 897 return; 898 899 error: 900 if (sc->sc_biossz) 901 free(sc->sc_bios, M_DEVBUF); 902 903 if (sc->sc_regsz) 904 bus_space_unmap(sc->sc_regt, sc->sc_regh, sc->sc_regsz); 905 906 if (sc->sc_memsz) 907 bus_space_unmap(sc->sc_memt, sc->sc_memh, sc->sc_memsz); 908 } 909 910 static int 911 radeonfb_drm_print(void *aux, const char *pnp) 912 { 913 if (pnp) 914 aprint_normal("drm at %s", pnp); 915 return (UNCONF); 916 } 917 918 int 919 radeonfb_ioctl(void *v, void *vs, 920 unsigned long cmd, void *d, int flag, struct lwp *l) 921 { 922 struct vcons_data *vd; 923 struct radeonfb_display *dp; 924 struct radeonfb_softc *sc; 925 struct wsdisplay_param *param; 926 927 vd = (struct vcons_data *)v; 928 dp = (struct radeonfb_display *)vd->cookie; 929 sc = dp->rd_softc; 930 931 switch (cmd) { 932 case WSDISPLAYIO_GTYPE: 933 *(unsigned *)d = WSDISPLAY_TYPE_PCIMISC; 934 return 0; 935 936 case WSDISPLAYIO_GINFO: 937 if (vd->active != NULL) { 938 struct wsdisplay_fbinfo *fb; 939 fb = (struct wsdisplay_fbinfo *)d; 940 fb->width = dp->rd_virtx; 941 fb->height = dp->rd_virty; 942 fb->depth = dp->rd_bpp; 943 fb->cmsize = 256; 944 return 0; 945 } else 946 return ENODEV; 947 case WSDISPLAYIO_GVIDEO: 948 if (radeonfb_isblank(dp)) 949 *(unsigned *)d = WSDISPLAYIO_VIDEO_OFF; 950 else 951 *(unsigned *)d = WSDISPLAYIO_VIDEO_ON; 952 return 0; 953 954 case WSDISPLAYIO_SVIDEO: 955 radeonfb_blank(dp, 956 (*(unsigned int *)d == WSDISPLAYIO_VIDEO_OFF)); 957 return 0; 958 959 case WSDISPLAYIO_GETCMAP: 960 #if 0 961 if (dp->rd_bpp == 8) 962 return radeonfb_getcmap(sc, 963 (struct wsdisplay_cmap *)d); 964 #endif 965 return EINVAL; 966 967 case WSDISPLAYIO_PUTCMAP: 968 #if 0 969 if (dp->rd_bpp == 8) 970 return radeonfb_putcmap(sc, 971 (struct wsdisplay_cmap *)d); 972 #endif 973 return EINVAL; 974 975 case WSDISPLAYIO_LINEBYTES: 976 *(unsigned *)d = dp->rd_stride; 977 return 0; 978 979 case WSDISPLAYIO_SMODE: 980 if (*(int *)d != dp->rd_wsmode) { 981 dp->rd_wsmode = *(int *)d; 982 if ((dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) && 983 (dp->rd_vd.active)) { 984 radeonfb_engine_init(dp); 985 radeonfb_modeswitch(dp); 986 vcons_redraw_screen(dp->rd_vd.active); 987 } 988 } 989 return 0; 990 991 case WSDISPLAYIO_GCURMAX: 992 ((struct wsdisplay_curpos *)d)->x = RADEON_CURSORMAXX; 993 ((struct wsdisplay_curpos *)d)->y = RADEON_CURSORMAXY; 994 return 0; 995 996 case WSDISPLAYIO_SCURSOR: 997 return radeonfb_set_cursor(dp, (struct wsdisplay_cursor *)d); 998 999 case WSDISPLAYIO_GCURSOR: 1000 return EPASSTHROUGH; 1001 1002 case WSDISPLAYIO_GCURPOS: 1003 ((struct wsdisplay_curpos *)d)->x = dp->rd_cursor.rc_pos.x; 1004 ((struct wsdisplay_curpos *)d)->y = dp->rd_cursor.rc_pos.y; 1005 return 0; 1006 1007 case WSDISPLAYIO_SCURPOS: 1008 return radeonfb_set_curpos(dp, (struct wsdisplay_curpos *)d); 1009 1010 case WSDISPLAYIO_SSPLASH: 1011 #if defined(SPLASHSCREEN) 1012 if (*(int *)d == 1) { 1013 SCREEN_DISABLE_DRAWING(&dp->rd_vscreen); 1014 splash_render(&dp->rd_splash, 1015 SPLASH_F_CENTER|SPLASH_F_FILL); 1016 } else 1017 SCREEN_ENABLE_DRAWING(&dp->rd_vscreen); 1018 return 0; 1019 #else 1020 return ENODEV; 1021 #endif 1022 case WSDISPLAYIO_SPROGRESS: 1023 #if defined(SPLASHSCREEN) && defined(SPLASHSCREEN_PROGRESS) 1024 dp->rd_progress.sp_force = 1; 1025 splash_progress_update(&dp->rd_progress); 1026 dp->rd_progress.sp_force = 0; 1027 return 0; 1028 #else 1029 return ENODEV; 1030 #endif 1031 case WSDISPLAYIO_GETPARAM: 1032 param = (struct wsdisplay_param *)d; 1033 if (param->param == WSDISPLAYIO_PARAM_BACKLIGHT) { 1034 param->min = 0; 1035 param->max = RADEONFB_BACKLIGHT_MAX; 1036 param->curval = radeonfb_get_backlight(dp); 1037 return 0; 1038 } 1039 return EPASSTHROUGH; 1040 1041 case WSDISPLAYIO_SETPARAM: 1042 param = (struct wsdisplay_param *)d; 1043 if (param->param == WSDISPLAYIO_PARAM_BACKLIGHT) { 1044 return radeonfb_set_backlight(dp, param->curval); 1045 } 1046 return EPASSTHROUGH; 1047 1048 /* PCI config read/write passthrough. */ 1049 case PCI_IOC_CFGREAD: 1050 case PCI_IOC_CFGWRITE: 1051 return (pci_devioctl(sc->sc_pc, sc->sc_pt, cmd, d, flag, l)); 1052 1053 default: 1054 return EPASSTHROUGH; 1055 } 1056 } 1057 1058 paddr_t 1059 radeonfb_mmap(void *v, void *vs, off_t offset, int prot) 1060 { 1061 struct vcons_data *vd; 1062 struct radeonfb_display *dp; 1063 struct radeonfb_softc *sc; 1064 #ifdef RADEONFB_MMAP_BARS 1065 struct lwp *me; 1066 #endif 1067 paddr_t pa; 1068 1069 vd = (struct vcons_data *)v; 1070 dp = (struct radeonfb_display *)vd->cookie; 1071 sc = dp->rd_softc; 1072 1073 /* XXX: note that we don't allow mapping of registers right now */ 1074 /* XXX: this means that the XFree86 radeon driver won't work */ 1075 1076 if ((offset >= 0) && (offset < (dp->rd_virty * dp->rd_stride))) { 1077 pa = bus_space_mmap(sc->sc_memt, 1078 sc->sc_memaddr + dp->rd_offset + offset, 0, 1079 prot, BUS_SPACE_MAP_LINEAR); 1080 return pa; 1081 } 1082 1083 #ifdef RADEONFB_MMAP_BARS 1084 /* 1085 * restrict all other mappings to processes with superuser privileges 1086 * or the kernel itself 1087 */ 1088 me = curlwp; 1089 if (me != NULL) { 1090 if (kauth_authorize_generic(me->l_cred, KAUTH_GENERIC_ISSUSER, 1091 NULL) != 0) { 1092 aprint_error_dev(&sc->sc_dev, "mmap() rejected.\n"); 1093 return -1; 1094 } 1095 } 1096 1097 if ((offset >= sc->sc_regaddr) && 1098 (offset < sc->sc_regaddr + sc->sc_regsz)) { 1099 return bus_space_mmap(sc->sc_regt, offset, 0, prot, 1100 BUS_SPACE_MAP_LINEAR); 1101 } 1102 1103 if ((offset >= sc->sc_memaddr) && 1104 (offset < sc->sc_memaddr + sc->sc_memsz)) { 1105 return bus_space_mmap(sc->sc_memt, offset, 0, prot, 1106 BUS_SPACE_MAP_LINEAR); 1107 } 1108 1109 #ifdef PCI_MAGIC_IO_RANGE 1110 /* allow mapping of IO space */ 1111 if ((offset >= PCI_MAGIC_IO_RANGE) && 1112 (offset < PCI_MAGIC_IO_RANGE + 0x10000)) { 1113 pa = bus_space_mmap(sc->sc_iot, offset - PCI_MAGIC_IO_RANGE, 1114 0, prot, 0); 1115 return pa; 1116 } 1117 #endif /* macppc */ 1118 1119 #endif /* RADEONFB_MMAP_BARS */ 1120 1121 return -1; 1122 } 1123 1124 static void 1125 radeonfb_loadbios(struct radeonfb_softc *sc, struct pci_attach_args *pa) 1126 { 1127 bus_space_tag_t romt; 1128 bus_space_handle_t romh, biosh; 1129 bus_size_t romsz; 1130 bus_addr_t ptr; 1131 1132 if (pci_mapreg_map(pa, PCI_MAPREG_ROM, PCI_MAPREG_TYPE_ROM, 1133 BUS_SPACE_MAP_PREFETCHABLE, &romt, &romh, NULL, &romsz) != 0) { 1134 aprint_verbose("%s: unable to map BIOS!\n", XNAME(sc)); 1135 return; 1136 } 1137 1138 pci_find_rom(pa, romt, romh, PCI_ROM_CODE_TYPE_X86, &biosh, 1139 &sc->sc_biossz); 1140 if (sc->sc_biossz == 0) { 1141 aprint_verbose("%s: Video BIOS not present\n", XNAME(sc)); 1142 return; 1143 } 1144 1145 sc->sc_bios = malloc(sc->sc_biossz, M_DEVBUF, M_WAITOK); 1146 bus_space_read_region_1(romt, biosh, 0, sc->sc_bios, sc->sc_biossz); 1147 1148 /* unmap the PCI expansion rom */ 1149 bus_space_unmap(romt, romh, romsz); 1150 1151 /* turn off rom decoder now */ 1152 pci_conf_write(pa->pa_pc, pa->pa_tag, PCI_MAPREG_ROM, 1153 pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_MAPREG_ROM) & 1154 ~PCI_MAPREG_ROM_ENABLE); 1155 1156 ptr = GETBIOS16(sc, 0x48); 1157 if ((GETBIOS32(sc, ptr + 4) == 0x41544f4d /* "ATOM" */) || 1158 (GETBIOS32(sc, ptr + 4) == 0x4d4f5441 /* "MOTA" */)) { 1159 sc->sc_flags |= RFB_ATOM; 1160 } 1161 1162 aprint_verbose("%s: Found %d KB %s BIOS\n", XNAME(sc), 1163 (unsigned)sc->sc_biossz >> 10, IS_ATOM(sc) ? "ATOM" : "Legacy"); 1164 } 1165 1166 1167 uint32_t 1168 radeonfb_get32(struct radeonfb_softc *sc, uint32_t reg) 1169 { 1170 1171 return bus_space_read_4(sc->sc_regt, sc->sc_regh, reg); 1172 } 1173 1174 void 1175 radeonfb_put32(struct radeonfb_softc *sc, uint32_t reg, uint32_t val) 1176 { 1177 1178 bus_space_write_4(sc->sc_regt, sc->sc_regh, reg, val); 1179 } 1180 1181 void 1182 radeonfb_mask32(struct radeonfb_softc *sc, uint32_t reg, 1183 uint32_t andmask, uint32_t ormask) 1184 { 1185 int s; 1186 uint32_t val; 1187 1188 s = splhigh(); 1189 val = radeonfb_get32(sc, reg); 1190 val = (val & andmask) | ormask; 1191 radeonfb_put32(sc, reg, val); 1192 splx(s); 1193 } 1194 1195 uint32_t 1196 radeonfb_getindex(struct radeonfb_softc *sc, uint32_t idx) 1197 { 1198 int s; 1199 uint32_t val; 1200 1201 s = splhigh(); 1202 radeonfb_put32(sc, RADEON_MM_INDEX, idx); 1203 val = radeonfb_get32(sc, RADEON_MM_DATA); 1204 splx(s); 1205 1206 return (val); 1207 } 1208 1209 void 1210 radeonfb_putindex(struct radeonfb_softc *sc, uint32_t idx, uint32_t val) 1211 { 1212 int s; 1213 1214 s = splhigh(); 1215 radeonfb_put32(sc, RADEON_MM_INDEX, idx); 1216 radeonfb_put32(sc, RADEON_MM_DATA, val); 1217 splx(s); 1218 } 1219 1220 void 1221 radeonfb_maskindex(struct radeonfb_softc *sc, uint32_t idx, 1222 uint32_t andmask, uint32_t ormask) 1223 { 1224 int s; 1225 uint32_t val; 1226 1227 s = splhigh(); 1228 radeonfb_put32(sc, RADEON_MM_INDEX, idx); 1229 val = radeonfb_get32(sc, RADEON_MM_DATA); 1230 val = (val & andmask) | ormask; 1231 radeonfb_put32(sc, RADEON_MM_DATA, val); 1232 splx(s); 1233 } 1234 1235 uint32_t 1236 radeonfb_getpll(struct radeonfb_softc *sc, uint32_t idx) 1237 { 1238 int s; 1239 uint32_t val; 1240 1241 s = splhigh(); 1242 radeonfb_put32(sc, RADEON_CLOCK_CNTL_INDEX, idx & 0x3f); 1243 val = radeonfb_get32(sc, RADEON_CLOCK_CNTL_DATA); 1244 if (HAS_R300CG(sc)) 1245 radeonfb_r300cg_workaround(sc); 1246 splx(s); 1247 1248 return (val); 1249 } 1250 1251 void 1252 radeonfb_putpll(struct radeonfb_softc *sc, uint32_t idx, uint32_t val) 1253 { 1254 int s; 1255 1256 s = splhigh(); 1257 radeonfb_put32(sc, RADEON_CLOCK_CNTL_INDEX, (idx & 0x3f) | 1258 RADEON_PLL_WR_EN); 1259 radeonfb_put32(sc, RADEON_CLOCK_CNTL_DATA, val); 1260 radeonfb_put32(sc, RADEON_CLOCK_CNTL_INDEX, 0); 1261 splx(s); 1262 } 1263 1264 void 1265 radeonfb_maskpll(struct radeonfb_softc *sc, uint32_t idx, 1266 uint32_t andmask, uint32_t ormask) 1267 { 1268 int s; 1269 uint32_t val; 1270 1271 s = splhigh(); 1272 radeonfb_put32(sc, RADEON_CLOCK_CNTL_INDEX, (idx & 0x3f) | 1273 RADEON_PLL_WR_EN); 1274 val = radeonfb_get32(sc, RADEON_CLOCK_CNTL_DATA); 1275 val = (val & andmask) | ormask; 1276 radeonfb_put32(sc, RADEON_CLOCK_CNTL_DATA, val); 1277 radeonfb_put32(sc, RADEON_CLOCK_CNTL_INDEX, 0); 1278 splx(s); 1279 } 1280 1281 int 1282 radeonfb_scratch_test(struct radeonfb_softc *sc, int reg, uint32_t v) 1283 { 1284 uint32_t saved; 1285 1286 saved = GET32(sc, reg); 1287 PUT32(sc, reg, v); 1288 if (GET32(sc, reg) != v) { 1289 return -1; 1290 } 1291 PUT32(sc, reg, saved); 1292 return 0; 1293 } 1294 1295 uintmax_t 1296 radeonfb_getprop_num(struct radeonfb_softc *sc, const char *name, 1297 uintmax_t defval) 1298 { 1299 prop_number_t pn; 1300 pn = prop_dictionary_get(device_properties(&sc->sc_dev), name); 1301 if (pn == NULL) { 1302 return defval; 1303 } 1304 KASSERT(prop_object_type(pn) == PROP_TYPE_NUMBER); 1305 return (prop_number_integer_value(pn)); 1306 } 1307 1308 int 1309 radeonfb_getclocks(struct radeonfb_softc *sc) 1310 { 1311 bus_addr_t ptr; 1312 int refclk = 0; 1313 int refdiv = 0; 1314 int minpll = 0; 1315 int maxpll = 0; 1316 1317 /* load initial property values if port/board provides them */ 1318 refclk = radeonfb_getprop_num(sc, "refclk", 0) & 0xffff; 1319 refdiv = radeonfb_getprop_num(sc, "refdiv", 0) & 0xffff; 1320 minpll = radeonfb_getprop_num(sc, "minpll", 0) & 0xffffffffU; 1321 maxpll = radeonfb_getprop_num(sc, "maxpll", 0) & 0xffffffffU; 1322 1323 if (refclk && refdiv && minpll && maxpll) 1324 goto dontprobe; 1325 1326 if (!sc->sc_biossz) { 1327 /* no BIOS */ 1328 aprint_verbose("%s: No video BIOS, using default clocks\n", 1329 XNAME(sc)); 1330 if (IS_IGP(sc)) 1331 refclk = refclk ? refclk : 1432; 1332 else 1333 refclk = refclk ? refclk : 2700; 1334 refdiv = refdiv ? refdiv : 12; 1335 minpll = minpll ? minpll : 12500; 1336 maxpll = maxpll ? maxpll : 35000; 1337 } else if (IS_ATOM(sc)) { 1338 /* ATOM BIOS */ 1339 ptr = GETBIOS16(sc, 0x48); 1340 ptr = GETBIOS16(sc, ptr + 32); /* aka MasterDataStart */ 1341 ptr = GETBIOS16(sc, ptr + 12); /* pll info block */ 1342 refclk = refclk ? refclk : GETBIOS16(sc, ptr + 82); 1343 minpll = minpll ? minpll : GETBIOS16(sc, ptr + 78); 1344 maxpll = maxpll ? maxpll : GETBIOS16(sc, ptr + 32); 1345 /* 1346 * ATOM BIOS doesn't supply a reference divider, so we 1347 * have to probe for it. 1348 */ 1349 if (refdiv < 2) 1350 refdiv = GETPLL(sc, RADEON_PPLL_REF_DIV) & 1351 RADEON_PPLL_REF_DIV_MASK; 1352 /* 1353 * if probe is zero, just assume one that should work 1354 * for most parts 1355 */ 1356 if (refdiv < 2) 1357 refdiv = 12; 1358 1359 } else { 1360 /* Legacy BIOS */ 1361 ptr = GETBIOS16(sc, 0x48); 1362 ptr = GETBIOS16(sc, ptr + 0x30); 1363 refclk = refclk ? refclk : GETBIOS16(sc, ptr + 0x0E); 1364 refdiv = refdiv ? refdiv : GETBIOS16(sc, ptr + 0x10); 1365 minpll = minpll ? minpll : GETBIOS32(sc, ptr + 0x12); 1366 maxpll = maxpll ? maxpll : GETBIOS32(sc, ptr + 0x16); 1367 } 1368 1369 1370 dontprobe: 1371 sc->sc_refclk = refclk * 10; 1372 sc->sc_refdiv = refdiv; 1373 sc->sc_minpll = minpll * 10; 1374 sc->sc_maxpll = maxpll * 10; 1375 return 0; 1376 } 1377 1378 int 1379 radeonfb_calc_dividers(struct radeonfb_softc *sc, uint32_t dotclock, 1380 uint32_t *postdivbit, uint32_t *feedbackdiv) 1381 { 1382 int i; 1383 uint32_t outfreq; 1384 int div; 1385 1386 DPRINTF(("dot clock: %u\n", dotclock)); 1387 for (i = 0; (div = radeonfb_dividers[i].divider) != 0; i++) { 1388 outfreq = div * dotclock; 1389 if ((outfreq >= sc->sc_minpll) && 1390 (outfreq <= sc->sc_maxpll)) { 1391 DPRINTF(("outfreq: %u\n", outfreq)); 1392 *postdivbit = 1393 ((uint32_t)radeonfb_dividers[i].mask << 16); 1394 DPRINTF(("post divider: %d (mask %x)\n", div, 1395 *postdivbit)); 1396 break; 1397 } 1398 } 1399 1400 if (div == 0) 1401 return 1; 1402 1403 *feedbackdiv = DIVIDE(sc->sc_refdiv * outfreq, sc->sc_refclk); 1404 DPRINTF(("feedback divider: %d\n", *feedbackdiv)); 1405 return 0; 1406 } 1407 1408 #if 0 1409 #ifdef RADEON_DEBUG 1410 static void 1411 dump_buffer(const char *pfx, void *buffer, unsigned int size) 1412 { 1413 char asc[17]; 1414 unsigned ptr = (unsigned)buffer; 1415 char *start = (char *)(ptr & ~0xf); 1416 char *end = (char *)(ptr + size); 1417 1418 end = (char *)(((unsigned)end + 0xf) & ~0xf); 1419 1420 if (pfx == NULL) { 1421 pfx = ""; 1422 } 1423 1424 while (start < end) { 1425 unsigned offset = (unsigned)start & 0xf; 1426 if (offset == 0) { 1427 printf("%s%x: ", pfx, (unsigned)start); 1428 } 1429 if (((unsigned)start < ptr) || 1430 ((unsigned)start >= (ptr + size))) { 1431 printf(" "); 1432 asc[offset] = ' '; 1433 } else { 1434 printf("%02x", *(unsigned char *)start); 1435 if ((*start >= ' ') && (*start <= '~')) { 1436 asc[offset] = *start; 1437 } else { 1438 asc[offset] = '.'; 1439 } 1440 } 1441 asc[offset + 1] = 0; 1442 if (offset % 2) { 1443 printf(" "); 1444 } 1445 if (offset == 15) { 1446 printf(" %s\n", asc); 1447 } 1448 start++; 1449 } 1450 } 1451 #endif 1452 #endif 1453 1454 int 1455 radeonfb_getconnectors(struct radeonfb_softc *sc) 1456 { 1457 int i; 1458 int found = 0; 1459 1460 for (i = 0; i < 2; i++) { 1461 sc->sc_ports[i].rp_mon_type = RADEON_MT_UNKNOWN; 1462 sc->sc_ports[i].rp_ddc_type = RADEON_DDC_NONE; 1463 sc->sc_ports[i].rp_dac_type = RADEON_DAC_UNKNOWN; 1464 sc->sc_ports[i].rp_conn_type = RADEON_CONN_NONE; 1465 sc->sc_ports[i].rp_tmds_type = RADEON_TMDS_UNKNOWN; 1466 } 1467 1468 /* 1469 * This logic is borrowed from Xorg's radeon driver. 1470 */ 1471 if (!sc->sc_biossz) 1472 goto nobios; 1473 1474 if (IS_ATOM(sc)) { 1475 /* not done yet */ 1476 } else { 1477 uint16_t ptr; 1478 int port = 0; 1479 1480 ptr = GETBIOS16(sc, 0x48); 1481 ptr = GETBIOS16(sc, ptr + 0x50); 1482 for (i = 1; i < 4; i++) { 1483 uint16_t entry; 1484 uint8_t conn, ddc, dac, tmds; 1485 1486 /* 1487 * Parse the connector table. From reading the code, 1488 * it appears to made up of 16-bit entries for each 1489 * connector. The 16-bits are defined as: 1490 * 1491 * bits 12-15 - connector type (0 == end of table) 1492 * bits 8-11 - DDC type 1493 * bits 5-7 - ??? 1494 * bit 4 - TMDS type (1 = EXT, 0 = INT) 1495 * bits 1-3 - ??? 1496 * bit 0 - DAC, 1 = TVDAC, 0 = primary 1497 */ 1498 if (!GETBIOS8(sc, ptr + i * 2) && i > 1) 1499 break; 1500 entry = GETBIOS16(sc, ptr + i * 2); 1501 1502 conn = (entry >> 12) & 0xf; 1503 ddc = (entry >> 8) & 0xf; 1504 dac = (entry & 0x1) ? RADEON_DAC_TVDAC : 1505 RADEON_DAC_PRIMARY; 1506 tmds = ((entry >> 4) & 0x1) ? RADEON_TMDS_EXT : 1507 RADEON_TMDS_INT; 1508 1509 if (conn == RADEON_CONN_NONE) 1510 continue; /* no connector */ 1511 1512 if ((found > 0) && 1513 (sc->sc_ports[port].rp_ddc_type == ddc)) { 1514 /* duplicate entry for same connector */ 1515 continue; 1516 } 1517 1518 /* internal DDC_DVI port gets priority */ 1519 if ((ddc == RADEON_DDC_DVI) || (port == 1)) 1520 port = 0; 1521 else 1522 port = 1; 1523 1524 sc->sc_ports[port].rp_ddc_type = 1525 ddc > RADEON_DDC_CRT2 ? RADEON_DDC_NONE : ddc; 1526 sc->sc_ports[port].rp_dac_type = dac; 1527 sc->sc_ports[port].rp_conn_type = 1528 min(conn, RADEON_CONN_UNSUPPORTED) ; 1529 1530 sc->sc_ports[port].rp_tmds_type = tmds; 1531 1532 if ((conn != RADEON_CONN_DVI_I) && 1533 (conn != RADEON_CONN_DVI_D) && 1534 (tmds == RADEON_TMDS_INT)) 1535 sc->sc_ports[port].rp_tmds_type = 1536 RADEON_TMDS_UNKNOWN; 1537 1538 found += (port + 1); 1539 } 1540 } 1541 1542 nobios: 1543 if (!found) { 1544 DPRINTF(("No connector info in BIOS!\n")); 1545 /* default, port 0 = internal TMDS, port 1 = CRT */ 1546 sc->sc_ports[0].rp_mon_type = RADEON_MT_UNKNOWN; 1547 sc->sc_ports[0].rp_ddc_type = RADEON_DDC_DVI; 1548 sc->sc_ports[0].rp_dac_type = RADEON_DAC_TVDAC; 1549 sc->sc_ports[0].rp_conn_type = RADEON_CONN_DVI_D; 1550 sc->sc_ports[0].rp_tmds_type = RADEON_TMDS_INT; 1551 1552 sc->sc_ports[1].rp_mon_type = RADEON_MT_UNKNOWN; 1553 sc->sc_ports[1].rp_ddc_type = RADEON_DDC_VGA; 1554 sc->sc_ports[1].rp_dac_type = RADEON_DAC_PRIMARY; 1555 sc->sc_ports[1].rp_conn_type = RADEON_CONN_CRT; 1556 sc->sc_ports[1].rp_tmds_type = RADEON_TMDS_EXT; 1557 } 1558 1559 /* 1560 * Fixup for RS300/RS350/RS400 chips, that lack a primary DAC. 1561 * these chips should use TVDAC for the VGA port. 1562 */ 1563 if (HAS_SDAC(sc)) { 1564 if (sc->sc_ports[0].rp_conn_type == RADEON_CONN_CRT) { 1565 sc->sc_ports[0].rp_dac_type = RADEON_DAC_TVDAC; 1566 sc->sc_ports[1].rp_dac_type = RADEON_DAC_PRIMARY; 1567 } else { 1568 sc->sc_ports[1].rp_dac_type = RADEON_DAC_TVDAC; 1569 sc->sc_ports[0].rp_dac_type = RADEON_DAC_PRIMARY; 1570 } 1571 } else if (!HAS_CRTC2(sc)) { 1572 sc->sc_ports[0].rp_dac_type = RADEON_DAC_PRIMARY; 1573 } 1574 1575 for (i = 0; i < 2; i++) { 1576 char edid[128]; 1577 uint8_t ddc; 1578 struct edid_info *eip = &sc->sc_ports[i].rp_edid; 1579 prop_data_t edid_data; 1580 1581 DPRINTF(("Port #%d:\n", i)); 1582 DPRINTF((" conn = %d\n", sc->sc_ports[i].rp_conn_type)); 1583 DPRINTF((" ddc = %d\n", sc->sc_ports[i].rp_ddc_type)); 1584 DPRINTF((" dac = %d\n", sc->sc_ports[i].rp_dac_type)); 1585 DPRINTF((" tmds = %d\n", sc->sc_ports[i].rp_tmds_type)); 1586 1587 sc->sc_ports[i].rp_edid_valid = 0; 1588 /* first look for static EDID data */ 1589 if ((edid_data = prop_dictionary_get(device_properties( 1590 &sc->sc_dev), "EDID")) != NULL) { 1591 1592 aprint_normal_dev(&sc->sc_dev, "using static EDID\n"); 1593 memcpy(edid, prop_data_data_nocopy(edid_data), 128); 1594 if (edid_parse(edid, eip) == 0) { 1595 1596 sc->sc_ports[i].rp_edid_valid = 1; 1597 } 1598 } 1599 /* if we didn't find any we'll try to talk to the monitor */ 1600 if (sc->sc_ports[i].rp_edid_valid != 1) { 1601 1602 ddc = sc->sc_ports[i].rp_ddc_type; 1603 if (ddc != RADEON_DDC_NONE) { 1604 if ((radeonfb_i2c_read_edid(sc, ddc, edid) 1605 == 0) && (edid_parse(edid, eip) == 0)) { 1606 1607 sc->sc_ports[i].rp_edid_valid = 1; 1608 edid_print(eip); 1609 } 1610 } 1611 } 1612 } 1613 1614 return found; 1615 } 1616 1617 int 1618 radeonfb_gettmds(struct radeonfb_softc *sc) 1619 { 1620 int i; 1621 1622 if (!sc->sc_biossz) { 1623 goto nobios; 1624 } 1625 1626 if (IS_ATOM(sc)) { 1627 /* XXX: not done yet */ 1628 } else { 1629 uint16_t ptr; 1630 int n; 1631 1632 ptr = GETBIOS16(sc, 0x48); 1633 ptr = GETBIOS16(sc, ptr + 0x34); 1634 DPRINTF(("DFP table revision %d\n", GETBIOS8(sc, ptr))); 1635 if (GETBIOS8(sc, ptr) == 3) { 1636 /* revision three table */ 1637 n = GETBIOS8(sc, ptr + 5) + 1; 1638 n = min(n, 4); 1639 1640 memset(sc->sc_tmds_pll, 0, sizeof (sc->sc_tmds_pll)); 1641 for (i = 0; i < n; i++) { 1642 sc->sc_tmds_pll[i].rtp_pll = GETBIOS32(sc, 1643 ptr + i * 10 + 8); 1644 sc->sc_tmds_pll[i].rtp_freq = GETBIOS16(sc, 1645 ptr + i * 10 + 0x10); 1646 DPRINTF(("TMDS_PLL dot clock %d pll %x\n", 1647 sc->sc_tmds_pll[i].rtp_freq, 1648 sc->sc_tmds_pll[i].rtp_pll)); 1649 } 1650 return 0; 1651 } 1652 } 1653 1654 nobios: 1655 DPRINTF(("no suitable DFP table present\n")); 1656 for (i = 0; 1657 i < sizeof (radeonfb_tmds_pll) / sizeof (radeonfb_tmds_pll[0]); 1658 i++) { 1659 int j; 1660 1661 if (radeonfb_tmds_pll[i].family != sc->sc_family) 1662 continue; 1663 1664 for (j = 0; j < 4; j++) { 1665 sc->sc_tmds_pll[j] = radeonfb_tmds_pll[i].plls[j]; 1666 DPRINTF(("TMDS_PLL dot clock %d pll %x\n", 1667 sc->sc_tmds_pll[j].rtp_freq, 1668 sc->sc_tmds_pll[j].rtp_pll)); 1669 } 1670 return 0; 1671 } 1672 1673 return -1; 1674 } 1675 1676 const struct videomode * 1677 radeonfb_modelookup(const char *name) 1678 { 1679 int i; 1680 1681 for (i = 0; i < videomode_count; i++) 1682 if (!strcmp(name, videomode_list[i].name)) 1683 return &videomode_list[i]; 1684 1685 return NULL; 1686 } 1687 1688 void 1689 radeonfb_pllwriteupdate(struct radeonfb_softc *sc, int crtc) 1690 { 1691 if (crtc) { 1692 while (GETPLL(sc, RADEON_P2PLL_REF_DIV) & 1693 RADEON_P2PLL_ATOMIC_UPDATE_R); 1694 SETPLL(sc, RADEON_P2PLL_REF_DIV, RADEON_P2PLL_ATOMIC_UPDATE_W); 1695 } else { 1696 while (GETPLL(sc, RADEON_PPLL_REF_DIV) & 1697 RADEON_PPLL_ATOMIC_UPDATE_R); 1698 SETPLL(sc, RADEON_PPLL_REF_DIV, RADEON_PPLL_ATOMIC_UPDATE_W); 1699 } 1700 } 1701 1702 void 1703 radeonfb_pllwaitatomicread(struct radeonfb_softc *sc, int crtc) 1704 { 1705 int i; 1706 1707 for (i = 10000; i; i--) { 1708 if (crtc) { 1709 if (GETPLL(sc, RADEON_P2PLL_REF_DIV) & 1710 RADEON_P2PLL_ATOMIC_UPDATE_R) 1711 break; 1712 } else { 1713 if (GETPLL(sc, RADEON_PPLL_REF_DIV) & 1714 RADEON_PPLL_ATOMIC_UPDATE_R) 1715 break; 1716 } 1717 } 1718 } 1719 1720 void 1721 radeonfb_program_vclk(struct radeonfb_softc *sc, int dotclock, int crtc) 1722 { 1723 uint32_t pbit = 0; 1724 uint32_t feed = 0; 1725 uint32_t data; 1726 #if 1 1727 int i; 1728 #endif 1729 1730 radeonfb_calc_dividers(sc, dotclock, &pbit, &feed); 1731 1732 if (crtc == 0) { 1733 1734 /* XXXX: mobility workaround missing */ 1735 /* XXXX: R300 stuff missing */ 1736 1737 PATCHPLL(sc, RADEON_VCLK_ECP_CNTL, 1738 RADEON_VCLK_SRC_SEL_CPUCLK, 1739 ~RADEON_VCLK_SRC_SEL_MASK); 1740 1741 /* put vclk into reset, use atomic updates */ 1742 SETPLL(sc, RADEON_PPLL_CNTL, 1743 RADEON_PPLL_REFCLK_SEL | 1744 RADEON_PPLL_FBCLK_SEL | 1745 RADEON_PPLL_RESET | 1746 RADEON_PPLL_ATOMIC_UPDATE_EN | 1747 RADEON_PPLL_VGA_ATOMIC_UPDATE_EN); 1748 1749 /* select clock 3 */ 1750 #if 0 1751 PATCH32(sc, RADEON_CLOCK_CNTL_INDEX, RADEON_PLL_DIV_SEL, 1752 ~RADEON_PLL_DIV_SEL); 1753 #else 1754 PATCH32(sc, RADEON_CLOCK_CNTL_INDEX, 0, 1755 ~RADEON_PLL_DIV_SEL); 1756 #endif 1757 1758 /* XXX: R300 family -- program divider differently? */ 1759 1760 /* program reference divider */ 1761 PATCHPLL(sc, RADEON_PPLL_REF_DIV, sc->sc_refdiv, 1762 ~RADEON_PPLL_REF_DIV_MASK); 1763 PRINTPLL(RADEON_PPLL_REF_DIV); 1764 1765 #if 0 1766 data = GETPLL(sc, RADEON_PPLL_DIV_3); 1767 data &= ~(RADEON_PPLL_FB3_DIV_MASK | 1768 RADEON_PPLL_POST3_DIV_MASK); 1769 data |= pbit; 1770 data |= (feed & RADEON_PPLL_FB3_DIV_MASK); 1771 PUTPLL(sc, RADEON_PPLL_DIV_3, data); 1772 #else 1773 for (i = 0; i < 4; i++) { 1774 } 1775 #endif 1776 1777 /* use the atomic update */ 1778 radeonfb_pllwriteupdate(sc, crtc); 1779 1780 /* and wait for it to complete */ 1781 radeonfb_pllwaitatomicread(sc, crtc); 1782 1783 /* program HTOTAL (why?) */ 1784 PUTPLL(sc, RADEON_HTOTAL_CNTL, 0); 1785 1786 /* drop reset */ 1787 CLRPLL(sc, RADEON_PPLL_CNTL, 1788 RADEON_PPLL_RESET | RADEON_PPLL_SLEEP | 1789 RADEON_PPLL_ATOMIC_UPDATE_EN | 1790 RADEON_PPLL_VGA_ATOMIC_UPDATE_EN); 1791 1792 PRINTPLL(RADEON_PPLL_CNTL); 1793 1794 /* give clock time to lock */ 1795 delay(50000); 1796 1797 PATCHPLL(sc, RADEON_VCLK_ECP_CNTL, 1798 RADEON_VCLK_SRC_SEL_PPLLCLK, 1799 ~RADEON_VCLK_SRC_SEL_MASK); 1800 1801 } else { 1802 1803 PATCHPLL(sc, RADEON_PIXCLKS_CNTL, 1804 RADEON_PIX2CLK_SRC_SEL_CPUCLK, 1805 ~RADEON_PIX2CLK_SRC_SEL_MASK); 1806 1807 /* put vclk into reset, use atomic updates */ 1808 SETPLL(sc, RADEON_P2PLL_CNTL, 1809 RADEON_P2PLL_RESET | 1810 RADEON_P2PLL_ATOMIC_UPDATE_EN | 1811 RADEON_P2PLL_VGA_ATOMIC_UPDATE_EN); 1812 1813 /* XXX: R300 family -- program divider differently? */ 1814 1815 /* program reference divider */ 1816 PATCHPLL(sc, RADEON_P2PLL_REF_DIV, sc->sc_refdiv, 1817 ~RADEON_P2PLL_REF_DIV_MASK); 1818 1819 /* program feedback and post dividers */ 1820 data = GETPLL(sc, RADEON_P2PLL_DIV_0); 1821 data &= ~(RADEON_P2PLL_FB0_DIV_MASK | 1822 RADEON_P2PLL_POST0_DIV_MASK); 1823 data |= pbit; 1824 data |= (feed & RADEON_P2PLL_FB0_DIV_MASK); 1825 PUTPLL(sc, RADEON_P2PLL_DIV_0, data); 1826 1827 /* use the atomic update */ 1828 radeonfb_pllwriteupdate(sc, crtc); 1829 1830 /* and wait for it to complete */ 1831 radeonfb_pllwaitatomicread(sc, crtc); 1832 1833 /* program HTOTAL (why?) */ 1834 PUTPLL(sc, RADEON_HTOTAL2_CNTL, 0); 1835 1836 /* drop reset */ 1837 CLRPLL(sc, RADEON_P2PLL_CNTL, 1838 RADEON_P2PLL_RESET | RADEON_P2PLL_SLEEP | 1839 RADEON_P2PLL_ATOMIC_UPDATE_EN | 1840 RADEON_P2PLL_VGA_ATOMIC_UPDATE_EN); 1841 1842 /* allow time for clock to lock */ 1843 delay(50000); 1844 1845 PATCHPLL(sc, RADEON_PIXCLKS_CNTL, 1846 RADEON_PIX2CLK_SRC_SEL_P2PLLCLK, 1847 ~RADEON_PIX2CLK_SRC_SEL_MASK); 1848 } 1849 PRINTREG(RADEON_CRTC_MORE_CNTL); 1850 } 1851 1852 void 1853 radeonfb_modeswitch(struct radeonfb_display *dp) 1854 { 1855 struct radeonfb_softc *sc = dp->rd_softc; 1856 int i; 1857 1858 /* blank the display while we switch modes */ 1859 //radeonfb_blank(dp, 1); 1860 1861 #if 0 1862 SET32(sc, RADEON_CRTC_EXT_CNTL, 1863 RADEON_CRTC_VSYNC_DIS | RADEON_CRTC_HSYNC_DIS | 1864 RADEON_CRTC_DISPLAY_DIS /* | RADEON_CRTC_DISP_REQ_EN_B */); 1865 #endif 1866 1867 /* these registers might get in the way... */ 1868 PUT32(sc, RADEON_OVR_CLR, 0); 1869 PUT32(sc, RADEON_OVR_WID_LEFT_RIGHT, 0); 1870 PUT32(sc, RADEON_OVR_WID_TOP_BOTTOM, 0); 1871 PUT32(sc, RADEON_OV0_SCALE_CNTL, 0); 1872 PUT32(sc, RADEON_SUBPIC_CNTL, 0); 1873 PUT32(sc, RADEON_VIPH_CONTROL, 0); 1874 PUT32(sc, RADEON_I2C_CNTL_1, 0); 1875 PUT32(sc, RADEON_GEN_INT_CNTL, 0); 1876 PUT32(sc, RADEON_CAP0_TRIG_CNTL, 0); 1877 PUT32(sc, RADEON_CAP1_TRIG_CNTL, 0); 1878 PUT32(sc, RADEON_SURFACE_CNTL, 0); 1879 1880 for (i = 0; i < dp->rd_ncrtcs; i++) 1881 radeonfb_setcrtc(dp, i); 1882 1883 /* activate the display */ 1884 //radeonfb_blank(dp, 0); 1885 } 1886 1887 void 1888 radeonfb_setcrtc(struct radeonfb_display *dp, int index) 1889 { 1890 int crtc; 1891 struct videomode *mode; 1892 struct radeonfb_softc *sc; 1893 struct radeonfb_crtc *cp; 1894 uint32_t v; 1895 uint32_t gencntl; 1896 uint32_t htotaldisp; 1897 uint32_t hsyncstrt; 1898 uint32_t vtotaldisp; 1899 uint32_t vsyncstrt; 1900 uint32_t fphsyncstrt; 1901 uint32_t fpvsyncstrt; 1902 uint32_t fphtotaldisp; 1903 uint32_t fpvtotaldisp; 1904 uint32_t pitch; 1905 1906 sc = dp->rd_softc; 1907 cp = &dp->rd_crtcs[index]; 1908 crtc = cp->rc_number; 1909 mode = &cp->rc_videomode; 1910 1911 #if 1 1912 pitch = (((dp->rd_virtx * dp->rd_bpp) + ((dp->rd_bpp * 8) - 1)) / 1913 (dp->rd_bpp * 8)); 1914 #else 1915 pitch = (((sc->sc_maxx * sc->sc_maxbpp) + ((sc->sc_maxbpp * 8) - 1)) / 1916 (sc->sc_maxbpp * 8)); 1917 #endif 1918 //pitch = pitch | (pitch << 16); 1919 1920 switch (crtc) { 1921 case 0: 1922 gencntl = RADEON_CRTC_GEN_CNTL; 1923 htotaldisp = RADEON_CRTC_H_TOTAL_DISP; 1924 hsyncstrt = RADEON_CRTC_H_SYNC_STRT_WID; 1925 vtotaldisp = RADEON_CRTC_V_TOTAL_DISP; 1926 vsyncstrt = RADEON_CRTC_V_SYNC_STRT_WID; 1927 fpvsyncstrt = RADEON_FP_V_SYNC_STRT_WID; 1928 fphsyncstrt = RADEON_FP_H_SYNC_STRT_WID; 1929 fpvtotaldisp = RADEON_FP_CRTC_V_TOTAL_DISP; 1930 fphtotaldisp = RADEON_FP_CRTC_H_TOTAL_DISP; 1931 break; 1932 case 1: 1933 gencntl = RADEON_CRTC2_GEN_CNTL; 1934 htotaldisp = RADEON_CRTC2_H_TOTAL_DISP; 1935 hsyncstrt = RADEON_CRTC2_H_SYNC_STRT_WID; 1936 vtotaldisp = RADEON_CRTC2_V_TOTAL_DISP; 1937 vsyncstrt = RADEON_CRTC2_V_SYNC_STRT_WID; 1938 fpvsyncstrt = RADEON_FP_V2_SYNC_STRT_WID; 1939 fphsyncstrt = RADEON_FP_H2_SYNC_STRT_WID; 1940 fpvtotaldisp = RADEON_FP_CRTC2_V_TOTAL_DISP; 1941 fphtotaldisp = RADEON_FP_CRTC2_H_TOTAL_DISP; 1942 break; 1943 default: 1944 panic("Bad CRTC!"); 1945 break; 1946 } 1947 1948 /* 1949 * CRTC_GEN_CNTL - depth, accelerator mode, etc. 1950 */ 1951 /* only bother with 32bpp and 8bpp */ 1952 v = dp->rd_format << RADEON_CRTC_PIX_WIDTH_SHIFT; 1953 1954 if (crtc == 1) { 1955 v |= RADEON_CRTC2_CRT2_ON | RADEON_CRTC2_EN; 1956 } else { 1957 v |= RADEON_CRTC_EXT_DISP_EN | RADEON_CRTC_EN; 1958 } 1959 1960 if (mode->flags & VID_DBLSCAN) 1961 v |= RADEON_CRTC2_DBL_SCAN_EN; 1962 1963 if (mode->flags & VID_INTERLACE) 1964 v |= RADEON_CRTC2_INTERLACE_EN; 1965 1966 if (mode->flags & VID_CSYNC) { 1967 v |= RADEON_CRTC2_CSYNC_EN; 1968 if (crtc == 1) 1969 v |= RADEON_CRTC2_VSYNC_TRISTAT; 1970 } 1971 1972 PUT32(sc, gencntl, v); 1973 DPRINTF(("CRTC%s_GEN_CNTL = %08x\n", crtc ? "2" : "", v)); 1974 1975 /* 1976 * CRTC_EXT_CNTL - preserve disable flags, set ATI linear and EXT_CNT 1977 */ 1978 v = GET32(sc, RADEON_CRTC_EXT_CNTL); 1979 if (crtc == 0) { 1980 v &= (RADEON_CRTC_VSYNC_DIS | RADEON_CRTC_HSYNC_DIS | 1981 RADEON_CRTC_DISPLAY_DIS); 1982 v |= RADEON_XCRT_CNT_EN | RADEON_VGA_ATI_LINEAR; 1983 if (mode->flags & VID_CSYNC) 1984 v |= RADEON_CRTC_VSYNC_TRISTAT; 1985 } 1986 /* unconditional turn on CRT, in case first CRTC is DFP */ 1987 v |= RADEON_CRTC_CRT_ON; 1988 PUT32(sc, RADEON_CRTC_EXT_CNTL, v); 1989 PRINTREG(RADEON_CRTC_EXT_CNTL); 1990 1991 /* 1992 * H_TOTAL_DISP 1993 */ 1994 v = ((mode->hdisplay / 8) - 1) << 16; 1995 v |= (mode->htotal / 8) - 1; 1996 PUT32(sc, htotaldisp, v); 1997 DPRINTF(("CRTC%s_H_TOTAL_DISP = %08x\n", crtc ? "2" : "", v)); 1998 PUT32(sc, fphtotaldisp, v); 1999 DPRINTF(("FP_H%s_TOTAL_DISP = %08x\n", crtc ? "2" : "", v)); 2000 2001 /* 2002 * H_SYNC_STRT_WID 2003 */ 2004 v = (((mode->hsync_end - mode->hsync_start) / 8) << 16); 2005 v |= mode->hsync_start; 2006 if (mode->flags & VID_NHSYNC) 2007 v |= RADEON_CRTC_H_SYNC_POL; 2008 PUT32(sc, hsyncstrt, v); 2009 DPRINTF(("CRTC%s_H_SYNC_STRT_WID = %08x\n", crtc ? "2" : "", v)); 2010 PUT32(sc, fphsyncstrt, v); 2011 DPRINTF(("FP_H%s_SYNC_STRT_WID = %08x\n", crtc ? "2" : "", v)); 2012 2013 /* 2014 * V_TOTAL_DISP 2015 */ 2016 v = ((mode->vdisplay - 1) << 16); 2017 v |= (mode->vtotal - 1); 2018 PUT32(sc, vtotaldisp, v); 2019 DPRINTF(("CRTC%s_V_TOTAL_DISP = %08x\n", crtc ? "2" : "", v)); 2020 PUT32(sc, fpvtotaldisp, v); 2021 DPRINTF(("FP_V%s_TOTAL_DISP = %08x\n", crtc ? "2" : "", v)); 2022 2023 /* 2024 * V_SYNC_STRT_WID 2025 */ 2026 v = ((mode->vsync_end - mode->vsync_start) << 16); 2027 v |= (mode->vsync_start - 1); 2028 if (mode->flags & VID_NVSYNC) 2029 v |= RADEON_CRTC_V_SYNC_POL; 2030 PUT32(sc, vsyncstrt, v); 2031 DPRINTF(("CRTC%s_V_SYNC_STRT_WID = %08x\n", crtc ? "2" : "", v)); 2032 PUT32(sc, fpvsyncstrt, v); 2033 DPRINTF(("FP_V%s_SYNC_STRT_WID = %08x\n", crtc ? "2" : "", v)); 2034 2035 radeonfb_program_vclk(sc, mode->dot_clock, crtc); 2036 2037 switch (crtc) { 2038 case 0: 2039 PUT32(sc, RADEON_CRTC_OFFSET, 0); 2040 PUT32(sc, RADEON_CRTC_OFFSET_CNTL, 0); 2041 PUT32(sc, RADEON_CRTC_PITCH, pitch); 2042 CLR32(sc, RADEON_DISP_MERGE_CNTL, RADEON_DISP_RGB_OFFSET_EN); 2043 2044 CLR32(sc, RADEON_CRTC_EXT_CNTL, 2045 RADEON_CRTC_VSYNC_DIS | RADEON_CRTC_HSYNC_DIS | 2046 RADEON_CRTC_DISPLAY_DIS /* | RADEON_CRTC_DISP_REQ_EN_B */); 2047 CLR32(sc, RADEON_CRTC_GEN_CNTL, RADEON_CRTC_DISP_REQ_EN_B); 2048 PRINTREG(RADEON_CRTC_EXT_CNTL); 2049 PRINTREG(RADEON_CRTC_GEN_CNTL); 2050 PRINTREG(RADEON_CLOCK_CNTL_INDEX); 2051 break; 2052 2053 case 1: 2054 PUT32(sc, RADEON_CRTC2_OFFSET, 0); 2055 PUT32(sc, RADEON_CRTC2_OFFSET_CNTL, 0); 2056 PUT32(sc, RADEON_CRTC2_PITCH, pitch); 2057 CLR32(sc, RADEON_DISP2_MERGE_CNTL, RADEON_DISP2_RGB_OFFSET_EN); 2058 CLR32(sc, RADEON_CRTC2_GEN_CNTL, 2059 RADEON_CRTC2_VSYNC_DIS | 2060 RADEON_CRTC2_HSYNC_DIS | 2061 RADEON_CRTC2_DISP_DIS | RADEON_CRTC2_DISP_REQ_EN_B); 2062 PRINTREG(RADEON_CRTC2_GEN_CNTL); 2063 break; 2064 } 2065 } 2066 2067 int 2068 radeonfb_isblank(struct radeonfb_display *dp) 2069 { 2070 uint32_t reg, mask; 2071 2072 if (dp->rd_crtcs[0].rc_number) { 2073 reg = RADEON_CRTC2_GEN_CNTL; 2074 mask = RADEON_CRTC2_DISP_DIS; 2075 } else { 2076 reg = RADEON_CRTC_EXT_CNTL; 2077 mask = RADEON_CRTC_DISPLAY_DIS; 2078 } 2079 return ((GET32(dp->rd_softc, reg) & mask) ? 1 : 0); 2080 } 2081 2082 void 2083 radeonfb_blank(struct radeonfb_display *dp, int blank) 2084 { 2085 struct radeonfb_softc *sc = dp->rd_softc; 2086 uint32_t reg, mask; 2087 uint32_t fpreg, fpval; 2088 int i; 2089 2090 for (i = 0; i < dp->rd_ncrtcs; i++) { 2091 2092 if (dp->rd_crtcs[i].rc_number) { 2093 reg = RADEON_CRTC2_GEN_CNTL; 2094 mask = RADEON_CRTC2_DISP_DIS; 2095 fpreg = RADEON_FP2_GEN_CNTL; 2096 fpval = RADEON_FP2_ON; 2097 } else { 2098 reg = RADEON_CRTC_EXT_CNTL; 2099 mask = RADEON_CRTC_DISPLAY_DIS; 2100 fpreg = RADEON_FP_GEN_CNTL; 2101 fpval = RADEON_FP_FPON; 2102 } 2103 2104 if (blank) { 2105 SET32(sc, reg, mask); 2106 CLR32(sc, fpreg, fpval); 2107 } else { 2108 CLR32(sc, reg, mask); 2109 SET32(sc, fpreg, fpval); 2110 } 2111 } 2112 PRINTREG(RADEON_FP_GEN_CNTL); 2113 PRINTREG(RADEON_FP2_GEN_CNTL); 2114 } 2115 2116 void 2117 radeonfb_init_screen(void *cookie, struct vcons_screen *scr, int existing, 2118 long *defattr) 2119 { 2120 struct radeonfb_display *dp = cookie; 2121 struct rasops_info *ri = &scr->scr_ri; 2122 2123 /* initialize font subsystem */ 2124 wsfont_init(); 2125 2126 DPRINTF(("init screen called, existing %d\n", existing)); 2127 2128 ri->ri_depth = dp->rd_bpp; 2129 ri->ri_width = dp->rd_virtx; 2130 ri->ri_height = dp->rd_virty; 2131 ri->ri_stride = dp->rd_stride; 2132 ri->ri_flg = RI_CENTER; 2133 ri->ri_bits = (void *)dp->rd_fbptr; 2134 2135 /* XXX: 32 bpp only */ 2136 /* this is rgb in "big-endian order..." */ 2137 ri->ri_rnum = 8; 2138 ri->ri_gnum = 8; 2139 ri->ri_bnum = 8; 2140 ri->ri_rpos = 16; 2141 ri->ri_gpos = 8; 2142 ri->ri_bpos = 0; 2143 2144 if (existing) { 2145 ri->ri_flg |= RI_CLEAR; 2146 2147 /* start a modeswitch now */ 2148 radeonfb_modeswitch(dp); 2149 } 2150 2151 /* 2152 * XXX: font selection should be based on properties, with some 2153 * normal/reasonable default. 2154 */ 2155 ri->ri_caps = WSSCREEN_WSCOLORS; 2156 2157 /* initialize and look for an initial font */ 2158 rasops_init(ri, dp->rd_virty/8, dp->rd_virtx/8); 2159 2160 rasops_reconfig(ri, dp->rd_virty / ri->ri_font->fontheight, 2161 dp->rd_virtx / ri->ri_font->fontwidth); 2162 2163 /* enable acceleration */ 2164 ri->ri_ops.copyrows = radeonfb_copyrows; 2165 ri->ri_ops.copycols = radeonfb_copycols; 2166 ri->ri_ops.eraserows = radeonfb_eraserows; 2167 ri->ri_ops.erasecols = radeonfb_erasecols; 2168 ri->ri_ops.allocattr = radeonfb_allocattr; 2169 if (!IS_R300(dp->rd_softc)) { 2170 ri->ri_ops.putchar = radeonfb_putchar; 2171 } 2172 ri->ri_ops.cursor = radeonfb_cursor; 2173 } 2174 2175 void 2176 radeonfb_set_fbloc(struct radeonfb_softc *sc) 2177 { 2178 uint32_t gen, ext, gen2 = 0; 2179 uint32_t agploc, aperbase, apersize, mcfbloc; 2180 2181 gen = GET32(sc, RADEON_CRTC_GEN_CNTL); 2182 ext = GET32(sc, RADEON_CRTC_EXT_CNTL); 2183 agploc = GET32(sc, RADEON_MC_AGP_LOCATION); 2184 aperbase = GET32(sc, RADEON_CONFIG_APER_0_BASE); 2185 apersize = GET32(sc, RADEON_CONFIG_APER_SIZE); 2186 2187 PUT32(sc, RADEON_CRTC_GEN_CNTL, gen | RADEON_CRTC_DISP_REQ_EN_B); 2188 PUT32(sc, RADEON_CRTC_EXT_CNTL, ext | RADEON_CRTC_DISPLAY_DIS); 2189 //PUT32(sc, RADEON_CRTC_GEN_CNTL, gen | RADEON_CRTC_DISPLAY_DIS); 2190 //PUT32(sc, RADEON_CRTC_EXT_CNTL, ext | RADEON_CRTC_DISP_REQ_EN_B); 2191 2192 if (HAS_CRTC2(sc)) { 2193 gen2 = GET32(sc, RADEON_CRTC2_GEN_CNTL); 2194 PUT32(sc, RADEON_CRTC2_GEN_CNTL, 2195 gen2 | RADEON_CRTC2_DISP_REQ_EN_B); 2196 } 2197 2198 delay(100000); 2199 2200 mcfbloc = (aperbase >> 16) | 2201 ((aperbase + (apersize - 1)) & 0xffff0000); 2202 2203 sc->sc_aperbase = (mcfbloc & 0xffff) << 16; 2204 sc->sc_memsz = apersize; 2205 2206 if (((agploc & 0xffff) << 16) != 2207 ((mcfbloc & 0xffff0000U) + 0x10000)) { 2208 agploc = mcfbloc & 0xffff0000U; 2209 agploc |= ((agploc + 0x10000) >> 16); 2210 } 2211 2212 PUT32(sc, RADEON_HOST_PATH_CNTL, 0); 2213 2214 PUT32(sc, RADEON_MC_FB_LOCATION, mcfbloc); 2215 PUT32(sc, RADEON_MC_AGP_LOCATION, agploc); 2216 2217 DPRINTF(("aperbase = %u\n", aperbase)); 2218 PRINTREG(RADEON_MC_FB_LOCATION); 2219 PRINTREG(RADEON_MC_AGP_LOCATION); 2220 2221 PUT32(sc, RADEON_DISPLAY_BASE_ADDR, sc->sc_aperbase); 2222 2223 if (HAS_CRTC2(sc)) 2224 PUT32(sc, RADEON_DISPLAY2_BASE_ADDR, sc->sc_aperbase); 2225 2226 PUT32(sc, RADEON_OV0_BASE_ADDR, sc->sc_aperbase); 2227 2228 #if 0 2229 /* XXX: what is this AGP garbage? :-) */ 2230 PUT32(sc, RADEON_AGP_CNTL, 0x00100000); 2231 #endif 2232 2233 delay(100000); 2234 2235 PUT32(sc, RADEON_CRTC_GEN_CNTL, gen); 2236 PUT32(sc, RADEON_CRTC_EXT_CNTL, ext); 2237 2238 if (HAS_CRTC2(sc)) 2239 PUT32(sc, RADEON_CRTC2_GEN_CNTL, gen2); 2240 } 2241 2242 void 2243 radeonfb_init_misc(struct radeonfb_softc *sc) 2244 { 2245 PUT32(sc, RADEON_BUS_CNTL, 2246 RADEON_BUS_MASTER_DIS | 2247 RADEON_BUS_PREFETCH_MODE_ACT | 2248 RADEON_BUS_PCI_READ_RETRY_EN | 2249 RADEON_BUS_PCI_WRT_RETRY_EN | 2250 (3 << RADEON_BUS_RETRY_WS_SHIFT) | 2251 RADEON_BUS_MSTR_RD_MULT | 2252 RADEON_BUS_MSTR_RD_LINE | 2253 RADEON_BUS_RD_DISCARD_EN | 2254 RADEON_BUS_MSTR_DISCONNECT_EN | 2255 RADEON_BUS_READ_BURST); 2256 2257 PUT32(sc, RADEON_BUS_CNTL1, 0xf0); 2258 /* PUT32(sc, RADEON_SEPROM_CNTL1, 0x09ff0000); */ 2259 PUT32(sc, RADEON_FCP_CNTL, RADEON_FCP0_SRC_GND); 2260 PUT32(sc, RADEON_RBBM_CNTL, 2261 (3 << RADEON_RB_SETTLE_SHIFT) | 2262 (4 << RADEON_ABORTCLKS_HI_SHIFT) | 2263 (4 << RADEON_ABORTCLKS_CP_SHIFT) | 2264 (4 << RADEON_ABORTCLKS_CFIFO_SHIFT)); 2265 2266 /* XXX: figure out what these mean! */ 2267 PUT32(sc, RADEON_AGP_CNTL, 0x00100000); 2268 PUT32(sc, RADEON_HOST_PATH_CNTL, 0); 2269 //PUT32(sc, RADEON_DISP_MISC_CNTL, 0x5bb00400); 2270 2271 PUT32(sc, RADEON_GEN_INT_CNTL, 0); 2272 PUT32(sc, RADEON_GEN_INT_STATUS, GET32(sc, RADEON_GEN_INT_STATUS)); 2273 } 2274 2275 /* 2276 * This loads a linear color map for true color. 2277 */ 2278 void 2279 radeonfb_init_palette(struct radeonfb_softc *sc, int crtc) 2280 { 2281 int i; 2282 uint32_t vclk; 2283 2284 #define DAC_WIDTH ((1 << 10) - 1) 2285 #define CLUT_WIDTH ((1 << 8) - 1) 2286 #define CLUT_COLOR(i) ((i * DAC_WIDTH * 2 / CLUT_WIDTH + 1) / 2) 2287 2288 vclk = GETPLL(sc, RADEON_VCLK_ECP_CNTL); 2289 PUTPLL(sc, RADEON_VCLK_ECP_CNTL, vclk & ~RADEON_PIXCLK_DAC_ALWAYS_ONb); 2290 2291 if (crtc) 2292 SET32(sc, RADEON_DAC_CNTL2, RADEON_DAC2_PALETTE_ACC_CTL); 2293 else 2294 CLR32(sc, RADEON_DAC_CNTL2, RADEON_DAC2_PALETTE_ACC_CTL); 2295 2296 PUT32(sc, RADEON_PALETTE_INDEX, 0); 2297 for (i = 0; i <= CLUT_WIDTH; ++i) { 2298 PUT32(sc, RADEON_PALETTE_30_DATA, 2299 (CLUT_COLOR(i) << 10) | 2300 (CLUT_COLOR(i) << 20) | 2301 (CLUT_COLOR(i))); 2302 } 2303 2304 CLR32(sc, RADEON_DAC_CNTL2, RADEON_DAC2_PALETTE_ACC_CTL); 2305 PRINTREG(RADEON_DAC_CNTL2); 2306 2307 PUTPLL(sc, RADEON_VCLK_ECP_CNTL, vclk); 2308 } 2309 2310 /* 2311 * Bugs in some R300 hardware requires this when accessing CLOCK_CNTL_INDEX. 2312 */ 2313 void 2314 radeonfb_r300cg_workaround(struct radeonfb_softc *sc) 2315 { 2316 uint32_t tmp, save; 2317 2318 save = GET32(sc, RADEON_CLOCK_CNTL_INDEX); 2319 tmp = save & ~(0x3f | RADEON_PLL_WR_EN); 2320 PUT32(sc, RADEON_CLOCK_CNTL_INDEX, tmp); 2321 tmp = GET32(sc, RADEON_CLOCK_CNTL_DATA); 2322 PUT32(sc, RADEON_CLOCK_CNTL_INDEX, save); 2323 } 2324 2325 /* 2326 * Acceleration entry points. 2327 */ 2328 static void 2329 radeonfb_putchar(void *cookie, int row, int col, u_int c, long attr) 2330 { 2331 struct rasops_info *ri = cookie; 2332 struct vcons_screen *scr = ri->ri_hw; 2333 struct radeonfb_display *dp = scr->scr_cookie; 2334 uint32_t x, y, w, h; 2335 uint32_t bg, fg; 2336 uint8_t *data; 2337 2338 if (dp->rd_wsmode != WSDISPLAYIO_MODE_EMUL) 2339 return; 2340 2341 if (!CHAR_IN_FONT(c, ri->ri_font)) 2342 return; 2343 2344 w = ri->ri_font->fontwidth; 2345 h = ri->ri_font->fontheight; 2346 2347 bg = ri->ri_devcmap[(attr >> 16) & 0xf]; 2348 fg = ri->ri_devcmap[(attr >> 24) & 0xf]; 2349 2350 x = ri->ri_xorigin + col * w; 2351 y = ri->ri_yorigin + row * h; 2352 2353 if (c == 0x20) { 2354 radeonfb_rectfill(dp, x, y, w, h, bg); 2355 } else { 2356 data = (uint8_t *)ri->ri_font->data + 2357 (c - ri->ri_font->firstchar) * ri->ri_fontscale; 2358 2359 radeonfb_setup_mono(dp, x, y, w, h, fg, bg); 2360 radeonfb_feed_bytes(dp, ri->ri_fontscale, data); 2361 } 2362 } 2363 2364 static void 2365 radeonfb_eraserows(void *cookie, int row, int nrows, long fillattr) 2366 { 2367 struct rasops_info *ri = cookie; 2368 struct vcons_screen *scr = ri->ri_hw; 2369 struct radeonfb_display *dp = scr->scr_cookie; 2370 uint32_t x, y, w, h, fg, bg, ul; 2371 2372 /* XXX: check for full emulation mode? */ 2373 if (dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) { 2374 x = ri->ri_xorigin; 2375 y = ri->ri_yorigin + ri->ri_font->fontheight * row; 2376 w = ri->ri_emuwidth; 2377 h = ri->ri_font->fontheight * nrows; 2378 2379 rasops_unpack_attr(fillattr, &fg, &bg, &ul); 2380 radeonfb_rectfill(dp, x, y, w, h, ri->ri_devcmap[bg & 0xf]); 2381 } 2382 } 2383 2384 static void 2385 radeonfb_copyrows(void *cookie, int srcrow, int dstrow, int nrows) 2386 { 2387 struct rasops_info *ri = cookie; 2388 struct vcons_screen *scr = ri->ri_hw; 2389 struct radeonfb_display *dp = scr->scr_cookie; 2390 uint32_t x, ys, yd, w, h; 2391 2392 if (dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) { 2393 x = ri->ri_xorigin; 2394 ys = ri->ri_yorigin + ri->ri_font->fontheight * srcrow; 2395 yd = ri->ri_yorigin + ri->ri_font->fontheight * dstrow; 2396 w = ri->ri_emuwidth; 2397 h = ri->ri_font->fontheight * nrows; 2398 radeonfb_bitblt(dp, x, ys, x, yd, w, h, 2399 RADEON_ROP3_S, 0xffffffff); 2400 } 2401 } 2402 2403 static void 2404 radeonfb_copycols(void *cookie, int row, int srccol, int dstcol, int ncols) 2405 { 2406 struct rasops_info *ri = cookie; 2407 struct vcons_screen *scr = ri->ri_hw; 2408 struct radeonfb_display *dp = scr->scr_cookie; 2409 uint32_t xs, xd, y, w, h; 2410 2411 if (dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) { 2412 xs = ri->ri_xorigin + ri->ri_font->fontwidth * srccol; 2413 xd = ri->ri_xorigin + ri->ri_font->fontwidth * dstcol; 2414 y = ri->ri_yorigin + ri->ri_font->fontheight * row; 2415 w = ri->ri_font->fontwidth * ncols; 2416 h = ri->ri_font->fontheight; 2417 radeonfb_bitblt(dp, xs, y, xd, y, w, h, 2418 RADEON_ROP3_S, 0xffffffff); 2419 } 2420 } 2421 2422 static void 2423 radeonfb_erasecols(void *cookie, int row, int startcol, int ncols, 2424 long fillattr) 2425 { 2426 struct rasops_info *ri = cookie; 2427 struct vcons_screen *scr = ri->ri_hw; 2428 struct radeonfb_display *dp = scr->scr_cookie; 2429 uint32_t x, y, w, h, fg, bg, ul; 2430 2431 if (dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) { 2432 x = ri->ri_xorigin + ri->ri_font->fontwidth * startcol; 2433 y = ri->ri_yorigin + ri->ri_font->fontheight * row; 2434 w = ri->ri_font->fontwidth * ncols; 2435 h = ri->ri_font->fontheight; 2436 2437 rasops_unpack_attr(fillattr, &fg, &bg, &ul); 2438 radeonfb_rectfill(dp, x, y, w, h, ri->ri_devcmap[bg & 0xf]); 2439 } 2440 } 2441 2442 static void 2443 radeonfb_cursor(void *cookie, int on, int row, int col) 2444 { 2445 struct rasops_info *ri = cookie; 2446 struct vcons_screen *scr = ri->ri_hw; 2447 struct radeonfb_display *dp = scr->scr_cookie; 2448 int x, y, wi, he; 2449 2450 wi = ri->ri_font->fontwidth; 2451 he = ri->ri_font->fontheight; 2452 2453 if (dp->rd_wsmode == WSDISPLAYIO_MODE_EMUL) { 2454 x = ri->ri_ccol * wi + ri->ri_xorigin; 2455 y = ri->ri_crow * he + ri->ri_yorigin; 2456 /* first turn off the old cursor */ 2457 if (ri->ri_flg & RI_CURSOR) { 2458 radeonfb_bitblt(dp, x, y, x, y, wi, he, 2459 RADEON_ROP3_Dn, 0xffffffff); 2460 ri->ri_flg &= ~RI_CURSOR; 2461 } 2462 ri->ri_crow = row; 2463 ri->ri_ccol = col; 2464 /* then (possibly) turn on the new one */ 2465 if (on) { 2466 x = ri->ri_ccol * wi + ri->ri_xorigin; 2467 y = ri->ri_crow * he + ri->ri_yorigin; 2468 radeonfb_bitblt(dp, x, y, x, y, wi, he, 2469 RADEON_ROP3_Dn, 0xffffffff); 2470 ri->ri_flg |= RI_CURSOR; 2471 } 2472 } else { 2473 scr->scr_ri.ri_crow = row; 2474 scr->scr_ri.ri_ccol = col; 2475 scr->scr_ri.ri_flg &= ~RI_CURSOR; 2476 } 2477 } 2478 2479 static int 2480 radeonfb_allocattr(void *cookie, int fg, int bg, int flags, long *attrp) 2481 { 2482 if ((fg == 0) && (bg == 0)) { 2483 fg = WS_DEFAULT_FG; 2484 bg = WS_DEFAULT_BG; 2485 } 2486 *attrp = ((fg & 0xf) << 24) | ((bg & 0xf) << 16) | (flags & 0xff) << 8; 2487 return 0; 2488 } 2489 2490 /* 2491 * Underlying acceleration support. 2492 */ 2493 static void 2494 radeonfb_setup_mono(struct radeonfb_display *dp, int xd, int yd, int width, 2495 int height, uint32_t fg, uint32_t bg) 2496 { 2497 struct radeonfb_softc *sc = dp->rd_softc; 2498 uint32_t gmc; 2499 uint32_t padded_width = (width+7) & 0xfff8; 2500 uint32_t topleft, bottomright; 2501 2502 gmc = dp->rd_format << RADEON_GMC_DST_DATATYPE_SHIFT; 2503 2504 if (width != padded_width) { 2505 2506 radeonfb_wait_fifo(sc, 2); 2507 topleft = ((yd << 16) & 0x1fff0000) | (xd & 0x1fff); 2508 bottomright = (((yd + height) << 16) & 0x1fff0000) | 2509 ((xd + width) & 0x1fff); 2510 PUT32(sc, RADEON_SC_TOP_LEFT, topleft); 2511 PUT32(sc, RADEON_SC_BOTTOM_RIGHT, bottomright); 2512 } 2513 2514 radeonfb_wait_fifo(sc, 5); 2515 2516 PUT32(sc, RADEON_DP_GUI_MASTER_CNTL, 2517 RADEON_GMC_BRUSH_NONE | 2518 RADEON_GMC_SRC_DATATYPE_MONO_FG_BG | 2519 //RADEON_GMC_BYTE_LSB_TO_MSB | 2520 RADEON_GMC_DST_CLIPPING | 2521 RADEON_ROP3_S | 2522 RADEON_DP_SRC_SOURCE_HOST_DATA | 2523 RADEON_GMC_CLR_CMP_CNTL_DIS | 2524 RADEON_GMC_WR_MSK_DIS | 2525 gmc); 2526 2527 PUT32(sc, RADEON_DP_SRC_FRGD_CLR, fg); 2528 PUT32(sc, RADEON_DP_SRC_BKGD_CLR, bg); 2529 2530 PUT32(sc, RADEON_DST_X_Y, (xd << 16) | yd); 2531 PUT32(sc, RADEON_DST_WIDTH_HEIGHT, (padded_width << 16) | height); 2532 2533 } 2534 2535 static void 2536 radeonfb_feed_bytes(struct radeonfb_display *dp, int count, uint8_t *data) 2537 { 2538 struct radeonfb_softc *sc = dp->rd_softc; 2539 int i; 2540 uint32_t latch = 0; 2541 int shift = 0; 2542 2543 for (i = 0; i < count; i++) { 2544 latch |= (data[i] << shift); 2545 if (shift == 24) { 2546 radeonfb_wait_fifo(sc, 1); 2547 PUT32(sc, RADEON_HOST_DATA0, latch); 2548 latch = 0; 2549 shift = 0; 2550 } else 2551 shift += 8; 2552 } 2553 if (shift != 0) { 2554 radeonfb_wait_fifo(sc, 1); 2555 PUT32(sc, RADEON_HOST_DATA0, latch); 2556 } 2557 radeonfb_unclip(sc); 2558 } 2559 2560 static void 2561 radeonfb_rectfill(struct radeonfb_display *dp, int dstx, int dsty, 2562 int width, int height, uint32_t color) 2563 { 2564 struct radeonfb_softc *sc = dp->rd_softc; 2565 uint32_t gmc; 2566 2567 gmc = dp->rd_format << RADEON_GMC_DST_DATATYPE_SHIFT; 2568 2569 radeonfb_wait_fifo(sc, 6); 2570 2571 PUT32(sc, RADEON_DP_GUI_MASTER_CNTL, 2572 RADEON_GMC_BRUSH_SOLID_COLOR | 2573 RADEON_GMC_SRC_DATATYPE_COLOR | 2574 RADEON_GMC_CLR_CMP_CNTL_DIS | 2575 RADEON_ROP3_P | gmc); 2576 2577 PUT32(sc, RADEON_DP_BRUSH_FRGD_CLR, color); 2578 PUT32(sc, RADEON_DP_WRITE_MASK, 0xffffffff); 2579 PUT32(sc, RADEON_DP_CNTL, 2580 RADEON_DST_X_LEFT_TO_RIGHT | 2581 RADEON_DST_Y_TOP_TO_BOTTOM); 2582 PUT32(sc, RADEON_DST_Y_X, (dsty << 16) | dstx); 2583 PUT32(sc, RADEON_DST_WIDTH_HEIGHT, (width << 16) | (height)); 2584 2585 /* 2586 * XXX: we don't wait for the fifo to empty -- that would slow 2587 * things down! The linux radeonfb driver waits, but xfree doesn't 2588 */ 2589 /* XXX: for now we do, to make it safe for direct drawing */ 2590 radeonfb_engine_idle(sc); 2591 } 2592 2593 static void 2594 radeonfb_bitblt(struct radeonfb_display *dp, int srcx, int srcy, 2595 int dstx, int dsty, int width, int height, int rop, uint32_t mask) 2596 { 2597 struct radeonfb_softc *sc = dp->rd_softc; 2598 uint32_t gmc; 2599 uint32_t dir; 2600 2601 if (dsty < srcy) { 2602 dir = RADEON_DST_Y_TOP_TO_BOTTOM; 2603 } else { 2604 srcy += height - 1; 2605 dsty += height - 1; 2606 dir = 0; 2607 } 2608 if (dstx < srcx) { 2609 dir |= RADEON_DST_X_LEFT_TO_RIGHT; 2610 } else { 2611 srcx += width - 1; 2612 dstx += width - 1; 2613 } 2614 2615 gmc = dp->rd_format << RADEON_GMC_DST_DATATYPE_SHIFT; 2616 2617 radeonfb_wait_fifo(sc, 6); 2618 2619 PUT32(sc, RADEON_DP_GUI_MASTER_CNTL, 2620 //RADEON_GMC_SRC_CLIPPING | 2621 RADEON_GMC_BRUSH_SOLID_COLOR | 2622 RADEON_GMC_SRC_DATATYPE_COLOR | 2623 RADEON_GMC_CLR_CMP_CNTL_DIS | 2624 RADEON_DP_SRC_SOURCE_MEMORY | 2625 rop | gmc); 2626 2627 PUT32(sc, RADEON_DP_WRITE_MASK, mask); 2628 PUT32(sc, RADEON_DP_CNTL, dir); 2629 PUT32(sc, RADEON_SRC_Y_X, (srcy << 16) | srcx); 2630 PUT32(sc, RADEON_DST_Y_X, (dsty << 16) | dstx); 2631 PUT32(sc, RADEON_DST_WIDTH_HEIGHT, (width << 16) | (height)); 2632 2633 /* 2634 * XXX: we don't wait for the fifo to empty -- that would slow 2635 * things down! The linux radeonfb driver waits, but xfree doesn't 2636 */ 2637 /* XXX: for now we do, to make it safe for direct drawing */ 2638 radeonfb_engine_idle(sc); 2639 } 2640 2641 static void 2642 radeonfb_engine_idle(struct radeonfb_softc *sc) 2643 { 2644 int i; 2645 2646 radeonfb_wait_fifo(sc, 64); 2647 for (i = RADEON_TIMEOUT; i; i--) { 2648 if ((GET32(sc, RADEON_RBBM_STATUS) & 2649 RADEON_RBBM_ACTIVE) == 0) { 2650 radeonfb_engine_flush(sc); 2651 break; 2652 } 2653 } 2654 } 2655 2656 static void 2657 radeonfb_wait_fifo(struct radeonfb_softc *sc, int n) 2658 { 2659 int i; 2660 2661 for (i = RADEON_TIMEOUT; i; i--) { 2662 if ((GET32(sc, RADEON_RBBM_STATUS) & 2663 RADEON_RBBM_FIFOCNT_MASK) >= n) 2664 return; 2665 } 2666 #ifdef DIAGNOSTIC 2667 if (!i) 2668 printf("%s: timed out waiting for fifo (%x)\n", 2669 XNAME(sc), GET32(sc, RADEON_RBBM_STATUS)); 2670 #endif 2671 } 2672 2673 static void 2674 radeonfb_engine_flush(struct radeonfb_softc *sc) 2675 { 2676 int i; 2677 SET32(sc, RADEON_RB2D_DSTCACHE_CTLSTAT, RADEON_RB2D_DC_FLUSH_ALL); 2678 for (i = RADEON_TIMEOUT; i; i--) { 2679 if ((GET32(sc, RADEON_RB2D_DSTCACHE_CTLSTAT) & 2680 RADEON_RB2D_DC_BUSY) == 0) 2681 break; 2682 } 2683 #ifdef DIAGNOSTIC 2684 if (!i) 2685 printf("%s: engine flush timed out!\n", XNAME(sc)); 2686 #endif 2687 } 2688 2689 static inline void 2690 radeonfb_unclip(struct radeonfb_softc *sc) 2691 { 2692 2693 radeonfb_wait_fifo(sc, 2); 2694 PUT32(sc, RADEON_SC_TOP_LEFT, 0); 2695 PUT32(sc, RADEON_SC_BOTTOM_RIGHT, 0x1fff1fff); 2696 } 2697 2698 static void 2699 radeonfb_engine_init(struct radeonfb_display *dp) 2700 { 2701 struct radeonfb_softc *sc = dp->rd_softc; 2702 uint32_t pitch; 2703 2704 /* no 3D */ 2705 PUT32(sc, RADEON_RB3D_CNTL, 0); 2706 2707 radeonfb_engine_reset(sc); 2708 pitch = ((dp->rd_virtx * (dp->rd_bpp / 8) + 0x3f)) >> 6; 2709 //pitch = ((sc->sc_maxx * (sc->sc_maxbpp / 8) + 0x3f)) >> 6; 2710 2711 radeonfb_wait_fifo(sc, 1); 2712 if (!IS_R300(sc)) 2713 PUT32(sc, RADEON_RB2D_DSTCACHE_MODE, 0); 2714 2715 radeonfb_wait_fifo(sc, 3); 2716 PUT32(sc, RADEON_DEFAULT_PITCH_OFFSET, 2717 (pitch << 22) | (sc->sc_aperbase >> 10)); 2718 2719 2720 PUT32(sc, RADEON_DST_PITCH_OFFSET, 2721 (pitch << 22) | (sc->sc_aperbase >> 10)); 2722 PUT32(sc, RADEON_SRC_PITCH_OFFSET, 2723 (pitch << 22) | (sc->sc_aperbase >> 10)); 2724 2725 radeonfb_wait_fifo(sc, 1); 2726 #if _BYTE_ORDER == _BIG_ENDIAN 2727 SET32(sc, RADEON_DP_DATATYPE, RADEON_HOST_BIG_ENDIAN_EN); 2728 #else 2729 CLR32(sc, RADEON_DP_DATATYPE, RADEON_HOST_BIG_ENDIAN_EN); 2730 #endif 2731 2732 /* default scissors -- no clipping */ 2733 radeonfb_wait_fifo(sc, 1); 2734 PUT32(sc, RADEON_DEFAULT_SC_BOTTOM_RIGHT, 2735 RADEON_DEFAULT_SC_RIGHT_MAX | RADEON_DEFAULT_SC_BOTTOM_MAX); 2736 2737 radeonfb_wait_fifo(sc, 1); 2738 PUT32(sc, RADEON_DP_GUI_MASTER_CNTL, 2739 (dp->rd_format << RADEON_GMC_DST_DATATYPE_SHIFT) | 2740 RADEON_GMC_CLR_CMP_CNTL_DIS | 2741 RADEON_GMC_BRUSH_SOLID_COLOR | 2742 RADEON_GMC_SRC_DATATYPE_COLOR); 2743 2744 radeonfb_wait_fifo(sc, 7); 2745 PUT32(sc, RADEON_DST_LINE_START, 0); 2746 PUT32(sc, RADEON_DST_LINE_END, 0); 2747 PUT32(sc, RADEON_DP_BRUSH_FRGD_CLR, 0xffffffff); 2748 PUT32(sc, RADEON_DP_BRUSH_BKGD_CLR, 0); 2749 PUT32(sc, RADEON_DP_SRC_FRGD_CLR, 0xffffffff); 2750 PUT32(sc, RADEON_DP_SRC_BKGD_CLR, 0); 2751 PUT32(sc, RADEON_DP_WRITE_MASK, 0xffffffff); 2752 2753 radeonfb_engine_idle(sc); 2754 } 2755 2756 static void 2757 radeonfb_engine_reset(struct radeonfb_softc *sc) 2758 { 2759 uint32_t hpc, rbbm, mclkcntl, clkindex; 2760 2761 radeonfb_engine_flush(sc); 2762 2763 clkindex = GET32(sc, RADEON_CLOCK_CNTL_INDEX); 2764 if (HAS_R300CG(sc)) 2765 radeonfb_r300cg_workaround(sc); 2766 mclkcntl = GETPLL(sc, RADEON_MCLK_CNTL); 2767 2768 /* 2769 * According to comments in XFree code, resetting the HDP via 2770 * the RBBM_SOFT_RESET can cause bad behavior on some systems. 2771 * So we use HOST_PATH_CNTL instead. 2772 */ 2773 2774 hpc = GET32(sc, RADEON_HOST_PATH_CNTL); 2775 rbbm = GET32(sc, RADEON_RBBM_SOFT_RESET); 2776 if (IS_R300(sc)) { 2777 PUT32(sc, RADEON_RBBM_SOFT_RESET, rbbm | 2778 RADEON_SOFT_RESET_CP | 2779 RADEON_SOFT_RESET_HI | 2780 RADEON_SOFT_RESET_E2); 2781 GET32(sc, RADEON_RBBM_SOFT_RESET); 2782 PUT32(sc, RADEON_RBBM_SOFT_RESET, 0); 2783 /* 2784 * XXX: this bit is not defined in any ATI docs I have, 2785 * nor in the XFree code, but XFree does it. Why? 2786 */ 2787 SET32(sc, RADEON_RB2D_DSTCACHE_MODE, (1<<17)); 2788 } else { 2789 PUT32(sc, RADEON_RBBM_SOFT_RESET, rbbm | 2790 RADEON_SOFT_RESET_CP | 2791 RADEON_SOFT_RESET_SE | 2792 RADEON_SOFT_RESET_RE | 2793 RADEON_SOFT_RESET_PP | 2794 RADEON_SOFT_RESET_E2 | 2795 RADEON_SOFT_RESET_RB); 2796 GET32(sc, RADEON_RBBM_SOFT_RESET); 2797 PUT32(sc, RADEON_RBBM_SOFT_RESET, rbbm & 2798 ~(RADEON_SOFT_RESET_CP | 2799 RADEON_SOFT_RESET_SE | 2800 RADEON_SOFT_RESET_RE | 2801 RADEON_SOFT_RESET_PP | 2802 RADEON_SOFT_RESET_E2 | 2803 RADEON_SOFT_RESET_RB)); 2804 GET32(sc, RADEON_RBBM_SOFT_RESET); 2805 } 2806 2807 PUT32(sc, RADEON_HOST_PATH_CNTL, hpc | RADEON_HDP_SOFT_RESET); 2808 GET32(sc, RADEON_HOST_PATH_CNTL); 2809 PUT32(sc, RADEON_HOST_PATH_CNTL, hpc); 2810 2811 if (IS_R300(sc)) 2812 PUT32(sc, RADEON_RBBM_SOFT_RESET, rbbm); 2813 2814 PUT32(sc, RADEON_CLOCK_CNTL_INDEX, clkindex); 2815 PUTPLL(sc, RADEON_MCLK_CNTL, mclkcntl); 2816 2817 if (HAS_R300CG(sc)) 2818 radeonfb_r300cg_workaround(sc); 2819 } 2820 2821 static int 2822 radeonfb_set_curpos(struct radeonfb_display *dp, struct wsdisplay_curpos *pos) 2823 { 2824 int x, y; 2825 2826 x = pos->x; 2827 y = pos->y; 2828 2829 /* 2830 * This doesn't let a cursor move off the screen. I'm not 2831 * sure if this will have negative effects for e.g. Xinerama. 2832 * I'd guess Xinerama handles it by changing the cursor shape, 2833 * but that needs verification. 2834 */ 2835 if (x >= dp->rd_virtx) 2836 x = dp->rd_virtx - 1; 2837 if (x < 0) 2838 x = 0; 2839 if (y >= dp->rd_virty) 2840 y = dp->rd_virty - 1; 2841 if (y < 0) 2842 y = 0; 2843 2844 dp->rd_cursor.rc_pos.x = x; 2845 dp->rd_cursor.rc_pos.y = y; 2846 2847 radeonfb_cursor_position(dp); 2848 return 0; 2849 } 2850 2851 static int 2852 radeonfb_set_cursor(struct radeonfb_display *dp, struct wsdisplay_cursor *wc) 2853 { 2854 unsigned flags; 2855 2856 uint8_t r[2], g[2], b[2]; 2857 unsigned index, count; 2858 int i, err; 2859 int pitch, size; 2860 struct radeonfb_cursor nc; 2861 2862 flags = wc->which; 2863 2864 /* copy old values */ 2865 nc = dp->rd_cursor; 2866 2867 if (flags & WSDISPLAY_CURSOR_DOCMAP) { 2868 index = wc->cmap.index; 2869 count = wc->cmap.count; 2870 2871 if (index >= 2 || (index + count) > 2) 2872 return EINVAL; 2873 2874 err = copyin(wc->cmap.red, &r[index], count); 2875 if (err) 2876 return err; 2877 err = copyin(wc->cmap.green, &g[index], count); 2878 if (err) 2879 return err; 2880 err = copyin(wc->cmap.blue, &b[index], count); 2881 if (err) 2882 return err; 2883 2884 for (i = index; i < index + count; i++) { 2885 nc.rc_cmap[i] = 2886 (r[i] << 16) + (g[i] << 8) + (b[i] << 0); 2887 } 2888 } 2889 2890 if (flags & WSDISPLAY_CURSOR_DOSHAPE) { 2891 if ((wc->size.x > RADEON_CURSORMAXX) || 2892 (wc->size.y > RADEON_CURSORMAXY)) 2893 return EINVAL; 2894 2895 /* figure bytes per line */ 2896 pitch = (wc->size.x + 7) / 8; 2897 size = pitch * wc->size.y; 2898 2899 /* clear the old cursor and mask */ 2900 memset(nc.rc_image, 0, 512); 2901 memset(nc.rc_mask, 0, 512); 2902 2903 nc.rc_size = wc->size; 2904 2905 if ((err = copyin(wc->image, nc.rc_image, size)) != 0) 2906 return err; 2907 2908 if ((err = copyin(wc->mask, nc.rc_mask, size)) != 0) 2909 return err; 2910 } 2911 2912 if (flags & WSDISPLAY_CURSOR_DOHOT) { 2913 nc.rc_hot = wc->hot; 2914 if (nc.rc_hot.x >= nc.rc_size.x) 2915 nc.rc_hot.x = nc.rc_size.x - 1; 2916 if (nc.rc_hot.y >= nc.rc_size.y) 2917 nc.rc_hot.y = nc.rc_size.y - 1; 2918 } 2919 2920 if (flags & WSDISPLAY_CURSOR_DOPOS) { 2921 nc.rc_pos = wc->pos; 2922 if (nc.rc_pos.x >= dp->rd_virtx) 2923 nc.rc_pos.x = dp->rd_virtx - 1; 2924 #if 0 2925 if (nc.rc_pos.x < 0) 2926 nc.rc_pos.x = 0; 2927 #endif 2928 if (nc.rc_pos.y >= dp->rd_virty) 2929 nc.rc_pos.y = dp->rd_virty - 1; 2930 #if 0 2931 if (nc.rc_pos.y < 0) 2932 nc.rc_pos.y = 0; 2933 #endif 2934 } 2935 if (flags & WSDISPLAY_CURSOR_DOCUR) { 2936 nc.rc_visible = wc->enable; 2937 } 2938 2939 dp->rd_cursor = nc; 2940 radeonfb_cursor_update(dp, wc->which); 2941 2942 return 0; 2943 } 2944 2945 /* 2946 * Change the cursor shape. Call this with the cursor locked to avoid 2947 * flickering/tearing. 2948 */ 2949 static void 2950 radeonfb_cursor_shape(struct radeonfb_display *dp) 2951 { 2952 uint8_t and[512], xor[512]; 2953 int i, j, src, dst, pitch; 2954 const uint8_t *msk = dp->rd_cursor.rc_mask; 2955 const uint8_t *img = dp->rd_cursor.rc_image; 2956 2957 /* 2958 * Radeon cursor data interleaves one line of AND data followed 2959 * by a line of XOR data. (Each line corresponds to a whole hardware 2960 * pitch - i.e. 64 pixels or 8 bytes.) 2961 * 2962 * The cursor is displayed using the following table: 2963 * 2964 * AND XOR Result 2965 * ---------------------- 2966 * 0 0 Cursor color 0 2967 * 0 1 Cursor color 1 2968 * 1 0 Transparent 2969 * 1 1 Complement of background 2970 * 2971 * Our masks are therefore different from what we were passed. 2972 * Passed in, I'm assuming the data represents either color 0 or 1, 2973 * and a mask, so the passed in table looks like: 2974 * 2975 * IMG Mask Result 2976 * ----------------------- 2977 * 0 0 Transparent 2978 * 0 1 Cursor color 0 2979 * 1 0 Transparent 2980 * 1 1 Cursor color 1 2981 * 2982 * IF mask bit == 1, AND = 0, XOR = color. 2983 * IF mask bit == 0, AND = 1, XOR = 0. 2984 * 2985 * hence: AND = ~(mask); XOR = color & ~(mask); 2986 */ 2987 2988 pitch = ((dp->rd_cursor.rc_size.x + 7) / 8); 2989 2990 /* start by assuming all bits are transparent */ 2991 memset(and, 0xff, 512); 2992 memset(xor, 0x00, 512); 2993 2994 src = 0; 2995 dst = 0; 2996 for (i = 0; i < 64; i++) { 2997 for (j = 0; j < 64; j += 8) { 2998 if ((i < dp->rd_cursor.rc_size.y) && 2999 (j < dp->rd_cursor.rc_size.x)) { 3000 3001 /* take care to leave odd bits alone */ 3002 and[dst] &= ~(msk[src]); 3003 xor[dst] = img[src] & msk[src]; 3004 src++; 3005 } 3006 dst++; 3007 } 3008 } 3009 3010 /* copy the image into place */ 3011 for (i = 0; i < 64; i++) { 3012 memcpy((uint8_t *)dp->rd_curptr + (i * 16), 3013 &and[i * 8], 8); 3014 memcpy((uint8_t *)dp->rd_curptr + (i * 16) + 8, 3015 &xor[i * 8], 8); 3016 } 3017 } 3018 3019 static void 3020 radeonfb_cursor_position(struct radeonfb_display *dp) 3021 { 3022 struct radeonfb_softc *sc = dp->rd_softc; 3023 uint32_t offset, hvoff, hvpos; /* registers */ 3024 uint32_t coff; /* cursor offset */ 3025 int i, x, y, xoff, yoff, crtcoff; 3026 3027 /* 3028 * XXX: this also needs to handle pan/scan 3029 */ 3030 for (i = 0; i < dp->rd_ncrtcs; i++) { 3031 3032 struct radeonfb_crtc *rcp = &dp->rd_crtcs[i]; 3033 3034 if (rcp->rc_number) { 3035 offset = RADEON_CUR2_OFFSET; 3036 hvoff = RADEON_CUR2_HORZ_VERT_OFF; 3037 hvpos = RADEON_CUR2_HORZ_VERT_POSN; 3038 crtcoff = RADEON_CRTC2_OFFSET; 3039 } else { 3040 offset = RADEON_CUR_OFFSET; 3041 hvoff = RADEON_CUR_HORZ_VERT_OFF; 3042 hvpos = RADEON_CUR_HORZ_VERT_POSN; 3043 crtcoff = RADEON_CRTC_OFFSET; 3044 } 3045 3046 x = dp->rd_cursor.rc_pos.x; 3047 y = dp->rd_cursor.rc_pos.y; 3048 3049 while (y < rcp->rc_yoffset) { 3050 rcp->rc_yoffset -= RADEON_PANINCREMENT; 3051 } 3052 while (y >= (rcp->rc_yoffset + rcp->rc_videomode.vdisplay)) { 3053 rcp->rc_yoffset += RADEON_PANINCREMENT; 3054 } 3055 while (x < rcp->rc_xoffset) { 3056 rcp->rc_xoffset -= RADEON_PANINCREMENT; 3057 } 3058 while (x >= (rcp->rc_xoffset + rcp->rc_videomode.hdisplay)) { 3059 rcp->rc_xoffset += RADEON_PANINCREMENT; 3060 } 3061 3062 /* adjust for the cursor's hotspot */ 3063 x -= dp->rd_cursor.rc_hot.x; 3064 y -= dp->rd_cursor.rc_hot.y; 3065 xoff = yoff = 0; 3066 3067 if (x >= dp->rd_virtx) 3068 x = dp->rd_virtx - 1; 3069 if (y >= dp->rd_virty) 3070 y = dp->rd_virty - 1; 3071 3072 /* now adjust cursor so it is relative to viewport */ 3073 x -= rcp->rc_xoffset; 3074 y -= rcp->rc_yoffset; 3075 3076 /* 3077 * no need to check for fall off, because we should 3078 * never move off the screen entirely! 3079 */ 3080 coff = 0; 3081 if (x < 0) { 3082 xoff = -x; 3083 x = 0; 3084 } 3085 if (y < 0) { 3086 yoff = -y; 3087 y = 0; 3088 coff = (yoff * 2) * 8; 3089 } 3090 3091 /* pan the display */ 3092 PUT32(sc, crtcoff, (rcp->rc_yoffset * dp->rd_stride) + 3093 rcp->rc_xoffset); 3094 3095 PUT32(sc, offset, (dp->rd_curoff + coff) | RADEON_CUR_LOCK); 3096 PUT32(sc, hvoff, (xoff << 16) | (yoff) | RADEON_CUR_LOCK); 3097 /* NB: this unlocks the cursor */ 3098 PUT32(sc, hvpos, (x << 16) | y); 3099 } 3100 } 3101 3102 static void 3103 radeonfb_cursor_visible(struct radeonfb_display *dp) 3104 { 3105 int i; 3106 uint32_t gencntl, bit; 3107 3108 for (i = 0; i < dp->rd_ncrtcs; i++) { 3109 if (dp->rd_crtcs[i].rc_number) { 3110 gencntl = RADEON_CRTC2_GEN_CNTL; 3111 bit = RADEON_CRTC2_CUR_EN; 3112 } else { 3113 gencntl = RADEON_CRTC_GEN_CNTL; 3114 bit = RADEON_CRTC_CUR_EN; 3115 } 3116 3117 if (dp->rd_cursor.rc_visible) 3118 SET32(dp->rd_softc, gencntl, bit); 3119 else 3120 CLR32(dp->rd_softc, gencntl, bit); 3121 } 3122 } 3123 3124 static void 3125 radeonfb_cursor_cmap(struct radeonfb_display *dp) 3126 { 3127 int i; 3128 uint32_t c0reg, c1reg; 3129 struct radeonfb_softc *sc = dp->rd_softc; 3130 3131 for (i = 0; i < dp->rd_ncrtcs; i++) { 3132 if (dp->rd_crtcs[i].rc_number) { 3133 c0reg = RADEON_CUR2_CLR0; 3134 c1reg = RADEON_CUR2_CLR1; 3135 } else { 3136 c0reg = RADEON_CUR_CLR0; 3137 c1reg = RADEON_CUR_CLR1; 3138 } 3139 3140 PUT32(sc, c0reg, dp->rd_cursor.rc_cmap[0]); 3141 PUT32(sc, c1reg, dp->rd_cursor.rc_cmap[1]); 3142 } 3143 } 3144 3145 static void 3146 radeonfb_cursor_update(struct radeonfb_display *dp, unsigned which) 3147 { 3148 struct radeonfb_softc *sc; 3149 int i; 3150 3151 sc = dp->rd_softc; 3152 for (i = 0; i < dp->rd_ncrtcs; i++) { 3153 if (dp->rd_crtcs[i].rc_number) { 3154 SET32(sc, RADEON_CUR2_OFFSET, RADEON_CUR_LOCK); 3155 } else { 3156 SET32(sc, RADEON_CUR_OFFSET,RADEON_CUR_LOCK); 3157 } 3158 } 3159 3160 if (which & WSDISPLAY_CURSOR_DOCMAP) 3161 radeonfb_cursor_cmap(dp); 3162 3163 if (which & WSDISPLAY_CURSOR_DOSHAPE) 3164 radeonfb_cursor_shape(dp); 3165 3166 if (which & WSDISPLAY_CURSOR_DOCUR) 3167 radeonfb_cursor_visible(dp); 3168 3169 /* this one is unconditional, because it updates other stuff */ 3170 radeonfb_cursor_position(dp); 3171 } 3172 3173 static struct videomode * 3174 radeonfb_best_refresh(struct videomode *m1, struct videomode *m2) 3175 { 3176 int r1, r2; 3177 3178 /* otherwise pick the higher refresh rate */ 3179 r1 = DIVIDE(DIVIDE(m1->dot_clock, m1->htotal), m1->vtotal); 3180 r2 = DIVIDE(DIVIDE(m2->dot_clock, m2->htotal), m2->vtotal); 3181 3182 return (r1 < r2 ? m2 : m1); 3183 } 3184 3185 static const struct videomode * 3186 radeonfb_port_mode(struct radeonfb_softc *sc, struct radeonfb_port *rp, 3187 int x, int y) 3188 { 3189 struct edid_info *ep = &rp->rp_edid; 3190 struct videomode *vmp = NULL; 3191 int i; 3192 3193 if (!rp->rp_edid_valid) { 3194 /* fallback to safe mode */ 3195 return radeonfb_modelookup(sc->sc_defaultmode); 3196 } 3197 3198 /* always choose the preferred mode first! */ 3199 if (ep->edid_preferred_mode) { 3200 3201 /* XXX: add auto-stretching support for native mode */ 3202 3203 /* this may want panning to occur, btw */ 3204 if ((ep->edid_preferred_mode->hdisplay <= x) && 3205 (ep->edid_preferred_mode->vdisplay <= y)) 3206 return ep->edid_preferred_mode; 3207 } 3208 3209 for (i = 0; i < ep->edid_nmodes; i++) { 3210 /* 3211 * We elect to pick a resolution that is too large for 3212 * the monitor than one that is too small. This means 3213 * that we will prefer to pan rather than to try to 3214 * center a smaller display on a larger screen. In 3215 * practice, this shouldn't matter because if a 3216 * monitor can support a larger resolution, it can 3217 * probably also support the smaller. A specific 3218 * exception is fixed format panels, but hopefully 3219 * they are properly dealt with by the "autostretch" 3220 * logic above. 3221 */ 3222 if ((ep->edid_modes[i].hdisplay > x) || 3223 (ep->edid_modes[i].vdisplay > y)) { 3224 continue; 3225 } 3226 3227 /* 3228 * at this point, the display mode is no larger than 3229 * what we've requested. 3230 */ 3231 if (vmp == NULL) 3232 vmp = &ep->edid_modes[i]; 3233 3234 /* eliminate smaller modes */ 3235 if ((vmp->hdisplay >= ep->edid_modes[i].hdisplay) || 3236 (vmp->vdisplay >= ep->edid_modes[i].vdisplay)) 3237 continue; 3238 3239 if ((vmp->hdisplay < ep->edid_modes[i].hdisplay) || 3240 (vmp->vdisplay < ep->edid_modes[i].vdisplay)) { 3241 vmp = &ep->edid_modes[i]; 3242 continue; 3243 } 3244 3245 KASSERT(vmp->hdisplay == ep->edid_modes[i].hdisplay); 3246 KASSERT(vmp->vdisplay == ep->edid_modes[i].vdisplay); 3247 3248 vmp = radeonfb_best_refresh(vmp, &ep->edid_modes[i]); 3249 } 3250 3251 return (vmp ? vmp : radeonfb_modelookup(sc->sc_defaultmode)); 3252 } 3253 3254 static int 3255 radeonfb_hasres(struct videomode *list, int nlist, int x, int y) 3256 { 3257 int i; 3258 3259 for (i = 0; i < nlist; i++) { 3260 if ((x == list[i].hdisplay) && 3261 (y == list[i].vdisplay)) { 3262 return 1; 3263 } 3264 } 3265 return 0; 3266 } 3267 3268 static void 3269 radeonfb_pickres(struct radeonfb_display *dp, uint16_t *x, uint16_t *y, 3270 int pan) 3271 { 3272 struct radeonfb_port *rp; 3273 struct edid_info *ep; 3274 int i, j; 3275 3276 *x = 0; 3277 *y = 0; 3278 3279 if (pan) { 3280 for (i = 0; i < dp->rd_ncrtcs; i++) { 3281 rp = dp->rd_crtcs[i].rc_port; 3282 ep = &rp->rp_edid; 3283 if (!rp->rp_edid_valid) { 3284 /* monitor not present */ 3285 continue; 3286 } 3287 3288 /* 3289 * For now we are ignoring "conflict" that 3290 * could occur when mixing some modes like 3291 * 1280x1024 and 1400x800. It isn't clear 3292 * which is better, so the first one wins. 3293 */ 3294 for (j = 0; j < ep->edid_nmodes; j++) { 3295 /* 3296 * ignore resolutions that are too big for 3297 * the radeon 3298 */ 3299 if (ep->edid_modes[j].hdisplay > 3300 dp->rd_softc->sc_maxx) 3301 continue; 3302 if (ep->edid_modes[j].vdisplay > 3303 dp->rd_softc->sc_maxy) 3304 continue; 3305 3306 /* 3307 * pick largest resolution, the 3308 * smaller monitor will pan 3309 */ 3310 if ((ep->edid_modes[j].hdisplay >= *x) && 3311 (ep->edid_modes[j].vdisplay >= *y)) { 3312 *x = ep->edid_modes[j].hdisplay; 3313 *y = ep->edid_modes[j].vdisplay; 3314 } 3315 } 3316 } 3317 3318 } else { 3319 struct videomode modes[64]; 3320 int nmodes = 0; 3321 int valid = 0; 3322 3323 for (i = 0; i < dp->rd_ncrtcs; i++) { 3324 /* 3325 * pick the largest resolution in common. 3326 */ 3327 rp = dp->rd_crtcs[i].rc_port; 3328 ep = &rp->rp_edid; 3329 3330 if (!rp->rp_edid_valid) 3331 continue; 3332 3333 if (!valid) { 3334 /* 3335 * Pick the preferred mode for this port 3336 * if available. 3337 */ 3338 if (ep->edid_preferred_mode) { 3339 struct videomode *vmp = 3340 ep->edid_preferred_mode; 3341 3342 if ((vmp->hdisplay <= 3343 dp->rd_softc->sc_maxx) && 3344 (vmp->vdisplay <= 3345 dp->rd_softc->sc_maxy)) 3346 modes[nmodes++] = *vmp; 3347 } else { 3348 3349 /* initialize starting list */ 3350 for (j = 0; j < ep->edid_nmodes; j++) { 3351 /* 3352 * ignore resolutions that are 3353 * too big for the radeon 3354 */ 3355 if (ep->edid_modes[j].hdisplay > 3356 dp->rd_softc->sc_maxx) 3357 continue; 3358 if (ep->edid_modes[j].vdisplay > 3359 dp->rd_softc->sc_maxy) 3360 continue; 3361 3362 modes[nmodes] = 3363 ep->edid_modes[j]; 3364 nmodes++; 3365 } 3366 } 3367 valid = 1; 3368 } else { 3369 /* merge into preexisting list */ 3370 for (j = 0; j < nmodes; j++) { 3371 if (!radeonfb_hasres(ep->edid_modes, 3372 ep->edid_nmodes, 3373 modes[j].hdisplay, 3374 modes[j].vdisplay)) { 3375 modes[j] = modes[nmodes]; 3376 j--; 3377 nmodes--; 3378 } 3379 } 3380 } 3381 } 3382 3383 /* now we have to pick from the merged list */ 3384 for (i = 0; i < nmodes; i++) { 3385 if ((modes[i].hdisplay >= *x) && 3386 (modes[i].vdisplay >= *y)) { 3387 *x = modes[i].hdisplay; 3388 *y = modes[i].vdisplay; 3389 } 3390 } 3391 } 3392 3393 if ((*x == 0) || (*y == 0)) { 3394 /* fallback to safe mode */ 3395 *x = 640; 3396 *y = 480; 3397 } 3398 } 3399 3400 /* 3401 * backlight levels are linear on: 3402 * - RV200, RV250, RV280, RV350 3403 * - but NOT on PowerBook4,3 6,3 6,5 3404 * according to Linux' radeonfb 3405 */ 3406 3407 /* Get the current backlight level for the display. */ 3408 3409 static int 3410 radeonfb_get_backlight(struct radeonfb_display *dp) 3411 { 3412 int s; 3413 uint32_t level; 3414 3415 s = spltty(); 3416 3417 level = radeonfb_get32(dp->rd_softc, RADEON_LVDS_GEN_CNTL); 3418 level &= RADEON_LVDS_BL_MOD_LEV_MASK; 3419 level >>= RADEON_LVDS_BL_MOD_LEV_SHIFT; 3420 3421 /* 3422 * On some chips, we should negate the backlight level. 3423 * XXX Find out on which chips. 3424 */ 3425 if (dp->rd_softc->sc_flags & RFB_INV_BLIGHT) 3426 level = RADEONFB_BACKLIGHT_MAX - level; 3427 3428 splx(s); 3429 3430 return level; 3431 } 3432 3433 /* Set the backlight to the given level for the display. */ 3434 3435 static int 3436 radeonfb_set_backlight(struct radeonfb_display *dp, int level) 3437 { 3438 struct radeonfb_softc *sc; 3439 int rlevel, s; 3440 uint32_t lvds; 3441 3442 s = spltty(); 3443 3444 if (level < 0) 3445 level = 0; 3446 else if (level >= RADEONFB_BACKLIGHT_MAX) 3447 level = RADEONFB_BACKLIGHT_MAX; 3448 3449 sc = dp->rd_softc; 3450 3451 /* On some chips, we should negate the backlight level. */ 3452 if (dp->rd_softc->sc_flags & RFB_INV_BLIGHT) { 3453 rlevel = RADEONFB_BACKLIGHT_MAX - level; 3454 } else 3455 rlevel = level; 3456 3457 callout_stop(&dp->rd_bl_lvds_co); 3458 radeonfb_engine_idle(sc); 3459 3460 /* 3461 * Turn off the display if the backlight is set to 0, since the 3462 * display is useless without backlight anyway. 3463 */ 3464 if (level == 0) 3465 radeonfb_blank(dp, 1); 3466 else if (radeonfb_get_backlight(dp) == 0) 3467 radeonfb_blank(dp, 0); 3468 3469 lvds = radeonfb_get32(sc, RADEON_LVDS_GEN_CNTL); 3470 lvds &= ~RADEON_LVDS_DISPLAY_DIS; 3471 if (!(lvds & RADEON_LVDS_BLON) || !(lvds & RADEON_LVDS_ON)) { 3472 lvds |= dp->rd_bl_lvds_val & RADEON_LVDS_DIGON; 3473 lvds |= RADEON_LVDS_BLON | RADEON_LVDS_EN; 3474 radeonfb_put32(sc, RADEON_LVDS_GEN_CNTL, lvds); 3475 lvds &= ~RADEON_LVDS_BL_MOD_LEV_MASK; 3476 lvds |= rlevel << RADEON_LVDS_BL_MOD_LEV_SHIFT; 3477 lvds |= RADEON_LVDS_ON; 3478 lvds |= dp->rd_bl_lvds_val & RADEON_LVDS_BL_MOD_EN; 3479 } else { 3480 lvds &= ~RADEON_LVDS_BL_MOD_LEV_MASK; 3481 lvds |= rlevel << RADEON_LVDS_BL_MOD_LEV_SHIFT; 3482 radeonfb_put32(sc, RADEON_LVDS_GEN_CNTL, lvds); 3483 } 3484 3485 dp->rd_bl_lvds_val &= ~RADEON_LVDS_STATE_MASK; 3486 dp->rd_bl_lvds_val |= lvds & RADEON_LVDS_STATE_MASK; 3487 /* XXX What is the correct delay? */ 3488 callout_schedule(&dp->rd_bl_lvds_co, 200 * hz); 3489 3490 splx(s); 3491 3492 return 0; 3493 } 3494 3495 /* 3496 * Callout function for delayed operations on the LVDS_GEN_CNTL register. 3497 * Set the delayed bits in the register, and clear the stored delayed 3498 * value. 3499 */ 3500 3501 static void radeonfb_lvds_callout(void *arg) 3502 { 3503 struct radeonfb_display *dp = arg; 3504 int s; 3505 3506 s = splhigh(); 3507 3508 radeonfb_mask32(dp->rd_softc, RADEON_LVDS_GEN_CNTL, ~0, 3509 dp->rd_bl_lvds_val); 3510 dp->rd_bl_lvds_val = 0; 3511 3512 splx(s); 3513 } 3514