Linux-libre 5.7.3-gnu
[librecmc/linux-libre.git] / drivers / video / fbdev / macfb.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * macfb.c: Generic framebuffer for Macs whose colourmaps/modes we
4  * don't know how to set.
5  *
6  * (c) 1999 David Huggins-Daines <dhd@debian.org>
7  *
8  * Primarily based on vesafb.c, by Gerd Knorr
9  * (c) 1998 Gerd Knorr <kraxel@cs.tu-berlin.de>
10  *
11  * Also uses information and code from:
12  *
13  * The original macfb.c from Linux/mac68k 2.0, by Alan Cox, Juergen
14  * Mellinger, Mikael Forselius, Michael Schmitz, and others.
15  *
16  * valkyriefb.c, by Martin Costabel, Kevin Schoedel, Barry Nathan, Dan
17  * Jacobowitz, Paul Mackerras, Fabio Riccardi, and Geert Uytterhoeven.
18  *
19  * The VideoToolbox "Bugs" web page at
20  * http://rajsky.psych.nyu.edu/Tips/VideoBugs.html
21  */
22
23 #include <linux/module.h>
24 #include <linux/kernel.h>
25 #include <linux/errno.h>
26 #include <linux/string.h>
27 #include <linux/mm.h>
28 #include <linux/delay.h>
29 #include <linux/nubus.h>
30 #include <linux/init.h>
31 #include <linux/fb.h>
32
33 #include <asm/setup.h>
34 #include <asm/macintosh.h>
35 #include <asm/io.h>
36
37 /* Common DAC base address for the LC, RBV, Valkyrie, and IIvx */
38 #define DAC_BASE 0x50f24000
39
40 /* Some addresses for the DAFB */
41 #define DAFB_BASE 0xf9800200
42
43 /* Address for the built-in Civic framebuffer in Quadra AVs */
44 #define CIVIC_BASE 0x50f30800
45
46 /* GSC (Gray Scale Controller) base address */
47 #define GSC_BASE 0x50F20000
48
49 /* CSC (Color Screen Controller) base address */
50 #define CSC_BASE 0x50F20000
51
52 static int (*macfb_setpalette)(unsigned int regno, unsigned int red,
53                                unsigned int green, unsigned int blue,
54                                struct fb_info *info);
55
56 static struct {
57         unsigned char addr;
58         unsigned char lut;
59 } __iomem *v8_brazil_cmap_regs;
60
61 static struct {
62         unsigned char addr;
63         char pad1[3]; /* word aligned */
64         unsigned char lut;
65         char pad2[3]; /* word aligned */
66         unsigned char cntl; /* a guess as to purpose */
67 } __iomem *rbv_cmap_regs;
68
69 static struct {
70         unsigned long reset;
71         unsigned long pad1[3];
72         unsigned char pad2[3];
73         unsigned char lut;
74 } __iomem *dafb_cmap_regs;
75
76 static struct {
77         unsigned char addr;     /* OFFSET: 0x00 */
78         unsigned char pad1[15];
79         unsigned char lut;      /* OFFSET: 0x10 */
80         unsigned char pad2[15];
81         unsigned char status;   /* OFFSET: 0x20 */
82         unsigned char pad3[7];
83         unsigned long vbl_addr; /* OFFSET: 0x28 */
84         unsigned int  status2;  /* OFFSET: 0x2C */
85 } __iomem *civic_cmap_regs;
86
87 static struct {
88         char pad1[0x40];
89         unsigned char clut_waddr;       /* 0x40 */
90         char pad2;
91         unsigned char clut_data;        /* 0x42 */
92         char pad3[0x3];
93         unsigned char clut_raddr;       /* 0x46 */
94 } __iomem *csc_cmap_regs;
95
96 /* The registers in these structs are in NuBus slot space */
97 struct mdc_cmap_regs {
98         char pad1[0x200200];
99         unsigned char addr;
100         char pad2[6];
101         unsigned char lut;
102 };
103
104 struct toby_cmap_regs {
105         char pad1[0x90018];
106         unsigned char lut; /* TFBClutWDataReg, offset 0x90018 */
107         char pad2[3];
108         unsigned char addr; /* TFBClutAddrReg, offset 0x9001C */
109 };
110
111 struct jet_cmap_regs {
112         char pad1[0xe0e000];
113         unsigned char addr;
114         unsigned char lut;
115 };
116
117 #define PIXEL_TO_MM(a)  (((a)*10)/28)   /* width in mm at 72 dpi */
118
119 static struct fb_var_screeninfo macfb_defined = {
120         .activate       = FB_ACTIVATE_NOW,
121         .right_margin   = 32,
122         .upper_margin   = 16,
123         .lower_margin   = 4,
124         .vsync_len      = 4,
125         .vmode          = FB_VMODE_NONINTERLACED,
126 };
127
128 static struct fb_fix_screeninfo macfb_fix = {
129         .type   = FB_TYPE_PACKED_PIXELS,
130         .accel  = FB_ACCEL_NONE,
131 };
132
133 static void *slot_addr;
134 static struct fb_info fb_info;
135 static u32 pseudo_palette[16];
136 static int vidtest;
137
138 /*
139  * Unlike the Valkyrie, the DAFB cannot set individual colormap
140  * registers.  Therefore, we do what the MacOS driver does (no
141  * kidding!) and simply set them one by one until we hit the one we
142  * want.
143  */
144 static int dafb_setpalette(unsigned int regno, unsigned int red,
145                            unsigned int green, unsigned int blue,
146                            struct fb_info *info)
147 {
148         static int lastreg = -2;
149         unsigned long flags;
150
151         local_irq_save(flags);
152
153         /*
154          * fbdev will set an entire colourmap, but X won't.  Hopefully
155          * this should accommodate both of them
156          */
157         if (regno != lastreg + 1) {
158                 int i;
159
160                 /* Stab in the dark trying to reset the CLUT pointer */
161                 nubus_writel(0, &dafb_cmap_regs->reset);
162                 nop();
163
164                 /* Loop until we get to the register we want */
165                 for (i = 0; i < regno; i++) {
166                         nubus_writeb(info->cmap.red[i] >> 8,
167                                      &dafb_cmap_regs->lut);
168                         nop();
169                         nubus_writeb(info->cmap.green[i] >> 8,
170                                      &dafb_cmap_regs->lut);
171                         nop();
172                         nubus_writeb(info->cmap.blue[i] >> 8,
173                                      &dafb_cmap_regs->lut);
174                         nop();
175                 }
176         }
177
178         nubus_writeb(red, &dafb_cmap_regs->lut);
179         nop();
180         nubus_writeb(green, &dafb_cmap_regs->lut);
181         nop();
182         nubus_writeb(blue, &dafb_cmap_regs->lut);
183
184         local_irq_restore(flags);
185         lastreg = regno;
186         return 0;
187 }
188
189 /* V8 and Brazil seem to use the same DAC.  Sonora does as well. */
190 static int v8_brazil_setpalette(unsigned int regno, unsigned int red,
191                                 unsigned int green, unsigned int blue,
192                                 struct fb_info *info)
193 {
194         unsigned int bpp = info->var.bits_per_pixel;
195         unsigned long flags;
196
197         local_irq_save(flags);
198
199         /* On these chips, the CLUT register numbers are spread out
200          * across the register space.  Thus:
201          * In 8bpp, all regnos are valid.
202          * In 4bpp, the regnos are 0x0f, 0x1f, 0x2f, etc, etc
203          * In 2bpp, the regnos are 0x3f, 0x7f, 0xbf, 0xff
204          */
205         regno = (regno << (8 - bpp)) | (0xFF >> bpp);
206         nubus_writeb(regno, &v8_brazil_cmap_regs->addr);
207         nop();
208
209         /* send one color channel at a time */
210         nubus_writeb(red, &v8_brazil_cmap_regs->lut);
211         nop();
212         nubus_writeb(green, &v8_brazil_cmap_regs->lut);
213         nop();
214         nubus_writeb(blue, &v8_brazil_cmap_regs->lut);
215
216         local_irq_restore(flags);
217         return 0;
218 }
219
220 /* RAM-Based Video */
221 static int rbv_setpalette(unsigned int regno, unsigned int red,
222                           unsigned int green, unsigned int blue,
223                           struct fb_info *info)
224 {
225         unsigned long flags;
226
227         local_irq_save(flags);
228
229         /* From the VideoToolbox driver.  Seems to be saying that
230          * regno #254 and #255 are the important ones for 1-bit color,
231          * regno #252-255 are the important ones for 2-bit color, etc.
232          */
233         regno += 256 - (1 << info->var.bits_per_pixel);
234
235         /* reset clut? (VideoToolbox sez "not necessary") */
236         nubus_writeb(0xFF, &rbv_cmap_regs->cntl);
237         nop();
238
239         /* tell clut which address to use. */
240         nubus_writeb(regno, &rbv_cmap_regs->addr);
241         nop();
242
243         /* send one color channel at a time. */
244         nubus_writeb(red, &rbv_cmap_regs->lut);
245         nop();
246         nubus_writeb(green, &rbv_cmap_regs->lut);
247         nop();
248         nubus_writeb(blue, &rbv_cmap_regs->lut);
249
250         local_irq_restore(flags);
251         return 0;
252 }
253
254 /* Macintosh Display Card (8*24) */
255 static int mdc_setpalette(unsigned int regno, unsigned int red,
256                           unsigned int green, unsigned int blue,
257                           struct fb_info *info)
258 {
259         struct mdc_cmap_regs *cmap_regs = slot_addr;
260         unsigned long flags;
261
262         local_irq_save(flags);
263
264         /* the nop's are there to order writes. */
265         nubus_writeb(regno, &cmap_regs->addr);
266         nop();
267         nubus_writeb(red, &cmap_regs->lut);
268         nop();
269         nubus_writeb(green, &cmap_regs->lut);
270         nop();
271         nubus_writeb(blue, &cmap_regs->lut);
272
273         local_irq_restore(flags);
274         return 0;
275 }
276
277 /* Toby frame buffer */
278 static int toby_setpalette(unsigned int regno, unsigned int red,
279                            unsigned int green, unsigned int blue,
280                            struct fb_info *info)
281 {
282         struct toby_cmap_regs *cmap_regs = slot_addr;
283         unsigned int bpp = info->var.bits_per_pixel;
284         unsigned long flags;
285
286         red = ~red;
287         green = ~green;
288         blue = ~blue;
289         regno = (regno << (8 - bpp)) | (0xFF >> bpp);
290
291         local_irq_save(flags);
292
293         nubus_writeb(regno, &cmap_regs->addr);
294         nop();
295         nubus_writeb(red, &cmap_regs->lut);
296         nop();
297         nubus_writeb(green, &cmap_regs->lut);
298         nop();
299         nubus_writeb(blue, &cmap_regs->lut);
300
301         local_irq_restore(flags);
302         return 0;
303 }
304
305 /* Jet frame buffer */
306 static int jet_setpalette(unsigned int regno, unsigned int red,
307                           unsigned int green, unsigned int blue,
308                           struct fb_info *info)
309 {
310         struct jet_cmap_regs *cmap_regs = slot_addr;
311         unsigned long flags;
312
313         local_irq_save(flags);
314
315         nubus_writeb(regno, &cmap_regs->addr);
316         nop();
317         nubus_writeb(red, &cmap_regs->lut);
318         nop();
319         nubus_writeb(green, &cmap_regs->lut);
320         nop();
321         nubus_writeb(blue, &cmap_regs->lut);
322
323         local_irq_restore(flags);
324         return 0;
325 }
326
327 /*
328  * Civic framebuffer -- Quadra AV built-in video.  A chip
329  * called Sebastian holds the actual color palettes, and
330  * apparently, there are two different banks of 512K RAM
331  * which can act as separate framebuffers for doing video
332  * input and viewing the screen at the same time!  The 840AV
333  * Can add another 1MB RAM to give the two framebuffers
334  * 1MB RAM apiece.
335  */
336 static int civic_setpalette(unsigned int regno, unsigned int red,
337                             unsigned int green, unsigned int blue,
338                             struct fb_info *info)
339 {
340         unsigned long flags;
341         int clut_status;
342         
343         local_irq_save(flags);
344
345         /* Set the register address */
346         nubus_writeb(regno, &civic_cmap_regs->addr);
347         nop();
348
349         /*
350          * Grab a status word and do some checking;
351          * Then finally write the clut!
352          */
353         clut_status =  nubus_readb(&civic_cmap_regs->status2);
354
355         if ((clut_status & 0x0008) == 0)
356         {
357 #if 0
358                 if ((clut_status & 0x000D) != 0)
359                 {
360                         nubus_writeb(0x00, &civic_cmap_regs->lut);
361                         nop();
362                         nubus_writeb(0x00, &civic_cmap_regs->lut);
363                         nop();
364                 }
365 #endif
366
367                 nubus_writeb(red, &civic_cmap_regs->lut);
368                 nop();
369                 nubus_writeb(green, &civic_cmap_regs->lut);
370                 nop();
371                 nubus_writeb(blue, &civic_cmap_regs->lut);
372                 nop();
373                 nubus_writeb(0x00, &civic_cmap_regs->lut);
374         }
375         else
376         {
377                 unsigned char junk;
378
379                 junk = nubus_readb(&civic_cmap_regs->lut);
380                 nop();
381                 junk = nubus_readb(&civic_cmap_regs->lut);
382                 nop();
383                 junk = nubus_readb(&civic_cmap_regs->lut);
384                 nop();
385                 junk = nubus_readb(&civic_cmap_regs->lut);
386                 nop();
387
388                 if ((clut_status & 0x000D) != 0)
389                 {
390                         nubus_writeb(0x00, &civic_cmap_regs->lut);
391                         nop();
392                         nubus_writeb(0x00, &civic_cmap_regs->lut);
393                         nop();
394                 }
395
396                 nubus_writeb(red, &civic_cmap_regs->lut);
397                 nop();
398                 nubus_writeb(green, &civic_cmap_regs->lut);
399                 nop();
400                 nubus_writeb(blue, &civic_cmap_regs->lut);
401                 nop();
402                 nubus_writeb(junk, &civic_cmap_regs->lut);
403         }
404
405         local_irq_restore(flags);
406         return 0;
407 }
408
409 /*
410  * The CSC is the framebuffer on the PowerBook 190 series
411  * (and the 5300 too, but that's a PowerMac). This function
412  * brought to you in part by the ECSC driver for MkLinux.
413  */
414 static int csc_setpalette(unsigned int regno, unsigned int red,
415                           unsigned int green, unsigned int blue,
416                           struct fb_info *info)
417 {
418         unsigned long flags;
419
420         local_irq_save(flags);
421
422         udelay(1); /* mklinux on PB 5300 waits for 260 ns */
423         nubus_writeb(regno, &csc_cmap_regs->clut_waddr);
424         nubus_writeb(red, &csc_cmap_regs->clut_data);
425         nubus_writeb(green, &csc_cmap_regs->clut_data);
426         nubus_writeb(blue, &csc_cmap_regs->clut_data);
427
428         local_irq_restore(flags);
429         return 0;
430 }
431
432 static int macfb_setcolreg(unsigned regno, unsigned red, unsigned green,
433                            unsigned blue, unsigned transp,
434                            struct fb_info *fb_info)
435 {
436         /*
437          * Set a single color register. The values supplied are
438          * already rounded down to the hardware's capabilities
439          * (according to the entries in the `var' structure).
440          * Return non-zero for invalid regno.
441          */
442         
443         if (regno >= fb_info->cmap.len)
444                 return 1;
445
446         if (fb_info->var.bits_per_pixel <= 8) {
447                 switch (fb_info->var.bits_per_pixel) {
448                 case 1:
449                         /* We shouldn't get here */
450                         break;
451                 case 2:
452                 case 4:
453                 case 8:
454                         if (macfb_setpalette)
455                                 macfb_setpalette(regno, red >> 8, green >> 8,
456                                                  blue >> 8, fb_info);
457                         else
458                                 return 1;
459                         break;
460                 }
461         } else if (regno < 16) {
462                 switch (fb_info->var.bits_per_pixel) {
463                 case 16:
464                         if (fb_info->var.red.offset == 10) {
465                                 /* 1:5:5:5 */
466                                 ((u32*) (fb_info->pseudo_palette))[regno] =
467                                         ((red   & 0xf800) >>  1) |
468                                         ((green & 0xf800) >>  6) |
469                                         ((blue  & 0xf800) >> 11) |
470                                         ((transp != 0) << 15);
471                         } else {
472                                 /* 0:5:6:5 */
473                                 ((u32*) (fb_info->pseudo_palette))[regno] =
474                                         ((red   & 0xf800) >>  0) |
475                                         ((green & 0xfc00) >>  5) |
476                                         ((blue  & 0xf800) >> 11);
477                         }
478                         break;
479                 /*
480                  * 24-bit colour almost doesn't exist on 68k Macs --
481                  * http://support.apple.com/kb/TA28634 (Old Article: 10992)
482                  */
483                 case 24:
484                 case 32:
485                         red   >>= 8;
486                         green >>= 8;
487                         blue  >>= 8;
488                         ((u32 *)(fb_info->pseudo_palette))[regno] =
489                                 (red   << fb_info->var.red.offset) |
490                                 (green << fb_info->var.green.offset) |
491                                 (blue  << fb_info->var.blue.offset);
492                         break;
493                 }
494         }
495
496         return 0;
497 }
498
499 static const struct fb_ops macfb_ops = {
500         .owner          = THIS_MODULE,
501         .fb_setcolreg   = macfb_setcolreg,
502         .fb_fillrect    = cfb_fillrect,
503         .fb_copyarea    = cfb_copyarea,
504         .fb_imageblit   = cfb_imageblit,
505 };
506
507 static void __init macfb_setup(char *options)
508 {
509         char *this_opt;
510
511         if (!options || !*options)
512                 return;
513
514         while ((this_opt = strsep(&options, ",")) != NULL) {
515                 if (!*this_opt)
516                         continue;
517
518                 if (!strcmp(this_opt, "inverse"))
519                         fb_invert_cmaps();
520                 else
521                         if (!strcmp(this_opt, "vidtest"))
522                                 vidtest = 1; /* enable experimental CLUT code */
523         }
524 }
525
526 static void __init iounmap_macfb(void)
527 {
528         if (dafb_cmap_regs)
529                 iounmap(dafb_cmap_regs);
530         if (v8_brazil_cmap_regs)
531                 iounmap(v8_brazil_cmap_regs);
532         if (rbv_cmap_regs)
533                 iounmap(rbv_cmap_regs);
534         if (civic_cmap_regs)
535                 iounmap(civic_cmap_regs);
536         if (csc_cmap_regs)
537                 iounmap(csc_cmap_regs);
538 }
539
540 static int __init macfb_init(void)
541 {
542         int video_cmap_len, video_is_nubus = 0;
543         struct nubus_rsrc *ndev = NULL;
544         char *option = NULL;
545         int err;
546
547         if (fb_get_options("macfb", &option))
548                 return -ENODEV;
549         macfb_setup(option);
550
551         if (!MACH_IS_MAC) 
552                 return -ENODEV;
553
554         if (mac_bi_data.id == MAC_MODEL_Q630 ||
555             mac_bi_data.id == MAC_MODEL_P588)
556                 return -ENODEV; /* See valkyriefb.c */
557
558         macfb_defined.xres = mac_bi_data.dimensions & 0xFFFF;
559         macfb_defined.yres = mac_bi_data.dimensions >> 16;
560         macfb_defined.bits_per_pixel = mac_bi_data.videodepth;
561
562         macfb_fix.line_length = mac_bi_data.videorow;
563         macfb_fix.smem_len    = macfb_fix.line_length * macfb_defined.yres;
564         /* Note: physical address (since 2.1.127) */
565         macfb_fix.smem_start  = mac_bi_data.videoaddr;
566
567         /*
568          * This is actually redundant with the initial mappings.
569          * However, there are some non-obvious aspects to the way
570          * those mappings are set up, so this is in fact the safest
571          * way to ensure that this driver will work on every possible Mac
572          */
573         fb_info.screen_base = ioremap(mac_bi_data.videoaddr,
574                                       macfb_fix.smem_len);
575         if (!fb_info.screen_base)
576                 return -ENODEV;
577
578         pr_info("macfb: framebuffer at 0x%08lx, mapped to 0x%p, size %dk\n",
579                 macfb_fix.smem_start, fb_info.screen_base,
580                 macfb_fix.smem_len / 1024);
581         pr_info("macfb: mode is %dx%dx%d, linelength=%d\n",
582                 macfb_defined.xres, macfb_defined.yres,
583                 macfb_defined.bits_per_pixel, macfb_fix.line_length);
584
585         /* Fill in the available video resolution */
586         macfb_defined.xres_virtual = macfb_defined.xres;
587         macfb_defined.yres_virtual = macfb_defined.yres;
588         macfb_defined.height       = PIXEL_TO_MM(macfb_defined.yres);
589         macfb_defined.width        = PIXEL_TO_MM(macfb_defined.xres);
590
591         /* Some dummy values for timing to make fbset happy */
592         macfb_defined.pixclock     = 10000000 / macfb_defined.xres *
593                                      1000 / macfb_defined.yres;
594         macfb_defined.left_margin  = (macfb_defined.xres / 8) & 0xf8;
595         macfb_defined.hsync_len    = (macfb_defined.xres / 8) & 0xf8;
596
597         switch (macfb_defined.bits_per_pixel) {
598         case 1:
599                 macfb_defined.red.length = macfb_defined.bits_per_pixel;
600                 macfb_defined.green.length = macfb_defined.bits_per_pixel;
601                 macfb_defined.blue.length = macfb_defined.bits_per_pixel;
602                 video_cmap_len = 2;
603                 macfb_fix.visual = FB_VISUAL_MONO01;
604                 break;
605         case 2:
606         case 4:
607         case 8:
608                 macfb_defined.red.length = macfb_defined.bits_per_pixel;
609                 macfb_defined.green.length = macfb_defined.bits_per_pixel;
610                 macfb_defined.blue.length = macfb_defined.bits_per_pixel;
611                 video_cmap_len = 1 << macfb_defined.bits_per_pixel;
612                 macfb_fix.visual = FB_VISUAL_PSEUDOCOLOR;
613                 break;
614         case 16:
615                 macfb_defined.transp.offset = 15;
616                 macfb_defined.transp.length = 1;
617                 macfb_defined.red.offset = 10;
618                 macfb_defined.red.length = 5;
619                 macfb_defined.green.offset = 5;
620                 macfb_defined.green.length = 5;
621                 macfb_defined.blue.offset = 0;
622                 macfb_defined.blue.length = 5;
623                 video_cmap_len = 16;
624                 /*
625                  * Should actually be FB_VISUAL_DIRECTCOLOR, but this
626                  * works too
627                  */
628                 macfb_fix.visual = FB_VISUAL_TRUECOLOR;
629                 break;
630         case 24:
631         case 32:
632                 macfb_defined.red.offset = 16;
633                 macfb_defined.red.length = 8;
634                 macfb_defined.green.offset = 8;
635                 macfb_defined.green.length = 8;
636                 macfb_defined.blue.offset = 0;
637                 macfb_defined.blue.length = 8;
638                 video_cmap_len = 16;
639                 macfb_fix.visual = FB_VISUAL_TRUECOLOR;
640                 break;
641         default:
642                 pr_err("macfb: unknown or unsupported bit depth: %d\n",
643                        macfb_defined.bits_per_pixel);
644                 err = -EINVAL;
645                 goto fail_unmap;
646         }
647         
648         /*
649          * We take a wild guess that if the video physical address is
650          * in nubus slot space, that the nubus card is driving video.
651          * Penguin really ought to tell us whether we are using internal
652          * video or not.
653          * Hopefully we only find one of them.  Otherwise our NuBus
654          * code is really broken :-)
655          */
656
657         for_each_func_rsrc(ndev) {
658                 unsigned long base = ndev->board->slot_addr;
659
660                 if (mac_bi_data.videoaddr < base ||
661                     mac_bi_data.videoaddr - base > 0xFFFFFF)
662                         continue;
663
664                 if (ndev->category != NUBUS_CAT_DISPLAY ||
665                     ndev->type != NUBUS_TYPE_VIDEO)
666                         continue;
667
668                 video_is_nubus = 1;
669                 slot_addr = (unsigned char *)base;
670
671                 switch(ndev->dr_hw) {
672                 case NUBUS_DRHW_APPLE_MDC:
673                         strcpy(macfb_fix.id, "Mac Disp. Card");
674                         macfb_setpalette = mdc_setpalette;
675                         break;
676                 case NUBUS_DRHW_APPLE_TFB:
677                         strcpy(macfb_fix.id, "Toby");
678                         macfb_setpalette = toby_setpalette;
679                         break;
680                 case NUBUS_DRHW_APPLE_JET:
681                         strcpy(macfb_fix.id, "Jet");
682                         macfb_setpalette = jet_setpalette;
683                         break;
684                 default:
685                         strcpy(macfb_fix.id, "Generic NuBus");
686                         break;
687                 }
688         }
689
690         /* If it's not a NuBus card, it must be internal video */
691         if (!video_is_nubus)
692                 switch (mac_bi_data.id) {
693                 /*
694                  * DAFB Quadras
695                  * Note: these first four have the v7 DAFB, which is
696                  * known to be rather unlike the ones used in the
697                  * other models
698                  */
699                 case MAC_MODEL_P475:
700                 case MAC_MODEL_P475F:
701                 case MAC_MODEL_P575:
702                 case MAC_MODEL_Q605:
703
704                 case MAC_MODEL_Q800:
705                 case MAC_MODEL_Q650:
706                 case MAC_MODEL_Q610:
707                 case MAC_MODEL_C650:
708                 case MAC_MODEL_C610:
709                 case MAC_MODEL_Q700:
710                 case MAC_MODEL_Q900:
711                 case MAC_MODEL_Q950:
712                         strcpy(macfb_fix.id, "DAFB");
713                         macfb_setpalette = dafb_setpalette;
714                         dafb_cmap_regs = ioremap(DAFB_BASE, 0x1000);
715                         break;
716
717                 /*
718                  * LC II uses the V8 framebuffer
719                  */
720                 case MAC_MODEL_LCII:
721                         strcpy(macfb_fix.id, "V8");
722                         macfb_setpalette = v8_brazil_setpalette;
723                         v8_brazil_cmap_regs = ioremap(DAC_BASE, 0x1000);
724                         break;
725
726                 /*
727                  * IIvi, IIvx use the "Brazil" framebuffer (which is
728                  * very much like the V8, it seems, and probably uses
729                  * the same DAC)
730                  */
731                 case MAC_MODEL_IIVI:
732                 case MAC_MODEL_IIVX:
733                 case MAC_MODEL_P600:
734                         strcpy(macfb_fix.id, "Brazil");
735                         macfb_setpalette = v8_brazil_setpalette;
736                         v8_brazil_cmap_regs = ioremap(DAC_BASE, 0x1000);
737                         break;
738
739                 /*
740                  * LC III (and friends) use the Sonora framebuffer
741                  * Incidentally this is also used in the non-AV models
742                  * of the x100 PowerMacs
743                  * These do in fact seem to use the same DAC interface
744                  * as the LC II.
745                  */
746                 case MAC_MODEL_LCIII:
747                 case MAC_MODEL_P520:
748                 case MAC_MODEL_P550:
749                 case MAC_MODEL_P460:
750                         strcpy(macfb_fix.id, "Sonora");
751                         macfb_setpalette = v8_brazil_setpalette;
752                         v8_brazil_cmap_regs = ioremap(DAC_BASE, 0x1000);
753                         break;
754
755                 /*
756                  * IIci and IIsi use the infamous RBV chip
757                  * (the IIsi is just a rebadged and crippled
758                  * IIci in a different case, BTW)
759                  */
760                 case MAC_MODEL_IICI:
761                 case MAC_MODEL_IISI:
762                         strcpy(macfb_fix.id, "RBV");
763                         macfb_setpalette = rbv_setpalette;
764                         rbv_cmap_regs = ioremap(DAC_BASE, 0x1000);
765                         break;
766
767                 /*
768                  * AVs use the Civic framebuffer
769                  */
770                 case MAC_MODEL_Q840:
771                 case MAC_MODEL_C660:
772                         strcpy(macfb_fix.id, "Civic");
773                         macfb_setpalette = civic_setpalette;
774                         civic_cmap_regs = ioremap(CIVIC_BASE, 0x1000);
775                         break;
776
777                 
778                 /*
779                  * Assorted weirdos
780                  * We think this may be like the LC II
781                  */
782                 case MAC_MODEL_LC:
783                         strcpy(macfb_fix.id, "LC");
784                         if (vidtest) {
785                                 macfb_setpalette = v8_brazil_setpalette;
786                                 v8_brazil_cmap_regs =
787                                         ioremap(DAC_BASE, 0x1000);
788                         }
789                         break;
790
791                 /*
792                  * We think this may be like the LC II
793                  */
794                 case MAC_MODEL_CCL:
795                         strcpy(macfb_fix.id, "Color Classic");
796                         if (vidtest) {
797                                 macfb_setpalette = v8_brazil_setpalette;
798                                 v8_brazil_cmap_regs =
799                                         ioremap(DAC_BASE, 0x1000);
800                         }
801                         break;
802
803                 /*
804                  * And we *do* mean "weirdos"
805                  */
806                 case MAC_MODEL_TV:
807                         strcpy(macfb_fix.id, "Mac TV");
808                         break;
809
810                 /*
811                  * These don't have colour, so no need to worry
812                  */
813                 case MAC_MODEL_SE30:
814                 case MAC_MODEL_CLII:
815                         strcpy(macfb_fix.id, "Monochrome");
816                         break;
817
818                 /*
819                  * Powerbooks are particularly difficult.  Many of
820                  * them have separate framebuffers for external and
821                  * internal video, which is admittedly pretty cool,
822                  * but will be a bit of a headache to support here.
823                  * Also, many of them are grayscale, and we don't
824                  * really support that.
825                  */
826
827                 /*
828                  * Slot 0 ROM says TIM. No external video. B&W.
829                  */
830                 case MAC_MODEL_PB140:
831                 case MAC_MODEL_PB145:
832                 case MAC_MODEL_PB170:
833                         strcpy(macfb_fix.id, "DDC");
834                         break;
835
836                 /*
837                  * Internal is GSC, External (if present) is ViSC
838                  */
839                 case MAC_MODEL_PB150:   /* no external video */
840                 case MAC_MODEL_PB160:
841                 case MAC_MODEL_PB165:
842                 case MAC_MODEL_PB180:
843                 case MAC_MODEL_PB210:
844                 case MAC_MODEL_PB230:
845                         strcpy(macfb_fix.id, "GSC");
846                         break;
847
848                 /*
849                  * Internal is TIM, External is ViSC
850                  */
851                 case MAC_MODEL_PB165C:
852                 case MAC_MODEL_PB180C:
853                         strcpy(macfb_fix.id, "TIM");
854                         break;
855
856                 /*
857                  * Internal is CSC, External is Keystone+Ariel.
858                  */
859                 case MAC_MODEL_PB190:   /* external video is optional */
860                 case MAC_MODEL_PB520:
861                 case MAC_MODEL_PB250:
862                 case MAC_MODEL_PB270C:
863                 case MAC_MODEL_PB280:
864                 case MAC_MODEL_PB280C:
865                         strcpy(macfb_fix.id, "CSC");
866                         macfb_setpalette = csc_setpalette;
867                         csc_cmap_regs = ioremap(CSC_BASE, 0x1000);
868                         break;
869
870                 default:
871                         strcpy(macfb_fix.id, "Unknown");
872                         break;
873                 }
874
875         fb_info.fbops           = &macfb_ops;
876         fb_info.var             = macfb_defined;
877         fb_info.fix             = macfb_fix;
878         fb_info.pseudo_palette  = pseudo_palette;
879         fb_info.flags           = FBINFO_DEFAULT;
880
881         err = fb_alloc_cmap(&fb_info.cmap, video_cmap_len, 0);
882         if (err)
883                 goto fail_unmap;
884
885         err = register_framebuffer(&fb_info);
886         if (err)
887                 goto fail_dealloc;
888
889         fb_info(&fb_info, "%s frame buffer device\n", fb_info.fix.id);
890
891         return 0;
892
893 fail_dealloc:
894         fb_dealloc_cmap(&fb_info.cmap);
895 fail_unmap:
896         iounmap(fb_info.screen_base);
897         iounmap_macfb();
898         return err;
899 }
900
901 module_init(macfb_init);
902 MODULE_LICENSE("GPL");