aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/video/offb.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/video/offb.c')
-rw-r--r--drivers/video/offb.c122
1 files changed, 64 insertions, 58 deletions
diff --git a/drivers/video/offb.c b/drivers/video/offb.c
index 00d87f5bb7be..ad1434e3f227 100644
--- a/drivers/video/offb.c
+++ b/drivers/video/offb.c
@@ -223,6 +223,7 @@ static int offb_blank(int blank, struct fb_info *info)
223int __init offb_init(void) 223int __init offb_init(void)
224{ 224{
225 struct device_node *dp = NULL, *boot_disp = NULL; 225 struct device_node *dp = NULL, *boot_disp = NULL;
226
226#if defined(CONFIG_BOOTX_TEXT) && defined(CONFIG_PPC32) 227#if defined(CONFIG_BOOTX_TEXT) && defined(CONFIG_PPC32)
227 struct device_node *macos_display = NULL; 228 struct device_node *macos_display = NULL;
228#endif 229#endif
@@ -234,60 +235,54 @@ int __init offb_init(void)
234 if (boot_infos != 0) { 235 if (boot_infos != 0) {
235 unsigned long addr = 236 unsigned long addr =
236 (unsigned long) boot_infos->dispDeviceBase; 237 (unsigned long) boot_infos->dispDeviceBase;
238 u32 *addrp;
239 u64 daddr, dsize;
240 unsigned int flags;
241
237 /* find the device node corresponding to the macos display */ 242 /* find the device node corresponding to the macos display */
238 while ((dp = of_find_node_by_type(dp, "display"))) { 243 while ((dp = of_find_node_by_type(dp, "display"))) {
239 int i; 244 int i;
240 /*
241 * Grrr... It looks like the MacOS ATI driver
242 * munges the assigned-addresses property (but
243 * the AAPL,address value is OK).
244 */
245 if (strncmp(dp->name, "ATY,", 4) == 0
246 && dp->n_addrs == 1) {
247 unsigned int *ap =
248 (unsigned int *) get_property(dp,
249 "AAPL,address",
250 NULL);
251 if (ap != NULL) {
252 dp->addrs[0].address = *ap;
253 dp->addrs[0].size = 0x01000000;
254 }
255 }
256 245
257 /* 246 /*
258 * The LTPro on the Lombard powerbook has no addresses 247 * Look for an AAPL,address property first.
259 * on the display nodes, they are on their parent.
260 */ 248 */
261 if (dp->n_addrs == 0 249 unsigned int na;
262 && device_is_compatible(dp, "ATY,264LTPro")) { 250 unsigned int *ap =
263 int na; 251 (unsigned int *)get_property(dp, "AAPL,address",
264 unsigned int *ap = (unsigned int *) 252 &na);
265 get_property(dp, "AAPL,address", &na); 253 if (ap != 0) {
266 if (ap != 0) 254 for (na /= sizeof(unsigned int); na > 0;
267 for (na /= sizeof(unsigned int); 255 --na, ++ap)
268 na > 0; --na, ++ap) 256 if (*ap <= addr &&
269 if (*ap <= addr 257 addr < *ap + 0x1000000) {
270 && addr < 258 macos_display = dp;
271 *ap + 0x1000000) 259 goto foundit;
272 goto foundit; 260 }
273 } 261 }
274 262
275 /* 263 /*
276 * See if the display address is in one of the address 264 * See if the display address is in one of the address
277 * ranges for this display. 265 * ranges for this display.
278 */ 266 */
279 for (i = 0; i < dp->n_addrs; ++i) { 267 i = 0;
280 if (dp->addrs[i].address <= addr 268 for (;;) {
281 && addr < 269 addrp = of_get_address(dp, i++, &dsize, &flags);
282 dp->addrs[i].address + 270 if (addrp == NULL)
283 dp->addrs[i].size)
284 break; 271 break;
272 if (!(flags & IORESOURCE_MEM))
273 continue;
274 daddr = of_translate_address(dp, addrp);
275 if (daddr == OF_BAD_ADDR)
276 continue;
277 if (daddr <= addr && addr < (daddr + dsize)) {
278 macos_display = dp;
279 goto foundit;
280 }
285 } 281 }
286 if (i < dp->n_addrs) { 282 foundit:
287 foundit: 283 if (macos_display) {
288 printk(KERN_INFO "MacOS display is %s\n", 284 printk(KERN_INFO "MacOS display is %s\n",
289 dp->full_name); 285 dp->full_name);
290 macos_display = dp;
291 break; 286 break;
292 } 287 }
293 } 288 }
@@ -326,8 +321,10 @@ static void __init offb_init_nodriver(struct device_node *dp)
326 int *pp, i; 321 int *pp, i;
327 unsigned int len; 322 unsigned int len;
328 int width = 640, height = 480, depth = 8, pitch; 323 int width = 640, height = 480, depth = 8, pitch;
329 unsigned int rsize, *up; 324 unsigned int flags, rsize, *up;
330 unsigned long address = 0; 325 u64 address = OF_BAD_ADDR;
326 u32 *addrp;
327 u64 asize;
331 328
332 if ((pp = (int *) get_property(dp, "depth", &len)) != NULL 329 if ((pp = (int *) get_property(dp, "depth", &len)) != NULL
333 && len == sizeof(int)) 330 && len == sizeof(int))
@@ -363,7 +360,7 @@ static void __init offb_init_nodriver(struct device_node *dp)
363 break; 360 break;
364 } 361 }
365 if (pdev) { 362 if (pdev) {
366 for (i = 0; i < 6 && address == 0; i++) { 363 for (i = 0; i < 6 && address == OF_BAD_ADDR; i++) {
367 if ((pci_resource_flags(pdev, i) & 364 if ((pci_resource_flags(pdev, i) &
368 IORESOURCE_MEM) && 365 IORESOURCE_MEM) &&
369 (pci_resource_len(pdev, i) >= rsize)) 366 (pci_resource_len(pdev, i) >= rsize))
@@ -374,27 +371,33 @@ static void __init offb_init_nodriver(struct device_node *dp)
374 } 371 }
375#endif /* CONFIG_PCI */ 372#endif /* CONFIG_PCI */
376 373
377 if (address == 0 && 374 /* This one is dodgy, we may drop it ... */
378 (up = (unsigned *) get_property(dp, "address", &len)) != NULL && 375 if (address == OF_BAD_ADDR &&
379 len == sizeof(unsigned)) 376 (up = (unsigned *) get_property(dp, "address", &len)) != NULL &&
380 address = (u_long) * up; 377 len == sizeof(unsigned int))
381 if (address == 0) { 378 address = (u64) * up;
382 for (i = 0; i < dp->n_addrs; ++i) 379
383 if (dp->addrs[i].size >= 380 if (address == OF_BAD_ADDR) {
384 pitch * height * depth / 8) 381 for (i = 0; (addrp = of_get_address(dp, i, &asize, &flags))
385 break; 382 != NULL; i++) {
386 if (i >= dp->n_addrs) { 383 if (!(flags & IORESOURCE_MEM))
384 continue;
385 if (asize >= pitch * height * depth / 8)
386 break;
387 }
388 if (addrp == NULL) {
387 printk(KERN_ERR 389 printk(KERN_ERR
388 "no framebuffer address found for %s\n", 390 "no framebuffer address found for %s\n",
389 dp->full_name); 391 dp->full_name);
390 return; 392 return;
391 } 393 }
392 394 address = of_translate_address(dp, addrp);
393 address = (u_long) dp->addrs[i].address; 395 if (address == OF_BAD_ADDR) {
394 396 printk(KERN_ERR
395#ifdef CONFIG_PPC64 397 "can't translate framebuffer address for %s\n",
396 address += ((struct pci_dn *)dp->data)->phb->pci_mem_offset; 398 dp->full_name);
397#endif 399 return;
400 }
398 401
399 /* kludge for valkyrie */ 402 /* kludge for valkyrie */
400 if (strcmp(dp->name, "valkyrie") == 0) 403 if (strcmp(dp->name, "valkyrie") == 0)
@@ -459,7 +462,9 @@ static void __init offb_init_fb(const char *name, const char *full_name,
459 462
460 par->cmap_type = cmap_unknown; 463 par->cmap_type = cmap_unknown;
461 if (depth == 8) { 464 if (depth == 8) {
462 /* XXX kludge for ati */ 465
466 /* Palette hacks disabled for now */
467#if 0
463 if (dp && !strncmp(name, "ATY,Rage128", 11)) { 468 if (dp && !strncmp(name, "ATY,Rage128", 11)) {
464 unsigned long regbase = dp->addrs[2].address; 469 unsigned long regbase = dp->addrs[2].address;
465 par->cmap_adr = ioremap(regbase, 0x1FFF); 470 par->cmap_adr = ioremap(regbase, 0x1FFF);
@@ -490,6 +495,7 @@ static void __init offb_init_fb(const char *name, const char *full_name,
490 par->cmap_adr = ioremap(regbase + 0x6000, 0x1000); 495 par->cmap_adr = ioremap(regbase + 0x6000, 0x1000);
491 par->cmap_type = cmap_gxt2000; 496 par->cmap_type = cmap_gxt2000;
492 } 497 }
498#endif
493 fix->visual = par->cmap_adr ? FB_VISUAL_PSEUDOCOLOR 499 fix->visual = par->cmap_adr ? FB_VISUAL_PSEUDOCOLOR
494 : FB_VISUAL_STATIC_PSEUDOCOLOR; 500 : FB_VISUAL_STATIC_PSEUDOCOLOR;
495 } else 501 } else