Linux-2.6.12-rc2
[safe/jmp/linux-2.6] / drivers / video / aty / atyfb_base.c
1 /*
2  *  ATI Frame Buffer Device Driver Core
3  *
4  *      Copyright (C) 2004  Alex Kern <alex.kern@gmx.de>
5  *      Copyright (C) 1997-2001  Geert Uytterhoeven
6  *      Copyright (C) 1998  Bernd Harries
7  *      Copyright (C) 1998  Eddie C. Dost  (ecd@skynet.be)
8  *
9  *  This driver supports the following ATI graphics chips:
10  *    - ATI Mach64
11  *
12  *  To do: add support for
13  *    - ATI Rage128 (from aty128fb.c)
14  *    - ATI Radeon (from radeonfb.c)
15  *
16  *  This driver is partly based on the PowerMac console driver:
17  *
18  *      Copyright (C) 1996 Paul Mackerras
19  *
20  *  and on the PowerMac ATI/mach64 display driver:
21  *
22  *      Copyright (C) 1997 Michael AK Tesch
23  *
24  *            with work by Jon Howell
25  *                         Harry AC Eaton
26  *                         Anthony Tong <atong@uiuc.edu>
27  *
28  *  Generic LCD support written by Daniel Mantione, ported from 2.4.20 by Alex Kern
29  *  Many Thanks to Ville Syrjälä for patches and fixing nasting 16 bit color bug.
30  *
31  *  This file is subject to the terms and conditions of the GNU General Public
32  *  License. See the file COPYING in the main directory of this archive for
33  *  more details.
34  *
35  *  Many thanks to Nitya from ATI devrel for support and patience !
36  */
37
38 /******************************************************************************
39
40   TODO:
41
42     - cursor support on all cards and all ramdacs.
43     - cursor parameters controlable via ioctl()s.
44     - guess PLL and MCLK based on the original PLL register values initialized
45       by Open Firmware (if they are initialized). BIOS is done
46
47     (Anyone with Mac to help with this?)
48
49 ******************************************************************************/
50
51
52 #include <linux/config.h>
53 #include <linux/module.h>
54 #include <linux/moduleparam.h>
55 #include <linux/kernel.h>
56 #include <linux/errno.h>
57 #include <linux/string.h>
58 #include <linux/mm.h>
59 #include <linux/slab.h>
60 #include <linux/vmalloc.h>
61 #include <linux/delay.h>
62 #include <linux/console.h>
63 #include <linux/fb.h>
64 #include <linux/init.h>
65 #include <linux/pci.h>
66 #include <linux/interrupt.h>
67 #include <linux/spinlock.h>
68 #include <linux/wait.h>
69
70 #include <asm/io.h>
71 #include <asm/uaccess.h>
72
73 #include <video/mach64.h>
74 #include "atyfb.h"
75 #include "ati_ids.h"
76
77 #ifdef __powerpc__
78 #include <asm/prom.h>
79 #include "../macmodes.h"
80 #endif
81 #ifdef __sparc__
82 #include <asm/pbm.h>
83 #include <asm/fbio.h>
84 #endif
85
86 #ifdef CONFIG_ADB_PMU
87 #include <linux/adb.h>
88 #include <linux/pmu.h>
89 #endif
90 #ifdef CONFIG_BOOTX_TEXT
91 #include <asm/btext.h>
92 #endif
93 #ifdef CONFIG_PMAC_BACKLIGHT
94 #include <asm/backlight.h>
95 #endif
96 #ifdef CONFIG_MTRR
97 #include <asm/mtrr.h>
98 #endif
99
100 /*
101  * Debug flags.
102  */
103 #undef DEBUG
104 /*#define DEBUG*/
105
106 /* Make sure n * PAGE_SIZE is protected at end of Aperture for GUI-regs */
107 /*  - must be large enough to catch all GUI-Regs   */
108 /*  - must be aligned to a PAGE boundary           */
109 #define GUI_RESERVE     (1 * PAGE_SIZE)
110
111 /* FIXME: remove the FAIL definition */
112 #define FAIL(msg) do { printk(KERN_CRIT "atyfb: " msg "\n"); return -EINVAL; } while (0)
113 #define FAIL_MAX(msg, x, _max_) do { if(x > _max_) { printk(KERN_CRIT "atyfb: " msg " %x(%x)\n", x, _max_); return -EINVAL; } } while (0)
114
115 #ifdef DEBUG
116 #define DPRINTK(fmt, args...)   printk(KERN_DEBUG "atyfb: " fmt, ## args)
117 #else
118 #define DPRINTK(fmt, args...)
119 #endif
120
121 #define PRINTKI(fmt, args...)   printk(KERN_INFO "atyfb: " fmt, ## args)
122 #define PRINTKE(fmt, args...)    printk(KERN_ERR "atyfb: " fmt, ## args)
123
124 #if defined(CONFIG_PM) || defined(CONFIG_PMAC_BACKLIGHT) || defined (CONFIG_FB_ATY_GENERIC_LCD)
125 static const u32 lt_lcd_regs[] = {
126         CONFIG_PANEL_LG,
127         LCD_GEN_CNTL_LG,
128         DSTN_CONTROL_LG,
129         HFB_PITCH_ADDR_LG,
130         HORZ_STRETCHING_LG,
131         VERT_STRETCHING_LG,
132         0, /* EXT_VERT_STRETCH */
133         LT_GIO_LG,
134         POWER_MANAGEMENT_LG
135 };
136
137 void aty_st_lcd(int index, u32 val, const struct atyfb_par *par)
138 {
139         if (M64_HAS(LT_LCD_REGS)) {
140                 aty_st_le32(lt_lcd_regs[index], val, par);
141         } else {
142                 unsigned long temp;
143
144                 /* write addr byte */
145                 temp = aty_ld_le32(LCD_INDEX, par);
146                 aty_st_le32(LCD_INDEX, (temp & ~LCD_INDEX_MASK) | index, par);
147                 /* write the register value */
148                 aty_st_le32(LCD_DATA, val, par);
149         }
150 }
151
152 u32 aty_ld_lcd(int index, const struct atyfb_par *par)
153 {
154         if (M64_HAS(LT_LCD_REGS)) {
155                 return aty_ld_le32(lt_lcd_regs[index], par);
156         } else {
157                 unsigned long temp;
158
159                 /* write addr byte */
160                 temp = aty_ld_le32(LCD_INDEX, par);
161                 aty_st_le32(LCD_INDEX, (temp & ~LCD_INDEX_MASK) | index, par);
162                 /* read the register value */
163                 return aty_ld_le32(LCD_DATA, par);
164         }
165 }
166 #endif /* defined(CONFIG_PM) || defined(CONFIG_PMAC_BACKLIGHT) || defined (CONFIG_FB_ATY_GENERIC_LCD) */
167
168 #ifdef CONFIG_FB_ATY_GENERIC_LCD
169 /*
170  * ATIReduceRatio --
171  *
172  * Reduce a fraction by factoring out the largest common divider of the
173  * fraction's numerator and denominator.
174  */
175 static void ATIReduceRatio(int *Numerator, int *Denominator)
176 {
177     int Multiplier, Divider, Remainder;
178
179     Multiplier = *Numerator;
180     Divider = *Denominator;
181
182     while ((Remainder = Multiplier % Divider))
183     {
184         Multiplier = Divider;
185         Divider = Remainder;
186     }
187
188     *Numerator /= Divider;
189     *Denominator /= Divider;
190 }
191 #endif
192     /*
193      *  The Hardware parameters for each card
194      */
195
196 struct aty_cmap_regs {
197         u8 windex;
198         u8 lut;
199         u8 mask;
200         u8 rindex;
201         u8 cntl;
202 };
203
204 struct pci_mmap_map {
205         unsigned long voff;
206         unsigned long poff;
207         unsigned long size;
208         unsigned long prot_flag;
209         unsigned long prot_mask;
210 };
211
212 static struct fb_fix_screeninfo atyfb_fix __devinitdata = {
213         .id             = "ATY Mach64",
214         .type           = FB_TYPE_PACKED_PIXELS,
215         .visual         = FB_VISUAL_PSEUDOCOLOR,
216         .xpanstep       = 8,
217         .ypanstep       = 1,
218 };
219
220     /*
221      *  Frame buffer device API
222      */
223
224 static int atyfb_open(struct fb_info *info, int user);
225 static int atyfb_release(struct fb_info *info, int user);
226 static int atyfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info);
227 static int atyfb_set_par(struct fb_info *info);
228 static int atyfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
229         u_int transp, struct fb_info *info);
230 static int atyfb_pan_display(struct fb_var_screeninfo *var, struct fb_info *info);
231 static int atyfb_blank(int blank, struct fb_info *info);
232 static int atyfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
233         u_long arg, struct fb_info *info);
234 extern void atyfb_fillrect(struct fb_info *info, const struct fb_fillrect *rect);
235 extern void atyfb_copyarea(struct fb_info *info, const struct fb_copyarea *area);
236 extern void atyfb_imageblit(struct fb_info *info, const struct fb_image *image);
237 #ifdef __sparc__
238 static int atyfb_mmap(struct fb_info *info, struct file *file, struct vm_area_struct *vma);
239 #endif
240 static int atyfb_sync(struct fb_info *info);
241
242     /*
243      *  Internal routines
244      */
245
246 static int aty_init(struct fb_info *info, const char *name);
247 #ifdef CONFIG_ATARI
248 static int store_video_par(char *videopar, unsigned char m64_num);
249 #endif
250
251 static struct crtc saved_crtc;
252 static union aty_pll saved_pll;
253 static void aty_get_crtc(const struct atyfb_par *par, struct crtc *crtc);
254
255 static void aty_set_crtc(const struct atyfb_par *par, const struct crtc *crtc);
256 static int aty_var_to_crtc(const struct fb_info *info, const struct fb_var_screeninfo *var, struct crtc *crtc);
257 static int aty_crtc_to_var(const struct crtc *crtc, struct fb_var_screeninfo *var);
258 static void set_off_pitch(struct atyfb_par *par, const struct fb_info *info);
259 #ifdef CONFIG_PPC
260 static int read_aty_sense(const struct atyfb_par *par);
261 #endif
262
263
264     /*
265      *  Interface used by the world
266      */
267
268 static struct fb_var_screeninfo default_var = {
269         /* 640x480, 60 Hz, Non-Interlaced (25.175 MHz dotclock) */
270         640, 480, 640, 480, 0, 0, 8, 0,
271         {0, 8, 0}, {0, 8, 0}, {0, 8, 0}, {0, 0, 0},
272         0, 0, -1, -1, 0, 39722, 48, 16, 33, 10, 96, 2,
273         0, FB_VMODE_NONINTERLACED
274 };
275
276 static struct fb_videomode defmode = {
277         /* 640x480 @ 60 Hz, 31.5 kHz hsync */
278         NULL, 60, 640, 480, 39721, 40, 24, 32, 11, 96, 2,
279         0, FB_VMODE_NONINTERLACED
280 };
281
282 static struct fb_ops atyfb_ops = {
283         .owner          = THIS_MODULE,
284         .fb_open        = atyfb_open,
285         .fb_release     = atyfb_release,
286         .fb_check_var   = atyfb_check_var,
287         .fb_set_par     = atyfb_set_par,
288         .fb_setcolreg   = atyfb_setcolreg,
289         .fb_pan_display = atyfb_pan_display,
290         .fb_blank       = atyfb_blank,
291         .fb_ioctl       = atyfb_ioctl,
292         .fb_fillrect    = atyfb_fillrect,
293         .fb_copyarea    = atyfb_copyarea,
294         .fb_imageblit   = atyfb_imageblit,
295         .fb_cursor      = soft_cursor,
296 #ifdef __sparc__
297         .fb_mmap        = atyfb_mmap,
298 #endif
299         .fb_sync        = atyfb_sync,
300 };
301
302 static int noaccel;
303 #ifdef CONFIG_MTRR
304 static int nomtrr;
305 #endif
306 static int vram;
307 static int pll;
308 static int mclk;
309 static int xclk;
310 static int comp_sync __initdata = -1;
311 static char *mode;
312
313 #ifdef CONFIG_PPC
314 static int default_vmode __initdata = VMODE_CHOOSE;
315 static int default_cmode __initdata = CMODE_CHOOSE;
316
317 module_param_named(vmode, default_vmode, int, 0);
318 MODULE_PARM_DESC(vmode, "int: video mode for mac");
319 module_param_named(cmode, default_cmode, int, 0);
320 MODULE_PARM_DESC(cmode, "int: color mode for mac");
321 #endif
322
323 #ifdef CONFIG_ATARI
324 static unsigned int mach64_count __initdata = 0;
325 static unsigned long phys_vmembase[FB_MAX] __initdata = { 0, };
326 static unsigned long phys_size[FB_MAX] __initdata = { 0, };
327 static unsigned long phys_guiregbase[FB_MAX] __initdata = { 0, };
328 #endif
329
330 /* top -> down is an evolution of mach64 chipset, any corrections? */
331 #define ATI_CHIP_88800GX   (M64F_GX)
332 #define ATI_CHIP_88800CX   (M64F_GX)
333
334 #define ATI_CHIP_264CT     (M64F_CT | M64F_INTEGRATED | M64F_CT_BUS | M64F_MAGIC_FIFO)
335 #define ATI_CHIP_264ET     (M64F_CT | M64F_INTEGRATED | M64F_CT_BUS | M64F_MAGIC_FIFO)
336
337 #define ATI_CHIP_264VT     (M64F_VT | M64F_INTEGRATED | M64F_VT_BUS | M64F_MAGIC_FIFO)
338 #define ATI_CHIP_264GT     (M64F_GT | M64F_INTEGRATED               | M64F_MAGIC_FIFO | M64F_EXTRA_BRIGHT)
339
340 #define ATI_CHIP_264VTB    (M64F_VT | M64F_INTEGRATED | M64F_VT_BUS | M64F_GTB_DSP)
341 #define ATI_CHIP_264VT3    (M64F_VT | M64F_INTEGRATED | M64F_VT_BUS | M64F_GTB_DSP | M64F_SDRAM_MAGIC_PLL)
342 #define ATI_CHIP_264VT4    (M64F_VT | M64F_INTEGRATED               | M64F_GTB_DSP)
343
344 #define ATI_CHIP_264LT     (M64F_GT | M64F_INTEGRATED               | M64F_GTB_DSP)
345
346 /* make sets shorter */
347 #define ATI_MODERN_SET     (M64F_GT | M64F_INTEGRATED               | M64F_GTB_DSP | M64F_EXTRA_BRIGHT)
348
349 #define ATI_CHIP_264GTB    (ATI_MODERN_SET | M64F_SDRAM_MAGIC_PLL)
350 /*#define ATI_CHIP_264GTDVD  ?*/
351 #define ATI_CHIP_264LTG    (ATI_MODERN_SET | M64F_SDRAM_MAGIC_PLL)
352
353 #define ATI_CHIP_264GT2C   (ATI_MODERN_SET | M64F_SDRAM_MAGIC_PLL | M64F_HW_TRIPLE)
354 #define ATI_CHIP_264GTPRO  (ATI_MODERN_SET | M64F_SDRAM_MAGIC_PLL | M64F_HW_TRIPLE | M64F_FIFO_32 | M64F_RESET_3D)
355 #define ATI_CHIP_264LTPRO  (ATI_MODERN_SET | M64F_HW_TRIPLE | M64F_FIFO_32 | M64F_RESET_3D)
356
357 #define ATI_CHIP_264XL     (ATI_MODERN_SET | M64F_HW_TRIPLE | M64F_FIFO_32 | M64F_RESET_3D | M64F_XL_DLL | M64F_MFB_FORCE_4)
358 #define ATI_CHIP_MOBILITY  (ATI_MODERN_SET | M64F_HW_TRIPLE | M64F_FIFO_32 | M64F_RESET_3D | M64F_XL_DLL | M64F_MFB_FORCE_4 | M64F_MOBIL_BUS)
359
360 static struct {
361         u16 pci_id;
362         const char *name;
363         int pll, mclk, xclk;
364         u32 features;
365 } aty_chips[] __devinitdata = {
366 #ifdef CONFIG_FB_ATY_GX
367         /* Mach64 GX */
368         { PCI_CHIP_MACH64GX, "ATI888GX00 (Mach64 GX)", 135, 50, 50, ATI_CHIP_88800GX },
369         { PCI_CHIP_MACH64CX, "ATI888CX00 (Mach64 CX)", 135, 50, 50, ATI_CHIP_88800CX },
370 #endif /* CONFIG_FB_ATY_GX */
371
372 #ifdef CONFIG_FB_ATY_CT
373         { PCI_CHIP_MACH64CT, "ATI264CT (Mach64 CT)", 135, 60, 60, ATI_CHIP_264CT },
374         { PCI_CHIP_MACH64ET, "ATI264ET (Mach64 ET)", 135, 60, 60, ATI_CHIP_264ET },
375         { PCI_CHIP_MACH64VT, "ATI264VT? (Mach64 VT)", 170, 67, 67, ATI_CHIP_264VT },
376         { PCI_CHIP_MACH64GT, "3D RAGE (Mach64 GT)", 135, 63, 63, ATI_CHIP_264GT },
377         /* FIXME { ...ATI_264GU, maybe ATI_CHIP_264GTDVD }, */
378         { PCI_CHIP_MACH64GU, "3D RAGE II+ (Mach64 GTB)", 200, 67, 67, ATI_CHIP_264GTB  },
379         { PCI_CHIP_MACH64VU, "ATI264VTB (Mach64 VU)", 200, 67, 67, ATI_CHIP_264VT3 },
380
381         { PCI_CHIP_MACH64LT, "3D RAGE LT (Mach64 LT)", 135, 63, 63, ATI_CHIP_264LT },
382          /* FIXME chipset maybe ATI_CHIP_264LTPRO ? */
383         { PCI_CHIP_MACH64LG, "3D RAGE LT-G (Mach64 LG)", 230, 63, 63, ATI_CHIP_264LTG | M64F_LT_LCD_REGS | M64F_G3_PB_1024x768 },
384
385         { PCI_CHIP_MACH64VV, "ATI264VT4 (Mach64 VV)", 230, 83, 83, ATI_CHIP_264VT4 },
386
387         { PCI_CHIP_MACH64GV, "3D RAGE IIC (Mach64 GV, PCI)", 230, 83, 83, ATI_CHIP_264GT2C },
388         { PCI_CHIP_MACH64GW, "3D RAGE IIC (Mach64 GW, AGP)", 230, 83, 83, ATI_CHIP_264GT2C },
389         { PCI_CHIP_MACH64GY, "3D RAGE IIC (Mach64 GY, PCI)", 230, 83, 83, ATI_CHIP_264GT2C },
390         { PCI_CHIP_MACH64GZ, "3D RAGE IIC (Mach64 GZ, AGP)", 230, 83, 83, ATI_CHIP_264GT2C },
391
392         { PCI_CHIP_MACH64GB, "3D RAGE PRO (Mach64 GB, BGA, AGP)", 230, 100, 100, ATI_CHIP_264GTPRO },
393         { PCI_CHIP_MACH64GD, "3D RAGE PRO (Mach64 GD, BGA, AGP 1x)", 230, 100, 100, ATI_CHIP_264GTPRO },
394         { PCI_CHIP_MACH64GI, "3D RAGE PRO (Mach64 GI, BGA, PCI)", 230, 100, 100, ATI_CHIP_264GTPRO | M64F_MAGIC_VRAM_SIZE },
395         { PCI_CHIP_MACH64GP, "3D RAGE PRO (Mach64 GP, PQFP, PCI)", 230, 100, 100, ATI_CHIP_264GTPRO },
396         { PCI_CHIP_MACH64GQ, "3D RAGE PRO (Mach64 GQ, PQFP, PCI, limited 3D)", 230, 100, 100, ATI_CHIP_264GTPRO },
397
398         { PCI_CHIP_MACH64LB, "3D RAGE LT PRO (Mach64 LB, AGP)", 236, 75, 100, ATI_CHIP_264LTPRO },
399         { PCI_CHIP_MACH64LD, "3D RAGE LT PRO (Mach64 LD, AGP)", 230, 100, 100, ATI_CHIP_264LTPRO },
400         { PCI_CHIP_MACH64LI, "3D RAGE LT PRO (Mach64 LI, PCI)", 230, 100, 100, ATI_CHIP_264LTPRO | M64F_G3_PB_1_1 | M64F_G3_PB_1024x768 },
401         { PCI_CHIP_MACH64LP, "3D RAGE LT PRO (Mach64 LP, PCI)", 230, 100, 100, ATI_CHIP_264LTPRO },
402         { PCI_CHIP_MACH64LQ, "3D RAGE LT PRO (Mach64 LQ, PCI)", 230, 100, 100, ATI_CHIP_264LTPRO },
403
404         { PCI_CHIP_MACH64GM, "3D RAGE XL (Mach64 GM, AGP)", 230, 83, 63, ATI_CHIP_264XL },
405         { PCI_CHIP_MACH64GN, "3D RAGE XL (Mach64 GN, AGP)", 230, 83, 63, ATI_CHIP_264XL },
406         { PCI_CHIP_MACH64GO, "3D RAGE XL (Mach64 GO, PCI-66/BGA)", 230, 83, 63, ATI_CHIP_264XL },
407         { PCI_CHIP_MACH64GR, "3D RAGE XL (Mach64 GR, PCI-33MHz)", 230, 83, 63, ATI_CHIP_264XL },
408         { PCI_CHIP_MACH64GL, "3D RAGE XL (Mach64 GL, PCI)", 230, 83, 63, ATI_CHIP_264XL },
409         { PCI_CHIP_MACH64GS, "3D RAGE XL (Mach64 GS, PCI)", 230, 83, 63, ATI_CHIP_264XL },
410
411         { PCI_CHIP_MACH64LM, "3D RAGE Mobility P/M (Mach64 LM, AGP 2x)", 230, 83, 125, ATI_CHIP_MOBILITY },
412         { PCI_CHIP_MACH64LN, "3D RAGE Mobility L (Mach64 LN, AGP 2x)", 230, 83, 125, ATI_CHIP_MOBILITY },
413         { PCI_CHIP_MACH64LR, "3D RAGE Mobility P/M (Mach64 LR, PCI)", 230, 83, 125, ATI_CHIP_MOBILITY },
414         { PCI_CHIP_MACH64LS, "3D RAGE Mobility L (Mach64 LS, PCI)", 230, 83, 125, ATI_CHIP_MOBILITY },
415 #endif /* CONFIG_FB_ATY_CT */
416 };
417
418 /* can not fail */
419 static int __devinit correct_chipset(struct atyfb_par *par)
420 {
421         u8 rev;
422         u16 type;
423         u32 chip_id;
424         const char *name;
425         int i;
426
427         for (i = sizeof(aty_chips) / sizeof(*aty_chips) - 1; i >= 0; i--)
428                 if (par->pci_id == aty_chips[i].pci_id)
429                         break;
430
431         name = aty_chips[i].name;
432         par->pll_limits.pll_max = aty_chips[i].pll;
433         par->pll_limits.mclk = aty_chips[i].mclk;
434         par->pll_limits.xclk = aty_chips[i].xclk;
435         par->features = aty_chips[i].features;
436
437         chip_id = aty_ld_le32(CONFIG_CHIP_ID, par);
438         type = chip_id & CFG_CHIP_TYPE;
439         rev = (chip_id & CFG_CHIP_REV) >> 24;
440
441         switch(par->pci_id) {
442 #ifdef CONFIG_FB_ATY_GX
443         case PCI_CHIP_MACH64GX:
444                 if(type != 0x00d7)
445                         return -ENODEV;
446                 break;
447         case PCI_CHIP_MACH64CX:
448                 if(type != 0x0057)
449                         return -ENODEV;
450                 break;
451 #endif
452 #ifdef CONFIG_FB_ATY_CT
453         case PCI_CHIP_MACH64VT:
454                 rev &= 0xc7;
455                 if(rev == 0x00) {
456                         name = "ATI264VTA3 (Mach64 VT)";
457                         par->pll_limits.pll_max = 170;
458                         par->pll_limits.mclk = 67;
459                         par->pll_limits.xclk = 67;
460                         par->features = ATI_CHIP_264VT;
461                 } else if(rev == 0x40) {
462                         name = "ATI264VTA4 (Mach64 VT)";
463                         par->pll_limits.pll_max = 200;
464                         par->pll_limits.mclk = 67;
465                         par->pll_limits.xclk = 67;
466                         par->features = ATI_CHIP_264VT | M64F_MAGIC_POSTDIV;
467                 } else {
468                         name = "ATI264VTB (Mach64 VT)";
469                         par->pll_limits.pll_max = 200;
470                         par->pll_limits.mclk = 67;
471                         par->pll_limits.xclk = 67;
472                         par->features = ATI_CHIP_264VTB;
473                 }
474                 break;
475         case PCI_CHIP_MACH64GT:
476                 rev &= 0x07;
477                 if(rev == 0x01) {
478                         par->pll_limits.pll_max = 170;
479                         par->pll_limits.mclk = 67;
480                         par->pll_limits.xclk = 67;
481                         par->features = ATI_CHIP_264GTB;
482                 } else if(rev == 0x02) {
483                         par->pll_limits.pll_max = 200;
484                         par->pll_limits.mclk = 67;
485                         par->pll_limits.xclk = 67;
486                         par->features = ATI_CHIP_264GTB;
487                 }
488                 break;
489 #endif
490         }
491
492         PRINTKI("%s [0x%04x rev 0x%02x]\n", name, type, rev);
493         return 0;
494 }
495
496 static char ram_dram[] __devinitdata = "DRAM";
497 static char ram_resv[] __devinitdata = "RESV";
498 #ifdef CONFIG_FB_ATY_GX
499 static char ram_vram[] __devinitdata = "VRAM";
500 #endif /* CONFIG_FB_ATY_GX */
501 #ifdef CONFIG_FB_ATY_CT
502 static char ram_edo[] __devinitdata = "EDO";
503 static char ram_sdram[] __devinitdata = "SDRAM (1:1)";
504 static char ram_sgram[] __devinitdata = "SGRAM (1:1)";
505 static char ram_sdram32[] __devinitdata = "SDRAM (2:1) (32-bit)";
506 static char ram_off[] __devinitdata = "OFF";
507 #endif /* CONFIG_FB_ATY_CT */
508
509
510 static u32 pseudo_palette[17];
511
512 #ifdef CONFIG_FB_ATY_GX
513 static char *aty_gx_ram[8] __devinitdata = {
514         ram_dram, ram_vram, ram_vram, ram_dram,
515         ram_dram, ram_vram, ram_vram, ram_resv
516 };
517 #endif /* CONFIG_FB_ATY_GX */
518
519 #ifdef CONFIG_FB_ATY_CT
520 static char *aty_ct_ram[8] __devinitdata = {
521         ram_off, ram_dram, ram_edo, ram_edo,
522         ram_sdram, ram_sgram, ram_sdram32, ram_resv
523 };
524 #endif /* CONFIG_FB_ATY_CT */
525
526 static u32 atyfb_get_pixclock(struct fb_var_screeninfo *var, struct atyfb_par *par)
527 {
528         u32 pixclock = var->pixclock;
529 #ifdef CONFIG_FB_ATY_GENERIC_LCD
530         u32 lcd_on_off;
531         par->pll.ct.xres = 0;
532         if (par->lcd_table != 0) {
533                 lcd_on_off = aty_ld_lcd(LCD_GEN_CNTL, par);
534                 if(lcd_on_off & LCD_ON) {
535                         par->pll.ct.xres = var->xres;
536                         pixclock = par->lcd_pixclock;
537                 }
538         }
539 #endif
540         return pixclock;
541 }
542
543 #if defined(CONFIG_PPC)
544
545 /*
546  *  Apple monitor sense
547  */
548
549 static int __init read_aty_sense(const struct atyfb_par *par)
550 {
551         int sense, i;
552
553         aty_st_le32(GP_IO, 0x31003100, par); /* drive outputs high */
554         __delay(200);
555         aty_st_le32(GP_IO, 0, par); /* turn off outputs */
556         __delay(2000);
557         i = aty_ld_le32(GP_IO, par); /* get primary sense value */
558         sense = ((i & 0x3000) >> 3) | (i & 0x100);
559
560         /* drive each sense line low in turn and collect the other 2 */
561         aty_st_le32(GP_IO, 0x20000000, par); /* drive A low */
562         __delay(2000);
563         i = aty_ld_le32(GP_IO, par);
564         sense |= ((i & 0x1000) >> 7) | ((i & 0x100) >> 4);
565         aty_st_le32(GP_IO, 0x20002000, par); /* drive A high again */
566         __delay(200);
567
568         aty_st_le32(GP_IO, 0x10000000, par); /* drive B low */
569         __delay(2000);
570         i = aty_ld_le32(GP_IO, par);
571         sense |= ((i & 0x2000) >> 10) | ((i & 0x100) >> 6);
572         aty_st_le32(GP_IO, 0x10001000, par); /* drive B high again */
573         __delay(200);
574
575         aty_st_le32(GP_IO, 0x01000000, par); /* drive C low */
576         __delay(2000);
577         sense |= (aty_ld_le32(GP_IO, par) & 0x3000) >> 12;
578         aty_st_le32(GP_IO, 0, par); /* turn off outputs */
579         return sense;
580 }
581
582 #endif /* defined(CONFIG_PPC) */
583
584 /* ------------------------------------------------------------------------- */
585
586 /*
587  *  CRTC programming
588  */
589
590 static void aty_get_crtc(const struct atyfb_par *par, struct crtc *crtc)
591 {
592 #ifdef CONFIG_FB_ATY_GENERIC_LCD
593         if (par->lcd_table != 0) {
594                 if(!M64_HAS(LT_LCD_REGS)) {
595                     crtc->lcd_index = aty_ld_le32(LCD_INDEX, par);
596                     aty_st_le32(LCD_INDEX, crtc->lcd_index, par);
597                 }
598                 crtc->lcd_config_panel = aty_ld_lcd(CONFIG_PANEL, par);
599                 crtc->lcd_gen_cntl = aty_ld_lcd(LCD_GEN_CNTL, par);
600
601
602                 /* switch to non shadow registers */
603                 aty_st_lcd(LCD_GEN_CNTL, crtc->lcd_gen_cntl &
604                     ~(CRTC_RW_SELECT | SHADOW_EN | SHADOW_RW_EN), par);
605
606                 /* save stretching */
607                 crtc->horz_stretching = aty_ld_lcd(HORZ_STRETCHING, par);
608                 crtc->vert_stretching = aty_ld_lcd(VERT_STRETCHING, par);
609                 if (!M64_HAS(LT_LCD_REGS))
610                         crtc->ext_vert_stretch = aty_ld_lcd(EXT_VERT_STRETCH, par);
611         }
612 #endif
613         crtc->h_tot_disp = aty_ld_le32(CRTC_H_TOTAL_DISP, par);
614         crtc->h_sync_strt_wid = aty_ld_le32(CRTC_H_SYNC_STRT_WID, par);
615         crtc->v_tot_disp = aty_ld_le32(CRTC_V_TOTAL_DISP, par);
616         crtc->v_sync_strt_wid = aty_ld_le32(CRTC_V_SYNC_STRT_WID, par);
617         crtc->vline_crnt_vline = aty_ld_le32(CRTC_VLINE_CRNT_VLINE, par);
618         crtc->off_pitch = aty_ld_le32(CRTC_OFF_PITCH, par);
619         crtc->gen_cntl = aty_ld_le32(CRTC_GEN_CNTL, par);
620
621 #ifdef CONFIG_FB_ATY_GENERIC_LCD
622         if (par->lcd_table != 0) {
623                 /* switch to shadow registers */
624                 aty_st_lcd(LCD_GEN_CNTL, (crtc->lcd_gen_cntl & ~CRTC_RW_SELECT) |
625                         SHADOW_EN | SHADOW_RW_EN, par);
626
627                 crtc->shadow_h_tot_disp = aty_ld_le32(CRTC_H_TOTAL_DISP, par);
628                 crtc->shadow_h_sync_strt_wid = aty_ld_le32(CRTC_H_SYNC_STRT_WID, par);
629                 crtc->shadow_v_tot_disp = aty_ld_le32(CRTC_V_TOTAL_DISP, par);
630                 crtc->shadow_v_sync_strt_wid = aty_ld_le32(CRTC_V_SYNC_STRT_WID, par);
631
632                 aty_st_le32(LCD_GEN_CNTL, crtc->lcd_gen_cntl, par);
633         }
634 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
635 }
636
637 static void aty_set_crtc(const struct atyfb_par *par, const struct crtc *crtc)
638 {
639 #ifdef CONFIG_FB_ATY_GENERIC_LCD
640         if (par->lcd_table != 0) {
641                 /* stop CRTC */
642                 aty_st_le32(CRTC_GEN_CNTL, crtc->gen_cntl & ~(CRTC_EXT_DISP_EN | CRTC_EN), par);
643
644                 /* update non-shadow registers first */
645                 aty_st_lcd(CONFIG_PANEL, crtc->lcd_config_panel, par);
646                 aty_st_lcd(LCD_GEN_CNTL, crtc->lcd_gen_cntl &
647                         ~(CRTC_RW_SELECT | SHADOW_EN | SHADOW_RW_EN), par);
648
649                 /* temporarily disable stretching */
650                 aty_st_lcd(HORZ_STRETCHING,
651                         crtc->horz_stretching &
652                         ~(HORZ_STRETCH_MODE | HORZ_STRETCH_EN), par);
653                 aty_st_lcd(VERT_STRETCHING,
654                         crtc->vert_stretching &
655                         ~(VERT_STRETCH_RATIO1 | VERT_STRETCH_RATIO2 |
656                         VERT_STRETCH_USE0 | VERT_STRETCH_EN), par);
657         }
658 #endif
659         /* turn off CRT */
660         aty_st_le32(CRTC_GEN_CNTL, crtc->gen_cntl & ~CRTC_EN, par);
661
662         DPRINTK("setting up CRTC\n");
663         DPRINTK("set primary CRT to %ix%i %c%c composite %c\n",
664             ((((crtc->h_tot_disp>>16) & 0xff) + 1)<<3), (((crtc->v_tot_disp>>16) & 0x7ff) + 1),
665             (crtc->h_sync_strt_wid & 0x200000)?'N':'P', (crtc->v_sync_strt_wid & 0x200000)?'N':'P',
666             (crtc->gen_cntl & CRTC_CSYNC_EN)?'P':'N');
667
668         DPRINTK("CRTC_H_TOTAL_DISP: %x\n",crtc->h_tot_disp);
669         DPRINTK("CRTC_H_SYNC_STRT_WID: %x\n",crtc->h_sync_strt_wid);
670         DPRINTK("CRTC_V_TOTAL_DISP: %x\n",crtc->v_tot_disp);
671         DPRINTK("CRTC_V_SYNC_STRT_WID: %x\n",crtc->v_sync_strt_wid);
672         DPRINTK("CRTC_OFF_PITCH: %x\n", crtc->off_pitch);
673         DPRINTK("CRTC_VLINE_CRNT_VLINE: %x\n", crtc->vline_crnt_vline);
674         DPRINTK("CRTC_GEN_CNTL: %x\n",crtc->gen_cntl);
675
676         aty_st_le32(CRTC_H_TOTAL_DISP, crtc->h_tot_disp, par);
677         aty_st_le32(CRTC_H_SYNC_STRT_WID, crtc->h_sync_strt_wid, par);
678         aty_st_le32(CRTC_V_TOTAL_DISP, crtc->v_tot_disp, par);
679         aty_st_le32(CRTC_V_SYNC_STRT_WID, crtc->v_sync_strt_wid, par);
680         aty_st_le32(CRTC_OFF_PITCH, crtc->off_pitch, par);
681         aty_st_le32(CRTC_VLINE_CRNT_VLINE, crtc->vline_crnt_vline, par);
682
683         aty_st_le32(CRTC_GEN_CNTL, crtc->gen_cntl, par);
684 #if 0
685         FIXME
686         if (par->accel_flags & FB_ACCELF_TEXT)
687                 aty_init_engine(par, info);
688 #endif
689 #ifdef CONFIG_FB_ATY_GENERIC_LCD
690         /* after setting the CRTC registers we should set the LCD registers. */
691         if (par->lcd_table != 0) {
692                 /* switch to shadow registers */
693                 aty_st_lcd(LCD_GEN_CNTL, (crtc->lcd_gen_cntl & ~CRTC_RW_SELECT) |
694                         (SHADOW_EN | SHADOW_RW_EN), par);
695
696                 DPRINTK("set secondary CRT to %ix%i %c%c\n",
697                     ((((crtc->shadow_h_tot_disp>>16) & 0xff) + 1)<<3), (((crtc->shadow_v_tot_disp>>16) & 0x7ff) + 1),
698                     (crtc->shadow_h_sync_strt_wid & 0x200000)?'N':'P', (crtc->shadow_v_sync_strt_wid & 0x200000)?'N':'P');
699
700                 DPRINTK("SHADOW CRTC_H_TOTAL_DISP: %x\n", crtc->shadow_h_tot_disp);
701                 DPRINTK("SHADOW CRTC_H_SYNC_STRT_WID: %x\n", crtc->shadow_h_sync_strt_wid);
702                 DPRINTK("SHADOW CRTC_V_TOTAL_DISP: %x\n", crtc->shadow_v_tot_disp);
703                 DPRINTK("SHADOW CRTC_V_SYNC_STRT_WID: %x\n", crtc->shadow_v_sync_strt_wid);
704
705                 aty_st_le32(CRTC_H_TOTAL_DISP, crtc->shadow_h_tot_disp, par);
706                 aty_st_le32(CRTC_H_SYNC_STRT_WID, crtc->shadow_h_sync_strt_wid, par);
707                 aty_st_le32(CRTC_V_TOTAL_DISP, crtc->shadow_v_tot_disp, par);
708                 aty_st_le32(CRTC_V_SYNC_STRT_WID, crtc->shadow_v_sync_strt_wid, par);
709
710                 /* restore CRTC selection & shadow state and enable stretching */
711                 DPRINTK("LCD_GEN_CNTL: %x\n", crtc->lcd_gen_cntl);
712                 DPRINTK("HORZ_STRETCHING: %x\n", crtc->horz_stretching);
713                 DPRINTK("VERT_STRETCHING: %x\n", crtc->vert_stretching);
714                 if(!M64_HAS(LT_LCD_REGS))
715                     DPRINTK("EXT_VERT_STRETCH: %x\n", crtc->ext_vert_stretch);
716
717                 aty_st_lcd(LCD_GEN_CNTL, crtc->lcd_gen_cntl, par);
718                 aty_st_lcd(HORZ_STRETCHING, crtc->horz_stretching, par);
719                 aty_st_lcd(VERT_STRETCHING, crtc->vert_stretching, par);
720                 if(!M64_HAS(LT_LCD_REGS)) {
721                     aty_st_lcd(EXT_VERT_STRETCH, crtc->ext_vert_stretch, par);
722                     aty_ld_le32(LCD_INDEX, par);
723                     aty_st_le32(LCD_INDEX, crtc->lcd_index, par);
724                 }
725         }
726 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
727 }
728
729 static int aty_var_to_crtc(const struct fb_info *info,
730         const struct fb_var_screeninfo *var, struct crtc *crtc)
731 {
732         struct atyfb_par *par = (struct atyfb_par *) info->par;
733         u32 xres, yres, vxres, vyres, xoffset, yoffset, bpp;
734         u32 sync, vmode, vdisplay;
735         u32 h_total, h_disp, h_sync_strt, h_sync_end, h_sync_dly, h_sync_wid, h_sync_pol;
736         u32 v_total, v_disp, v_sync_strt, v_sync_end, v_sync_wid, v_sync_pol, c_sync;
737         u32 pix_width, dp_pix_width, dp_chain_mask;
738
739         /* input */
740         xres = var->xres;
741         yres = var->yres;
742         vxres = var->xres_virtual;
743         vyres = var->yres_virtual;
744         xoffset = var->xoffset;
745         yoffset = var->yoffset;
746         bpp = var->bits_per_pixel;
747         if (bpp == 16)
748                 bpp = (var->green.length == 5) ? 15 : 16;
749         sync = var->sync;
750         vmode = var->vmode;
751
752         /* convert (and round up) and validate */
753         if (vxres < xres + xoffset)
754                 vxres = xres + xoffset;
755         h_disp = xres;
756
757         if (vyres < yres + yoffset)
758                 vyres = yres + yoffset;
759         v_disp = yres;
760
761         if (bpp <= 8) {
762                 bpp = 8;
763                 pix_width = CRTC_PIX_WIDTH_8BPP;
764                 dp_pix_width =
765                     HOST_8BPP | SRC_8BPP | DST_8BPP |
766                     BYTE_ORDER_LSB_TO_MSB;
767                 dp_chain_mask = DP_CHAIN_8BPP;
768         } else if (bpp <= 15) {
769                 bpp = 16;
770                 pix_width = CRTC_PIX_WIDTH_15BPP;
771                 dp_pix_width = HOST_15BPP | SRC_15BPP | DST_15BPP |
772                     BYTE_ORDER_LSB_TO_MSB;
773                 dp_chain_mask = DP_CHAIN_15BPP;
774         } else if (bpp <= 16) {
775                 bpp = 16;
776                 pix_width = CRTC_PIX_WIDTH_16BPP;
777                 dp_pix_width = HOST_16BPP | SRC_16BPP | DST_16BPP |
778                     BYTE_ORDER_LSB_TO_MSB;
779                 dp_chain_mask = DP_CHAIN_16BPP;
780         } else if (bpp <= 24 && M64_HAS(INTEGRATED)) {
781                 bpp = 24;
782                 pix_width = CRTC_PIX_WIDTH_24BPP;
783                 dp_pix_width =
784                     HOST_8BPP | SRC_8BPP | DST_8BPP |
785                     BYTE_ORDER_LSB_TO_MSB;
786                 dp_chain_mask = DP_CHAIN_24BPP;
787         } else if (bpp <= 32) {
788                 bpp = 32;
789                 pix_width = CRTC_PIX_WIDTH_32BPP;
790                 dp_pix_width = HOST_32BPP | SRC_32BPP | DST_32BPP |
791                     BYTE_ORDER_LSB_TO_MSB;
792                 dp_chain_mask = DP_CHAIN_32BPP;
793         } else
794                 FAIL("invalid bpp");
795
796         if (vxres * vyres * bpp / 8 > info->fix.smem_len)
797                 FAIL("not enough video RAM");
798
799         h_sync_pol = sync & FB_SYNC_HOR_HIGH_ACT ? 0 : 1;
800         v_sync_pol = sync & FB_SYNC_VERT_HIGH_ACT ? 0 : 1;
801
802         if((xres > 1600) || (yres > 1200)) {
803                 FAIL("MACH64 chips are designed for max 1600x1200\n"
804                 "select anoter resolution.");
805         }
806         h_sync_strt = h_disp + var->right_margin;
807         h_sync_end = h_sync_strt + var->hsync_len;
808         h_sync_dly  = var->right_margin & 7;
809         h_total = h_sync_end + h_sync_dly + var->left_margin;
810
811         v_sync_strt = v_disp + var->lower_margin;
812         v_sync_end = v_sync_strt + var->vsync_len;
813         v_total = v_sync_end + var->upper_margin;
814
815 #ifdef CONFIG_FB_ATY_GENERIC_LCD
816         if (par->lcd_table != 0) {
817                 if(!M64_HAS(LT_LCD_REGS)) {
818                     u32 lcd_index = aty_ld_le32(LCD_INDEX, par);
819                     crtc->lcd_index = lcd_index &
820                         ~(LCD_INDEX_MASK | LCD_DISPLAY_DIS | LCD_SRC_SEL | CRTC2_DISPLAY_DIS);
821                     aty_st_le32(LCD_INDEX, lcd_index, par);
822                 }
823
824                 if (!M64_HAS(MOBIL_BUS))
825                         crtc->lcd_index |= CRTC2_DISPLAY_DIS;
826
827                 crtc->lcd_config_panel = aty_ld_lcd(CONFIG_PANEL, par) | 0x4000;
828                 crtc->lcd_gen_cntl = aty_ld_lcd(LCD_GEN_CNTL, par) & ~CRTC_RW_SELECT;
829
830                 crtc->lcd_gen_cntl &=
831                         ~(HORZ_DIVBY2_EN | DIS_HOR_CRT_DIVBY2 | TVCLK_PM_EN |
832                         /*VCLK_DAC_PM_EN | USE_SHADOWED_VEND |*/
833                         USE_SHADOWED_ROWCUR | SHADOW_EN | SHADOW_RW_EN);
834                 crtc->lcd_gen_cntl |= DONT_SHADOW_VPAR | LOCK_8DOT;
835
836                 if((crtc->lcd_gen_cntl & LCD_ON) &&
837                         ((xres > par->lcd_width) || (yres > par->lcd_height))) {
838                         /* We cannot display the mode on the LCD. If the CRT is enabled
839                            we can turn off the LCD.
840                            If the CRT is off, it isn't a good idea to switch it on; we don't
841                            know if one is connected. So it's better to fail then.
842                          */
843                         if (crtc->lcd_gen_cntl & CRT_ON) {
844                                 PRINTKI("Disable lcd panel, because video mode does not fit.\n");
845                                 crtc->lcd_gen_cntl &= ~LCD_ON;
846                                 /*aty_st_lcd(LCD_GEN_CNTL, crtc->lcd_gen_cntl, par);*/
847                         } else {
848                                 FAIL("Video mode exceeds size of lcd panel.\nConnect this computer to a conventional monitor if you really need this mode.");
849                         }
850                 }
851         }
852
853         if ((par->lcd_table != 0) && (crtc->lcd_gen_cntl & LCD_ON)) {
854                 int VScan = 1;
855                 /* bpp -> bytespp, 1,4 -> 0; 8 -> 2; 15,16 -> 1; 24 -> 6; 32 -> 5
856                 const u8 DFP_h_sync_dly_LT[] = { 0, 2, 1, 6, 5 };
857                 const u8 ADD_to_strt_wid_and_dly_LT_DAC[] = { 0, 5, 6, 9, 9, 12, 12 };  */
858
859                 vmode &= ~(FB_VMODE_DOUBLE | FB_VMODE_INTERLACED);
860
861                 /* This is horror! When we simulate, say 640x480 on an 800x600
862                    lcd monitor, the CRTC should be programmed 800x600 values for
863                    the non visible part, but 640x480 for the visible part.
864                    This code has been tested on a laptop with it's 1400x1050 lcd
865                    monitor and a conventional monitor both switched on.
866                    Tested modes: 1280x1024, 1152x864, 1024x768, 800x600,
867                     works with little glitches also with DOUBLESCAN modes
868                  */
869                 if (yres < par->lcd_height) {
870                         VScan = par->lcd_height / yres;
871                         if(VScan > 1) {
872                                 VScan = 2;
873                                 vmode |= FB_VMODE_DOUBLE;
874                         }
875                 }
876
877                 h_sync_strt = h_disp + par->lcd_right_margin;
878                 h_sync_end = h_sync_strt + par->lcd_hsync_len;
879                 h_sync_dly = /*DFP_h_sync_dly[ ( bpp + 1 ) / 3 ]; */par->lcd_hsync_dly;
880                 h_total = h_disp + par->lcd_hblank_len;
881
882                 v_sync_strt = v_disp + par->lcd_lower_margin / VScan;
883                 v_sync_end = v_sync_strt + par->lcd_vsync_len / VScan;
884                 v_total = v_disp + par->lcd_vblank_len / VScan;
885         }
886 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
887
888         h_disp = (h_disp >> 3) - 1;
889         h_sync_strt = (h_sync_strt >> 3) - 1;
890         h_sync_end = (h_sync_end >> 3) - 1;
891         h_total = (h_total >> 3) - 1;
892         h_sync_wid = h_sync_end - h_sync_strt;
893
894         FAIL_MAX("h_disp too large", h_disp, 0xff);
895         FAIL_MAX("h_sync_strt too large", h_sync_strt, 0x1ff);
896         /*FAIL_MAX("h_sync_wid too large", h_sync_wid, 0x1f);*/
897         if(h_sync_wid > 0x1f)
898                 h_sync_wid = 0x1f;
899         FAIL_MAX("h_total too large", h_total, 0x1ff);
900
901         if (vmode & FB_VMODE_DOUBLE) {
902                 v_disp <<= 1;
903                 v_sync_strt <<= 1;
904                 v_sync_end <<= 1;
905                 v_total <<= 1;
906         }
907
908         vdisplay = yres;
909 #ifdef CONFIG_FB_ATY_GENERIC_LCD
910         if ((par->lcd_table != 0) && (crtc->lcd_gen_cntl & LCD_ON))
911                 vdisplay  = par->lcd_height;
912 #endif
913
914         if(vdisplay < 400) {
915                 h_sync_pol = 1;
916                 v_sync_pol = 0;
917         } else if(vdisplay < 480) {
918                 h_sync_pol = 0;
919                 v_sync_pol = 1;
920         } else if(vdisplay < 768) {
921                 h_sync_pol = 0;
922                 v_sync_pol = 0;
923         } else {
924                 h_sync_pol = 1;
925                 v_sync_pol = 1;
926         }
927
928         v_disp--;
929         v_sync_strt--;
930         v_sync_end--;
931         v_total--;
932         v_sync_wid = v_sync_end - v_sync_strt;
933
934         FAIL_MAX("v_disp too large", v_disp, 0x7ff);
935         FAIL_MAX("v_sync_stsrt too large", v_sync_strt, 0x7ff);
936         /*FAIL_MAX("v_sync_wid too large", v_sync_wid, 0x1f);*/
937         if(v_sync_wid > 0x1f)
938                 v_sync_wid = 0x1f;
939         FAIL_MAX("v_total too large", v_total, 0x7ff);
940
941         c_sync = sync & FB_SYNC_COMP_HIGH_ACT ? CRTC_CSYNC_EN : 0;
942
943         /* output */
944         crtc->vxres = vxres;
945         crtc->vyres = vyres;
946         crtc->xoffset = xoffset;
947         crtc->yoffset = yoffset;
948         crtc->bpp = bpp;
949         crtc->off_pitch = ((yoffset*vxres+xoffset)*bpp/64) | (vxres<<19);
950         crtc->vline_crnt_vline = 0;
951
952         crtc->h_tot_disp = h_total | (h_disp<<16);
953         crtc->h_sync_strt_wid = (h_sync_strt & 0xff) | (h_sync_dly<<8) |
954                 ((h_sync_strt & 0x100)<<4) | (h_sync_wid<<16) | (h_sync_pol<<21);
955         crtc->v_tot_disp = v_total | (v_disp<<16);
956         crtc->v_sync_strt_wid = v_sync_strt | (v_sync_wid<<16) | (v_sync_pol<<21);
957
958         /* crtc->gen_cntl = aty_ld_le32(CRTC_GEN_CNTL, par) & CRTC_PRESERVED_MASK; */
959         crtc->gen_cntl = CRTC_EXT_DISP_EN | CRTC_EN | pix_width | c_sync;
960         crtc->gen_cntl |= CRTC_VGA_LINEAR;
961
962         /* Enable doublescan mode if requested */
963         if (vmode & FB_VMODE_DOUBLE)
964                 crtc->gen_cntl |= CRTC_DBL_SCAN_EN;
965         /* Enable interlaced mode if requested */
966         if (vmode & FB_VMODE_INTERLACED)
967                 crtc->gen_cntl |= CRTC_INTERLACE_EN;
968 #ifdef CONFIG_FB_ATY_GENERIC_LCD
969         if (par->lcd_table != 0) {
970                 vdisplay = yres;
971                 if(vmode & FB_VMODE_DOUBLE)
972                         vdisplay <<= 1;
973                 if(vmode & FB_VMODE_INTERLACED) {
974                         vdisplay >>= 1;
975
976                         /* The prefered mode for the lcd is not interlaced, so disable it if
977                            it was enabled. For doublescan there is no problem, because we can
978                            compensate for it in the hardware stretching (we stretch half as much)
979                          */
980                         vmode &= ~FB_VMODE_INTERLACED;
981                         /*crtc->gen_cntl &= ~CRTC_INTERLACE_EN;*/
982                 }
983                 crtc->gen_cntl &= ~(CRTC2_EN | CRTC2_PIX_WIDTH);
984                 crtc->lcd_gen_cntl &= ~(HORZ_DIVBY2_EN | DIS_HOR_CRT_DIVBY2 |
985                         /*TVCLK_PM_EN | VCLK_DAC_PM_EN |*/
986                         USE_SHADOWED_VEND | USE_SHADOWED_ROWCUR | SHADOW_EN | SHADOW_RW_EN);
987                 crtc->lcd_gen_cntl |= (DONT_SHADOW_VPAR/* | LOCK_8DOT*/);
988
989                 /* MOBILITY M1 tested, FIXME: LT */
990                 crtc->horz_stretching = aty_ld_lcd(HORZ_STRETCHING, par);
991                 if (!M64_HAS(LT_LCD_REGS))
992                         crtc->ext_vert_stretch = aty_ld_lcd(EXT_VERT_STRETCH, par) &
993                                 ~(AUTO_VERT_RATIO | VERT_STRETCH_MODE | VERT_STRETCH_RATIO3);
994
995                 crtc->horz_stretching &=
996                         ~(HORZ_STRETCH_RATIO | HORZ_STRETCH_LOOP | AUTO_HORZ_RATIO |
997                         HORZ_STRETCH_MODE | HORZ_STRETCH_EN);
998                 if (xres < par->lcd_width) {
999                         do {
1000                                 /*
1001                                 * The horizontal blender misbehaves when HDisplay is less than a
1002                                 * a certain threshold (440 for a 1024-wide panel).  It doesn't
1003                                 * stretch such modes enough.  Use pixel replication instead of
1004                                 * blending to stretch modes that can be made to exactly fit the
1005                                 * panel width.  The undocumented "NoLCDBlend" option allows the
1006                                 * pixel-replicated mode to be slightly wider or narrower than the
1007                                 * panel width.  It also causes a mode that is exactly half as wide
1008                                 * as the panel to be pixel-replicated, rather than blended.
1009                                 */
1010                                 int HDisplay  = xres & ~7;
1011                                 int nStretch  = par->lcd_width / HDisplay;
1012                                 int Remainder = par->lcd_width % HDisplay;
1013
1014                                 if ((!Remainder && ((nStretch > 2))) ||
1015                                         (((HDisplay * 16) / par->lcd_width) < 7)) {
1016                                         static const char StretchLoops[] = {10, 12, 13, 15, 16};
1017                                         int horz_stretch_loop = -1, BestRemainder;
1018                                         int Numerator = HDisplay, Denominator = par->lcd_width;
1019                                         int Index = 5;
1020                                         ATIReduceRatio(&Numerator, &Denominator);
1021
1022                                         BestRemainder = (Numerator * 16) / Denominator;
1023                                         while (--Index >= 0) {
1024                                                 Remainder = ((Denominator - Numerator) * StretchLoops[Index]) %
1025                                                         Denominator;
1026                                                 if (Remainder < BestRemainder) {
1027                                                         horz_stretch_loop = Index;
1028                                                         if (!(BestRemainder = Remainder))
1029                                                                 break;
1030                                                 }
1031                                         }
1032
1033                                         if ((horz_stretch_loop >= 0) && !BestRemainder) {
1034                                                 int horz_stretch_ratio = 0, Accumulator = 0;
1035                                                 int reuse_previous = 1;
1036
1037                                                 Index = StretchLoops[horz_stretch_loop];
1038
1039                                                 while (--Index >= 0) {
1040                                                         if (Accumulator > 0)
1041                                                                 horz_stretch_ratio |= reuse_previous;
1042                                                         else
1043                                                                 Accumulator += Denominator;
1044                                                         Accumulator -= Numerator;
1045                                                         reuse_previous <<= 1;
1046                                                 }
1047
1048                                                 crtc->horz_stretching |= (HORZ_STRETCH_EN |
1049                                                         ((horz_stretch_loop & HORZ_STRETCH_LOOP) << 16) |
1050                                                         (horz_stretch_ratio & HORZ_STRETCH_RATIO));
1051                                                 break;      /* Out of the do { ... } while (0) */
1052                                         }
1053                                 }
1054
1055                                 crtc->horz_stretching |= (HORZ_STRETCH_MODE | HORZ_STRETCH_EN |
1056                                         (((HDisplay * (HORZ_STRETCH_BLEND + 1)) / par->lcd_width) & HORZ_STRETCH_BLEND));
1057                         } while (0);
1058                 }
1059
1060                 if (vdisplay < par->lcd_height) {
1061                         crtc->vert_stretching = (VERT_STRETCH_USE0 | VERT_STRETCH_EN |
1062                                 (((vdisplay * (VERT_STRETCH_RATIO0 + 1)) / par->lcd_height) & VERT_STRETCH_RATIO0));
1063
1064                         if (!M64_HAS(LT_LCD_REGS) &&
1065                             xres <= (M64_HAS(MOBIL_BUS)?1024:800))
1066                                 crtc->ext_vert_stretch |= VERT_STRETCH_MODE;
1067                 } else {
1068                         /*
1069                          * Don't use vertical blending if the mode is too wide or not
1070                          * vertically stretched.
1071                          */
1072                         crtc->vert_stretching = 0;
1073                 }
1074                 /* copy to shadow crtc */
1075                 crtc->shadow_h_tot_disp = crtc->h_tot_disp;
1076                 crtc->shadow_h_sync_strt_wid = crtc->h_sync_strt_wid;
1077                 crtc->shadow_v_tot_disp = crtc->v_tot_disp;
1078                 crtc->shadow_v_sync_strt_wid = crtc->v_sync_strt_wid;
1079         }
1080 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
1081
1082         if (M64_HAS(MAGIC_FIFO)) {
1083                 /* Not VTB/GTB */
1084                 /* FIXME: magic FIFO values */
1085                 crtc->gen_cntl |= (aty_ld_le32(CRTC_GEN_CNTL, par) & CRTC2_PIX_WIDTH);
1086         }
1087         crtc->dp_pix_width = dp_pix_width;
1088         crtc->dp_chain_mask = dp_chain_mask;
1089
1090         return 0;
1091 }
1092
1093 static int aty_crtc_to_var(const struct crtc *crtc, struct fb_var_screeninfo *var)
1094 {
1095         u32 xres, yres, bpp, left, right, upper, lower, hslen, vslen, sync;
1096         u32 h_total, h_disp, h_sync_strt, h_sync_dly, h_sync_wid,
1097             h_sync_pol;
1098         u32 v_total, v_disp, v_sync_strt, v_sync_wid, v_sync_pol, c_sync;
1099         u32 pix_width;
1100         u32 double_scan, interlace;
1101
1102         /* input */
1103         h_total = crtc->h_tot_disp & 0x1ff;
1104         h_disp = (crtc->h_tot_disp >> 16) & 0xff;
1105         h_sync_strt = (crtc->h_sync_strt_wid & 0xff) | ((crtc->h_sync_strt_wid >> 4) & 0x100);
1106         h_sync_dly = (crtc->h_sync_strt_wid >> 8) & 0x7;
1107         h_sync_wid = (crtc->h_sync_strt_wid >> 16) & 0x1f;
1108         h_sync_pol = (crtc->h_sync_strt_wid >> 21) & 0x1;
1109         v_total = crtc->v_tot_disp & 0x7ff;
1110         v_disp = (crtc->v_tot_disp >> 16) & 0x7ff;
1111         v_sync_strt = crtc->v_sync_strt_wid & 0x7ff;
1112         v_sync_wid = (crtc->v_sync_strt_wid >> 16) & 0x1f;
1113         v_sync_pol = (crtc->v_sync_strt_wid >> 21) & 0x1;
1114         c_sync = crtc->gen_cntl & CRTC_CSYNC_EN ? 1 : 0;
1115         pix_width = crtc->gen_cntl & CRTC_PIX_WIDTH_MASK;
1116         double_scan = crtc->gen_cntl & CRTC_DBL_SCAN_EN;
1117         interlace = crtc->gen_cntl & CRTC_INTERLACE_EN;
1118
1119         /* convert */
1120         xres = (h_disp + 1) * 8;
1121         yres = v_disp + 1;
1122         left = (h_total - h_sync_strt - h_sync_wid) * 8 - h_sync_dly;
1123         right = (h_sync_strt - h_disp) * 8 + h_sync_dly;
1124         hslen = h_sync_wid * 8;
1125         upper = v_total - v_sync_strt - v_sync_wid;
1126         lower = v_sync_strt - v_disp;
1127         vslen = v_sync_wid;
1128         sync = (h_sync_pol ? 0 : FB_SYNC_HOR_HIGH_ACT) |
1129             (v_sync_pol ? 0 : FB_SYNC_VERT_HIGH_ACT) |
1130             (c_sync ? FB_SYNC_COMP_HIGH_ACT : 0);
1131
1132         switch (pix_width) {
1133 #if 0
1134         case CRTC_PIX_WIDTH_4BPP:
1135                 bpp = 4;
1136                 var->red.offset = 0;
1137                 var->red.length = 8;
1138                 var->green.offset = 0;
1139                 var->green.length = 8;
1140                 var->blue.offset = 0;
1141                 var->blue.length = 8;
1142                 var->transp.offset = 0;
1143                 var->transp.length = 0;
1144                 break;
1145 #endif
1146         case CRTC_PIX_WIDTH_8BPP:
1147                 bpp = 8;
1148                 var->red.offset = 0;
1149                 var->red.length = 8;
1150                 var->green.offset = 0;
1151                 var->green.length = 8;
1152                 var->blue.offset = 0;
1153                 var->blue.length = 8;
1154                 var->transp.offset = 0;
1155                 var->transp.length = 0;
1156                 break;
1157         case CRTC_PIX_WIDTH_15BPP:      /* RGB 555 */
1158                 bpp = 16;
1159                 var->red.offset = 10;
1160                 var->red.length = 5;
1161                 var->green.offset = 5;
1162                 var->green.length = 5;
1163                 var->blue.offset = 0;
1164                 var->blue.length = 5;
1165                 var->transp.offset = 0;
1166                 var->transp.length = 0;
1167                 break;
1168         case CRTC_PIX_WIDTH_16BPP:      /* RGB 565 */
1169                 bpp = 16;
1170                 var->red.offset = 11;
1171                 var->red.length = 5;
1172                 var->green.offset = 5;
1173                 var->green.length = 6;
1174                 var->blue.offset = 0;
1175                 var->blue.length = 5;
1176                 var->transp.offset = 0;
1177                 var->transp.length = 0;
1178                 break;
1179         case CRTC_PIX_WIDTH_24BPP:      /* RGB 888 */
1180                 bpp = 24;
1181                 var->red.offset = 16;
1182                 var->red.length = 8;
1183                 var->green.offset = 8;
1184                 var->green.length = 8;
1185                 var->blue.offset = 0;
1186                 var->blue.length = 8;
1187                 var->transp.offset = 0;
1188                 var->transp.length = 0;
1189                 break;
1190         case CRTC_PIX_WIDTH_32BPP:      /* ARGB 8888 */
1191                 bpp = 32;
1192                 var->red.offset = 16;
1193                 var->red.length = 8;
1194                 var->green.offset = 8;
1195                 var->green.length = 8;
1196                 var->blue.offset = 0;
1197                 var->blue.length = 8;
1198                 var->transp.offset = 24;
1199                 var->transp.length = 8;
1200                 break;
1201         default:
1202                 FAIL("Invalid pixel width");
1203         }
1204
1205         /* output */
1206         var->xres = xres;
1207         var->yres = yres;
1208         var->xres_virtual = crtc->vxres;
1209         var->yres_virtual = crtc->vyres;
1210         var->bits_per_pixel = bpp;
1211         var->left_margin = left;
1212         var->right_margin = right;
1213         var->upper_margin = upper;
1214         var->lower_margin = lower;
1215         var->hsync_len = hslen;
1216         var->vsync_len = vslen;
1217         var->sync = sync;
1218         var->vmode = FB_VMODE_NONINTERLACED;
1219         /* In double scan mode, the vertical parameters are doubled, so we need to
1220            half them to get the right values.
1221            In interlaced mode the values are already correct, so no correction is
1222            necessary.
1223          */
1224         if (interlace)
1225                 var->vmode = FB_VMODE_INTERLACED;
1226
1227         if (double_scan) {
1228                 var->vmode = FB_VMODE_DOUBLE;
1229                 var->yres>>=1;
1230                 var->upper_margin>>=1;
1231                 var->lower_margin>>=1;
1232                 var->vsync_len>>=1;
1233         }
1234
1235         return 0;
1236 }
1237
1238 /* ------------------------------------------------------------------------- */
1239
1240 static int atyfb_set_par(struct fb_info *info)
1241 {
1242         struct atyfb_par *par = (struct atyfb_par *) info->par;
1243         struct fb_var_screeninfo *var = &info->var;
1244         u32 tmp, pixclock;
1245         int err;
1246 #ifdef DEBUG
1247         struct fb_var_screeninfo debug;
1248         u32 pixclock_in_ps;
1249 #endif
1250         if (par->asleep)
1251                 return 0;
1252
1253         if ((err = aty_var_to_crtc(info, var, &par->crtc)))
1254                 return err;
1255
1256         pixclock = atyfb_get_pixclock(var, par);
1257
1258         if (pixclock == 0) {
1259                 FAIL("Invalid pixclock");
1260         } else {
1261                 if((err = par->pll_ops->var_to_pll(info, pixclock, var->bits_per_pixel, &par->pll)))
1262                         return err;
1263         }
1264
1265         par->accel_flags = var->accel_flags; /* hack */
1266
1267         if (par->blitter_may_be_busy)
1268                 wait_for_idle(par);
1269
1270         aty_set_crtc(par, &par->crtc);
1271         par->dac_ops->set_dac(info, &par->pll, var->bits_per_pixel, par->accel_flags);
1272         par->pll_ops->set_pll(info, &par->pll);
1273
1274 #ifdef DEBUG
1275         if(par->pll_ops && par->pll_ops->pll_to_var)
1276                 pixclock_in_ps = par->pll_ops->pll_to_var(info, &(par->pll));
1277         else
1278                 pixclock_in_ps = 0;
1279
1280         if(0 == pixclock_in_ps) {
1281                 PRINTKE("ALERT ops->pll_to_var get 0\n");
1282                 pixclock_in_ps = pixclock;
1283         }
1284
1285         memset(&debug, 0, sizeof(debug));
1286         if(!aty_crtc_to_var(&(par->crtc), &debug)) {
1287                 u32 hSync, vRefresh;
1288                 u32 h_disp, h_sync_strt, h_sync_end, h_total;
1289                 u32 v_disp, v_sync_strt, v_sync_end, v_total;
1290
1291                 h_disp = debug.xres;
1292                 h_sync_strt = h_disp + debug.right_margin;
1293                 h_sync_end = h_sync_strt + debug.hsync_len;
1294                 h_total = h_sync_end + debug.left_margin;
1295                 v_disp = debug.yres;
1296                 v_sync_strt = v_disp + debug.lower_margin;
1297                 v_sync_end = v_sync_strt + debug.vsync_len;
1298                 v_total = v_sync_end + debug.upper_margin;
1299
1300                 hSync = 1000000000 / (pixclock_in_ps * h_total);
1301                 vRefresh = (hSync * 1000) / v_total;
1302                 if (par->crtc.gen_cntl & CRTC_INTERLACE_EN)
1303                 vRefresh *= 2;
1304                 if (par->crtc.gen_cntl & CRTC_DBL_SCAN_EN)
1305                 vRefresh /= 2;
1306
1307                 DPRINTK("atyfb_set_par\n");
1308                 DPRINTK(" Set Visible Mode to %ix%i-%i\n", var->xres, var->yres, var->bits_per_pixel);
1309                 DPRINTK(" Virtual resolution %ix%i, pixclock_in_ps %i (calculated %i)\n",
1310                         var->xres_virtual, var->yres_virtual, pixclock, pixclock_in_ps);
1311                 DPRINTK(" Dot clock:           %i MHz\n", 1000000 / pixclock_in_ps);
1312                 DPRINTK(" Horizontal sync:     %i kHz\n", hSync);
1313                 DPRINTK(" Vertical refresh:    %i Hz\n", vRefresh);
1314                 DPRINTK(" x  style: %i.%03i %i %i %i %i   %i %i %i %i\n",
1315                         1000000 / pixclock_in_ps, 1000000 % pixclock_in_ps,
1316                         h_disp, h_sync_strt, h_sync_end, h_total,
1317                         v_disp, v_sync_strt, v_sync_end, v_total);
1318                 DPRINTK(" fb style: %i  %i %i %i %i %i %i %i %i\n",
1319                         pixclock_in_ps,
1320                         debug.left_margin, h_disp, debug.right_margin, debug.hsync_len,
1321                         debug.upper_margin, v_disp, debug.lower_margin, debug.vsync_len);
1322         }
1323 #endif /* DEBUG */
1324
1325         if (!M64_HAS(INTEGRATED)) {
1326                 /* Don't forget MEM_CNTL */
1327                 tmp = aty_ld_le32(MEM_CNTL, par) & 0xf0ffffff;
1328                 switch (var->bits_per_pixel) {
1329                 case 8:
1330                         tmp |= 0x02000000;
1331                         break;
1332                 case 16:
1333                         tmp |= 0x03000000;
1334                         break;
1335                 case 32:
1336                         tmp |= 0x06000000;
1337                         break;
1338                 }
1339                 aty_st_le32(MEM_CNTL, tmp, par);
1340         } else {
1341                 tmp = aty_ld_le32(MEM_CNTL, par) & 0xf00fffff;
1342                 if (!M64_HAS(MAGIC_POSTDIV))
1343                         tmp |= par->mem_refresh_rate << 20;
1344                 switch (var->bits_per_pixel) {
1345                 case 8:
1346                 case 24:
1347                         tmp |= 0x00000000;
1348                         break;
1349                 case 16:
1350                         tmp |= 0x04000000;
1351                         break;
1352                 case 32:
1353                         tmp |= 0x08000000;
1354                         break;
1355                 }
1356                 if (M64_HAS(CT_BUS)) {
1357                         aty_st_le32(DAC_CNTL, 0x87010184, par);
1358                         aty_st_le32(BUS_CNTL, 0x680000f9, par);
1359                 } else if (M64_HAS(VT_BUS)) {
1360                         aty_st_le32(DAC_CNTL, 0x87010184, par);
1361                         aty_st_le32(BUS_CNTL, 0x680000f9, par);
1362                 } else if (M64_HAS(MOBIL_BUS)) {
1363                         aty_st_le32(DAC_CNTL, 0x80010102, par);
1364                         aty_st_le32(BUS_CNTL, 0x7b33a040 | (par->aux_start ? BUS_APER_REG_DIS : 0), par);
1365                 } else {
1366                         /* GT */
1367                         aty_st_le32(DAC_CNTL, 0x86010102, par);
1368                         aty_st_le32(BUS_CNTL, 0x7b23a040 | (par->aux_start ? BUS_APER_REG_DIS : 0), par);
1369                         aty_st_le32(EXT_MEM_CNTL, aty_ld_le32(EXT_MEM_CNTL, par) | 0x5000001, par);
1370                 }
1371                 aty_st_le32(MEM_CNTL, tmp, par);
1372         }
1373         aty_st_8(DAC_MASK, 0xff, par);
1374
1375         info->fix.line_length = var->xres_virtual * var->bits_per_pixel/8;
1376         info->fix.visual = var->bits_per_pixel <= 8 ?
1377                 FB_VISUAL_PSEUDOCOLOR : FB_VISUAL_DIRECTCOLOR;
1378
1379         /* Initialize the graphics engine */
1380         if (par->accel_flags & FB_ACCELF_TEXT)
1381                 aty_init_engine(par, info);
1382
1383 #ifdef CONFIG_BOOTX_TEXT
1384         btext_update_display(info->fix.smem_start,
1385                 (((par->crtc.h_tot_disp >> 16) & 0xff) + 1) * 8,
1386                 ((par->crtc.v_tot_disp >> 16) & 0x7ff) + 1,
1387                 var->bits_per_pixel,
1388                 par->crtc.vxres * var->bits_per_pixel / 8);
1389 #endif /* CONFIG_BOOTX_TEXT */
1390 #if 0
1391         /* switch to accelerator mode */
1392         if (!(par->crtc.gen_cntl & CRTC_EXT_DISP_EN))
1393                 aty_st_le32(CRTC_GEN_CNTL, par->crtc.gen_cntl | CRTC_EXT_DISP_EN, par);
1394 #endif
1395 #ifdef DEBUG
1396 {
1397         /* dump non shadow CRTC, pll, LCD registers */
1398         int i; u32 base;
1399
1400         /* CRTC registers */
1401         base = 0x2000;
1402         printk("debug atyfb: Mach64 non-shadow register values:");
1403         for (i = 0; i < 256; i = i+4) {
1404                 if(i%16 == 0) printk("\ndebug atyfb: 0x%04X: ", base + i);
1405                 printk(" %08X", aty_ld_le32(i, par));
1406         }
1407         printk("\n\n");
1408
1409 #ifdef CONFIG_FB_ATY_CT
1410         /* PLL registers */
1411         base = 0x00;
1412         printk("debug atyfb: Mach64 PLL register values:");
1413         for (i = 0; i < 64; i++) {
1414                 if(i%16 == 0) printk("\ndebug atyfb: 0x%02X: ", base + i);
1415                 if(i%4 == 0)  printk(" ");
1416                 printk("%02X", aty_ld_pll_ct(i, par));
1417         }
1418         printk("\n\n");
1419 #endif  /* CONFIG_FB_ATY_CT */
1420
1421 #ifdef CONFIG_FB_ATY_GENERIC_LCD
1422         if (par->lcd_table != 0) {
1423                 /* LCD registers */
1424                 base = 0x00;
1425                 printk("debug atyfb: LCD register values:");
1426                 if(M64_HAS(LT_LCD_REGS)) {
1427                     for(i = 0; i <= POWER_MANAGEMENT; i++) {
1428                         if(i == EXT_VERT_STRETCH)
1429                             continue;
1430                         printk("\ndebug atyfb: 0x%04X: ", lt_lcd_regs[i]);
1431                         printk(" %08X", aty_ld_lcd(i, par));
1432                     }
1433
1434                 } else {
1435                     for (i = 0; i < 64; i++) {
1436                         if(i%4 == 0) printk("\ndebug atyfb: 0x%02X: ", base + i);
1437                         printk(" %08X", aty_ld_lcd(i, par));
1438                     }
1439                 }
1440                 printk("\n\n");
1441         }
1442 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
1443 }
1444 #endif /* DEBUG */
1445         return 0;
1446 }
1447
1448 static int atyfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info)
1449 {
1450         struct atyfb_par *par = (struct atyfb_par *) info->par;
1451         int err;
1452         struct crtc crtc;
1453         union aty_pll pll;
1454         u32 pixclock;
1455
1456         memcpy(&pll, &(par->pll), sizeof(pll));
1457
1458         if((err = aty_var_to_crtc(info, var, &crtc)))
1459                 return err;
1460
1461         pixclock = atyfb_get_pixclock(var, par);
1462
1463         if (pixclock == 0) {
1464                 FAIL("Invalid pixclock");
1465         } else {
1466                 if((err = par->pll_ops->var_to_pll(info, pixclock, var->bits_per_pixel, &pll)))
1467                         return err;
1468         }
1469
1470         if (var->accel_flags & FB_ACCELF_TEXT)
1471                 info->var.accel_flags = FB_ACCELF_TEXT;
1472         else
1473                 info->var.accel_flags = 0;
1474
1475 #if 0 /* fbmon is not done. uncomment for 2.5.x -brad */
1476         if (!fbmon_valid_timings(pixclock, htotal, vtotal, info))
1477                 return -EINVAL;
1478 #endif
1479         aty_crtc_to_var(&crtc, var);
1480         var->pixclock = par->pll_ops->pll_to_var(info, &pll);
1481         return 0;
1482 }
1483
1484 static void set_off_pitch(struct atyfb_par *par, const struct fb_info *info)
1485 {
1486         u32 xoffset = info->var.xoffset;
1487         u32 yoffset = info->var.yoffset;
1488         u32 vxres = par->crtc.vxres;
1489         u32 bpp = info->var.bits_per_pixel;
1490
1491         par->crtc.off_pitch = ((yoffset * vxres + xoffset) * bpp / 64) | (vxres << 19);
1492 }
1493
1494
1495     /*
1496      *  Open/Release the frame buffer device
1497      */
1498
1499 static int atyfb_open(struct fb_info *info, int user)
1500 {
1501         struct atyfb_par *par = (struct atyfb_par *) info->par;
1502
1503         if (user) {
1504                 par->open++;
1505 #ifdef __sparc__
1506                 par->mmaped = 0;
1507 #endif
1508         }
1509         return (0);
1510 }
1511
1512 static irqreturn_t aty_irq(int irq, void *dev_id, struct pt_regs *fp)
1513 {
1514         struct atyfb_par *par = dev_id;
1515         int handled = 0;
1516         u32 int_cntl;
1517
1518         spin_lock(&par->int_lock);
1519
1520         int_cntl = aty_ld_le32(CRTC_INT_CNTL, par);
1521
1522         if (int_cntl & CRTC_VBLANK_INT) {
1523                 /* clear interrupt */
1524                 aty_st_le32(CRTC_INT_CNTL, (int_cntl & CRTC_INT_EN_MASK) | CRTC_VBLANK_INT_AK, par);
1525                 par->vblank.count++;
1526                 if (par->vblank.pan_display) {
1527                         par->vblank.pan_display = 0;
1528                         aty_st_le32(CRTC_OFF_PITCH, par->crtc.off_pitch, par);
1529                 }
1530                 wake_up_interruptible(&par->vblank.wait);
1531                 handled = 1;
1532         }
1533
1534         spin_unlock(&par->int_lock);
1535
1536         return IRQ_RETVAL(handled);
1537 }
1538
1539 static int aty_enable_irq(struct atyfb_par *par, int reenable)
1540 {
1541         u32 int_cntl;
1542
1543         if (!test_and_set_bit(0, &par->irq_flags)) {
1544                 if (request_irq(par->irq, aty_irq, SA_SHIRQ, "atyfb", par)) {
1545                         clear_bit(0, &par->irq_flags);
1546                         return -EINVAL;
1547                 }
1548                 spin_lock_irq(&par->int_lock);
1549                 int_cntl = aty_ld_le32(CRTC_INT_CNTL, par) & CRTC_INT_EN_MASK;
1550                 /* clear interrupt */
1551                 aty_st_le32(CRTC_INT_CNTL, int_cntl | CRTC_VBLANK_INT_AK, par);
1552                 /* enable interrupt */
1553                 aty_st_le32(CRTC_INT_CNTL, int_cntl | CRTC_VBLANK_INT_EN, par);
1554                 spin_unlock_irq(&par->int_lock);
1555         } else if (reenable) {
1556                 spin_lock_irq(&par->int_lock);
1557                 int_cntl = aty_ld_le32(CRTC_INT_CNTL, par) & CRTC_INT_EN_MASK;
1558                 if (!(int_cntl & CRTC_VBLANK_INT_EN)) {
1559                         printk("atyfb: someone disabled IRQ [%08x]\n", int_cntl);
1560                         /* re-enable interrupt */
1561                         aty_st_le32(CRTC_INT_CNTL, int_cntl | CRTC_VBLANK_INT_EN, par );
1562                 }
1563                 spin_unlock_irq(&par->int_lock);
1564         }
1565
1566         return 0;
1567 }
1568
1569 static int aty_disable_irq(struct atyfb_par *par)
1570 {
1571         u32 int_cntl;
1572
1573         if (test_and_clear_bit(0, &par->irq_flags)) {
1574                 if (par->vblank.pan_display) {
1575                         par->vblank.pan_display = 0;
1576                         aty_st_le32(CRTC_OFF_PITCH, par->crtc.off_pitch, par);
1577                 }
1578                 spin_lock_irq(&par->int_lock);
1579                 int_cntl = aty_ld_le32(CRTC_INT_CNTL, par) & CRTC_INT_EN_MASK;
1580                 /* disable interrupt */
1581                 aty_st_le32(CRTC_INT_CNTL, int_cntl & ~CRTC_VBLANK_INT_EN, par );
1582                 spin_unlock_irq(&par->int_lock);
1583                 free_irq(par->irq, par);
1584         }
1585
1586         return 0;
1587 }
1588
1589 static int atyfb_release(struct fb_info *info, int user)
1590 {
1591         struct atyfb_par *par = (struct atyfb_par *) info->par;
1592         if (user) {
1593                 par->open--;
1594                 mdelay(1);
1595                 wait_for_idle(par);
1596                 if (!par->open) {
1597 #ifdef __sparc__
1598                         int was_mmaped = par->mmaped;
1599
1600                         par->mmaped = 0;
1601
1602                         if (was_mmaped) {
1603                                 struct fb_var_screeninfo var;
1604
1605                                 /* Now reset the default display config, we have no
1606                                  * idea what the program(s) which mmap'd the chip did
1607                                  * to the configuration, nor whether it restored it
1608                                  * correctly.
1609                                  */
1610                                 var = default_var;
1611                                 if (noaccel)
1612                                         var.accel_flags &= ~FB_ACCELF_TEXT;
1613                                 else
1614                                         var.accel_flags |= FB_ACCELF_TEXT;
1615                                 if (var.yres == var.yres_virtual) {
1616                                         u32 videoram = (info->fix.smem_len - (PAGE_SIZE << 2));
1617                                         var.yres_virtual = ((videoram * 8) / var.bits_per_pixel) / var.xres_virtual;
1618                                         if (var.yres_virtual < var.yres)
1619                                                 var.yres_virtual = var.yres;
1620                                 }
1621                         }
1622 #endif
1623                         aty_disable_irq(par);
1624                 }
1625         }
1626         return (0);
1627 }
1628
1629     /*
1630      *  Pan or Wrap the Display
1631      *
1632      *  This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
1633      */
1634
1635 static int atyfb_pan_display(struct fb_var_screeninfo *var, struct fb_info *info)
1636 {
1637         struct atyfb_par *par = (struct atyfb_par *) info->par;
1638         u32 xres, yres, xoffset, yoffset;
1639
1640         xres = (((par->crtc.h_tot_disp >> 16) & 0xff) + 1) * 8;
1641         yres = ((par->crtc.v_tot_disp >> 16) & 0x7ff) + 1;
1642         if (par->crtc.gen_cntl & CRTC_DBL_SCAN_EN)
1643                 yres >>= 1;
1644         xoffset = (var->xoffset + 7) & ~7;
1645         yoffset = var->yoffset;
1646         if (xoffset + xres > par->crtc.vxres || yoffset + yres > par->crtc.vyres)
1647                 return -EINVAL;
1648         info->var.xoffset = xoffset;
1649         info->var.yoffset = yoffset;
1650         if (par->asleep)
1651                 return 0;
1652
1653         set_off_pitch(par, info);
1654         if ((var->activate & FB_ACTIVATE_VBL) && !aty_enable_irq(par, 0)) {
1655                 par->vblank.pan_display = 1;
1656         } else {
1657                 par->vblank.pan_display = 0;
1658                 aty_st_le32(CRTC_OFF_PITCH, par->crtc.off_pitch, par);
1659         }
1660
1661         return 0;
1662 }
1663
1664 static int aty_waitforvblank(struct atyfb_par *par, u32 crtc)
1665 {
1666         struct aty_interrupt *vbl;
1667         unsigned int count;
1668         int ret;
1669
1670         switch (crtc) {
1671         case 0:
1672                 vbl = &par->vblank;
1673                 break;
1674         default:
1675                 return -ENODEV;
1676         }
1677
1678         ret = aty_enable_irq(par, 0);
1679         if (ret)
1680                 return ret;
1681
1682         count = vbl->count;
1683         ret = wait_event_interruptible_timeout(vbl->wait, count != vbl->count, HZ/10);
1684         if (ret < 0) {
1685                 return ret;
1686         }
1687         if (ret == 0) {
1688                 aty_enable_irq(par, 1);
1689                 return -ETIMEDOUT;
1690         }
1691
1692         return 0;
1693 }
1694
1695
1696 #ifdef DEBUG
1697 #define ATYIO_CLKR              0x41545900      /* ATY\00 */
1698 #define ATYIO_CLKW              0x41545901      /* ATY\01 */
1699
1700 struct atyclk {
1701         u32 ref_clk_per;
1702         u8 pll_ref_div;
1703         u8 mclk_fb_div;
1704         u8 mclk_post_div;       /* 1,2,3,4,8 */
1705         u8 mclk_fb_mult;        /* 2 or 4 */
1706         u8 xclk_post_div;       /* 1,2,3,4,8 */
1707         u8 vclk_fb_div;
1708         u8 vclk_post_div;       /* 1,2,3,4,6,8,12 */
1709         u32 dsp_xclks_per_row;  /* 0-16383 */
1710         u32 dsp_loop_latency;   /* 0-15 */
1711         u32 dsp_precision;      /* 0-7 */
1712         u32 dsp_on;             /* 0-2047 */
1713         u32 dsp_off;            /* 0-2047 */
1714 };
1715
1716 #define ATYIO_FEATR             0x41545902      /* ATY\02 */
1717 #define ATYIO_FEATW             0x41545903      /* ATY\03 */
1718 #endif
1719
1720 #ifndef FBIO_WAITFORVSYNC
1721 #define FBIO_WAITFORVSYNC _IOW('F', 0x20, __u32)
1722 #endif
1723
1724 static int atyfb_ioctl(struct inode *inode, struct file *file, u_int cmd,
1725         u_long arg, struct fb_info *info)
1726 {
1727         struct atyfb_par *par = (struct atyfb_par *) info->par;
1728 #ifdef __sparc__
1729         struct fbtype fbtyp;
1730 #endif
1731
1732         switch (cmd) {
1733 #ifdef __sparc__
1734         case FBIOGTYPE:
1735                 fbtyp.fb_type = FBTYPE_PCI_GENERIC;
1736                 fbtyp.fb_width = par->crtc.vxres;
1737                 fbtyp.fb_height = par->crtc.vyres;
1738                 fbtyp.fb_depth = info->var.bits_per_pixel;
1739                 fbtyp.fb_cmsize = info->cmap.len;
1740                 fbtyp.fb_size = info->fix.smem_len;
1741                 if (copy_to_user((struct fbtype __user *) arg, &fbtyp, sizeof(fbtyp)))
1742                         return -EFAULT;
1743                 break;
1744 #endif /* __sparc__ */
1745
1746         case FBIO_WAITFORVSYNC:
1747                 {
1748                         u32 crtc;
1749
1750                         if (get_user(crtc, (__u32 __user *) arg))
1751                                 return -EFAULT;
1752
1753                         return aty_waitforvblank(par, crtc);
1754                 }
1755                 break;
1756
1757 #if defined(DEBUG) && defined(CONFIG_FB_ATY_CT)
1758         case ATYIO_CLKR:
1759                 if (M64_HAS(INTEGRATED)) {
1760                         struct atyclk clk;
1761                         union aty_pll *pll = &(par->pll);
1762                         u32 dsp_config = pll->ct.dsp_config;
1763                         u32 dsp_on_off = pll->ct.dsp_on_off;
1764                         clk.ref_clk_per = par->ref_clk_per;
1765                         clk.pll_ref_div = pll->ct.pll_ref_div;
1766                         clk.mclk_fb_div = pll->ct.mclk_fb_div;
1767                         clk.mclk_post_div = pll->ct.mclk_post_div_real;
1768                         clk.mclk_fb_mult = pll->ct.mclk_fb_mult;
1769                         clk.xclk_post_div = pll->ct.xclk_post_div_real;
1770                         clk.vclk_fb_div = pll->ct.vclk_fb_div;
1771                         clk.vclk_post_div = pll->ct.vclk_post_div_real;
1772                         clk.dsp_xclks_per_row = dsp_config & 0x3fff;
1773                         clk.dsp_loop_latency = (dsp_config >> 16) & 0xf;
1774                         clk.dsp_precision = (dsp_config >> 20) & 7;
1775                         clk.dsp_off = dsp_on_off & 0x7ff;
1776                         clk.dsp_on = (dsp_on_off >> 16) & 0x7ff;
1777                         if (copy_to_user((struct atyclk __user *) arg, &clk,
1778                                          sizeof(clk)))
1779                                 return -EFAULT;
1780                 } else
1781                         return -EINVAL;
1782                 break;
1783         case ATYIO_CLKW:
1784                 if (M64_HAS(INTEGRATED)) {
1785                         struct atyclk clk;
1786                         union aty_pll *pll = &(par->pll);
1787                         if (copy_from_user(&clk, (struct atyclk __user *) arg, sizeof(clk)))
1788                                 return -EFAULT;
1789                         par->ref_clk_per = clk.ref_clk_per;
1790                         pll->ct.pll_ref_div = clk.pll_ref_div;
1791                         pll->ct.mclk_fb_div = clk.mclk_fb_div;
1792                         pll->ct.mclk_post_div_real = clk.mclk_post_div;
1793                         pll->ct.mclk_fb_mult = clk.mclk_fb_mult;
1794                         pll->ct.xclk_post_div_real = clk.xclk_post_div;
1795                         pll->ct.vclk_fb_div = clk.vclk_fb_div;
1796                         pll->ct.vclk_post_div_real = clk.vclk_post_div;
1797                         pll->ct.dsp_config = (clk.dsp_xclks_per_row & 0x3fff) |
1798                                 ((clk.dsp_loop_latency & 0xf)<<16)| ((clk.dsp_precision & 7)<<20);
1799                         pll->ct.dsp_on_off = (clk.dsp_off & 0x7ff) | ((clk.dsp_on & 0x7ff)<<16);
1800                         /*aty_calc_pll_ct(info, &pll->ct);*/
1801                         aty_set_pll_ct(info, pll);
1802                 } else
1803                         return -EINVAL;
1804                 break;
1805         case ATYIO_FEATR:
1806                 if (get_user(par->features, (u32 __user *) arg))
1807                         return -EFAULT;
1808                 break;
1809         case ATYIO_FEATW:
1810                 if (put_user(par->features, (u32 __user *) arg))
1811                         return -EFAULT;
1812                 break;
1813 #endif /* DEBUG && CONFIG_FB_ATY_CT */
1814         default:
1815                 return -EINVAL;
1816         }
1817         return 0;
1818 }
1819
1820 static int atyfb_sync(struct fb_info *info)
1821 {
1822         struct atyfb_par *par = (struct atyfb_par *) info->par;
1823
1824         if (par->blitter_may_be_busy)
1825                 wait_for_idle(par);
1826         return 0;
1827 }
1828
1829 #ifdef __sparc__
1830 static int atyfb_mmap(struct fb_info *info, struct file *file, struct vm_area_struct *vma)
1831 {
1832         struct atyfb_par *par = (struct atyfb_par *) info->par;
1833         unsigned int size, page, map_size = 0;
1834         unsigned long map_offset = 0;
1835         unsigned long off;
1836         int i;
1837
1838         if (!par->mmap_map)
1839                 return -ENXIO;
1840
1841         if (vma->vm_pgoff > (~0UL >> PAGE_SHIFT))
1842                 return -EINVAL;
1843
1844         off = vma->vm_pgoff << PAGE_SHIFT;
1845         size = vma->vm_end - vma->vm_start;
1846
1847         /* To stop the swapper from even considering these pages. */
1848         vma->vm_flags |= (VM_IO | VM_RESERVED);
1849
1850         if (((vma->vm_pgoff == 0) && (size == info->fix.smem_len)) ||
1851             ((off == info->fix.smem_len) && (size == PAGE_SIZE)))
1852                 off += 0x8000000000000000UL;
1853
1854         vma->vm_pgoff = off >> PAGE_SHIFT;      /* propagate off changes */
1855
1856         /* Each page, see which map applies */
1857         for (page = 0; page < size;) {
1858                 map_size = 0;
1859                 for (i = 0; par->mmap_map[i].size; i++) {
1860                         unsigned long start = par->mmap_map[i].voff;
1861                         unsigned long end = start + par->mmap_map[i].size;
1862                         unsigned long offset = off + page;
1863
1864                         if (start > offset)
1865                                 continue;
1866                         if (offset >= end)
1867                                 continue;
1868
1869                         map_size = par->mmap_map[i].size - (offset - start);
1870                         map_offset =
1871                             par->mmap_map[i].poff + (offset - start);
1872                         break;
1873                 }
1874                 if (!map_size) {
1875                         page += PAGE_SIZE;
1876                         continue;
1877                 }
1878                 if (page + map_size > size)
1879                         map_size = size - page;
1880
1881                 pgprot_val(vma->vm_page_prot) &=
1882                     ~(par->mmap_map[i].prot_mask);
1883                 pgprot_val(vma->vm_page_prot) |= par->mmap_map[i].prot_flag;
1884
1885                 if (remap_pfn_range(vma, vma->vm_start + page,
1886                         map_offset >> PAGE_SHIFT, map_size, vma->vm_page_prot))
1887                         return -EAGAIN;
1888
1889                 page += map_size;
1890         }
1891
1892         if (!map_size)
1893                 return -EINVAL;
1894
1895         if (!par->mmaped)
1896                 par->mmaped = 1;
1897         return 0;
1898 }
1899
1900 static struct {
1901         u32 yoffset;
1902         u8 r[2][256];
1903         u8 g[2][256];
1904         u8 b[2][256];
1905 } atyfb_save;
1906
1907 static void atyfb_save_palette(struct atyfb_par *par, int enter)
1908 {
1909         int i, tmp;
1910
1911         for (i = 0; i < 256; i++) {
1912                 tmp = aty_ld_8(DAC_CNTL, par) & 0xfc;
1913                 if (M64_HAS(EXTRA_BRIGHT))
1914                         tmp |= 0x2;
1915                 aty_st_8(DAC_CNTL, tmp, par);
1916                 aty_st_8(DAC_MASK, 0xff, par);
1917
1918                 writeb(i, &par->aty_cmap_regs->rindex);
1919                 atyfb_save.r[enter][i] = readb(&par->aty_cmap_regs->lut);
1920                 atyfb_save.g[enter][i] = readb(&par->aty_cmap_regs->lut);
1921                 atyfb_save.b[enter][i] = readb(&par->aty_cmap_regs->lut);
1922                 writeb(i, &par->aty_cmap_regs->windex);
1923                 writeb(atyfb_save.r[1 - enter][i],
1924                        &par->aty_cmap_regs->lut);
1925                 writeb(atyfb_save.g[1 - enter][i],
1926                        &par->aty_cmap_regs->lut);
1927                 writeb(atyfb_save.b[1 - enter][i],
1928                        &par->aty_cmap_regs->lut);
1929         }
1930 }
1931
1932 static void atyfb_palette(int enter)
1933 {
1934         struct atyfb_par *par;
1935         struct fb_info *info;
1936         int i;
1937
1938         for (i = 0; i < FB_MAX; i++) {
1939                 info = registered_fb[i];
1940                 if (info && info->fbops == &atyfb_ops) {
1941                         par = (struct atyfb_par *) info->par;
1942                         
1943                         atyfb_save_palette(par, enter);
1944                         if (enter) {
1945                                 atyfb_save.yoffset = info->var.yoffset;
1946                                 info->var.yoffset = 0;
1947                                 set_off_pitch(par, info);
1948                         } else {
1949                                 info->var.yoffset = atyfb_save.yoffset;
1950                                 set_off_pitch(par, info);
1951                         }
1952                         aty_st_le32(CRTC_OFF_PITCH, par->crtc.off_pitch, par);
1953                         break;
1954                 }
1955         }
1956 }
1957 #endif /* __sparc__ */
1958
1959
1960
1961 #if defined(CONFIG_PM) && defined(CONFIG_PCI)
1962
1963 /* Power management routines. Those are used for PowerBook sleep.
1964  */
1965 static int aty_power_mgmt(int sleep, struct atyfb_par *par)
1966 {
1967         u32 pm;
1968         int timeout;
1969
1970         pm = aty_ld_lcd(POWER_MANAGEMENT, par);
1971         pm = (pm & ~PWR_MGT_MODE_MASK) | PWR_MGT_MODE_REG;
1972         aty_st_lcd(POWER_MANAGEMENT, pm, par);
1973         pm = aty_ld_lcd(POWER_MANAGEMENT, par);
1974
1975         timeout = 2000;
1976         if (sleep) {
1977                 /* Sleep */
1978                 pm &= ~PWR_MGT_ON;
1979                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
1980                 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
1981                 udelay(10);
1982                 pm &= ~(PWR_BLON | AUTO_PWR_UP);
1983                 pm |= SUSPEND_NOW;
1984                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
1985                 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
1986                 udelay(10);
1987                 pm |= PWR_MGT_ON;
1988                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
1989                 do {
1990                         pm = aty_ld_lcd(POWER_MANAGEMENT, par);
1991                         mdelay(1);
1992                         if ((--timeout) == 0)
1993                                 break;
1994                 } while ((pm & PWR_MGT_STATUS_MASK) != PWR_MGT_STATUS_SUSPEND);
1995         } else {
1996                 /* Wakeup */
1997                 pm &= ~PWR_MGT_ON;
1998                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
1999                 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
2000                 udelay(10);
2001                 pm &= ~SUSPEND_NOW;
2002                 pm |= (PWR_BLON | AUTO_PWR_UP);
2003                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
2004                 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
2005                 udelay(10);
2006                 pm |= PWR_MGT_ON;
2007                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
2008                 do {
2009                         pm = aty_ld_lcd(POWER_MANAGEMENT, par);
2010                         mdelay(1);
2011                         if ((--timeout) == 0)
2012                                 break;
2013                 } while ((pm & PWR_MGT_STATUS_MASK) != 0);
2014         }
2015         mdelay(500);
2016
2017         return timeout ? 0 : -EIO;
2018 }
2019
2020 static int atyfb_pci_suspend(struct pci_dev *pdev, pm_message_t state)
2021 {
2022         struct fb_info *info = pci_get_drvdata(pdev);
2023         struct atyfb_par *par = (struct atyfb_par *) info->par;
2024
2025 #ifdef CONFIG_PPC_PMAC
2026         /* HACK ALERT ! Once I find a proper way to say to each driver
2027          * individually what will happen with it's PCI slot, I'll change
2028          * that. On laptops, the AGP slot is just unclocked, so D2 is
2029          * expected, while on desktops, the card is powered off
2030          */
2031         if (state >= 3)
2032                 state = 2;
2033 #endif /* CONFIG_PPC_PMAC */
2034
2035         if (state != 2 || state == pdev->dev.power.power_state)
2036                 return 0;
2037
2038         acquire_console_sem();
2039
2040         fb_set_suspend(info, 1);
2041
2042         /* Idle & reset engine */
2043         wait_for_idle(par);
2044         aty_reset_engine(par);
2045
2046         /* Blank display and LCD */
2047         atyfb_blank(FB_BLANK_POWERDOWN, info);
2048
2049         par->asleep = 1;
2050         par->lock_blank = 1;
2051
2052         /* Set chip to "suspend" mode */
2053         if (aty_power_mgmt(1, par)) {
2054                 par->asleep = 0;
2055                 par->lock_blank = 0;
2056                 atyfb_blank(FB_BLANK_UNBLANK, info);
2057                 fb_set_suspend(info, 0);
2058                 release_console_sem();
2059                 return -EIO;
2060         }
2061
2062         release_console_sem();
2063
2064         pdev->dev.power.power_state = state;
2065
2066         return 0;
2067 }
2068
2069 static int atyfb_pci_resume(struct pci_dev *pdev)
2070 {
2071         struct fb_info *info = pci_get_drvdata(pdev);
2072         struct atyfb_par *par = (struct atyfb_par *) info->par;
2073
2074         if (pdev->dev.power.power_state == 0)
2075                 return 0;
2076
2077         acquire_console_sem();
2078
2079         if (pdev->dev.power.power_state == 2)
2080                 aty_power_mgmt(0, par);
2081         par->asleep = 0;
2082
2083         /* Restore display */
2084         atyfb_set_par(info);
2085
2086         /* Refresh */
2087         fb_set_suspend(info, 0);
2088
2089         /* Unblank */
2090         par->lock_blank = 0;
2091         atyfb_blank(FB_BLANK_UNBLANK, info);
2092
2093         release_console_sem();
2094
2095         pdev->dev.power.power_state = PMSG_ON;
2096
2097         return 0;
2098 }
2099
2100 #endif /*  defined(CONFIG_PM) && defined(CONFIG_PCI) */
2101
2102 #ifdef CONFIG_PMAC_BACKLIGHT
2103
2104     /*
2105      *   LCD backlight control
2106      */
2107
2108 static int backlight_conv[] = {
2109         0x00, 0x3f, 0x4c, 0x59, 0x66, 0x73, 0x80, 0x8d,
2110         0x9a, 0xa7, 0xb4, 0xc1, 0xcf, 0xdc, 0xe9, 0xff
2111 };
2112
2113 static int aty_set_backlight_enable(int on, int level, void *data)
2114 {
2115         struct fb_info *info = (struct fb_info *) data;
2116         struct atyfb_par *par = (struct atyfb_par *) info->par;
2117         unsigned int reg = aty_ld_lcd(LCD_MISC_CNTL, par);
2118
2119         reg |= (BLMOD_EN | BIASMOD_EN);
2120         if (on && level > BACKLIGHT_OFF) {
2121                 reg &= ~BIAS_MOD_LEVEL_MASK;
2122                 reg |= (backlight_conv[level] << BIAS_MOD_LEVEL_SHIFT);
2123         } else {
2124                 reg &= ~BIAS_MOD_LEVEL_MASK;
2125                 reg |= (backlight_conv[0] << BIAS_MOD_LEVEL_SHIFT);
2126         }
2127         aty_st_lcd(LCD_MISC_CNTL, reg, par);
2128         return 0;
2129 }
2130
2131 static int aty_set_backlight_level(int level, void *data)
2132 {
2133         return aty_set_backlight_enable(1, level, data);
2134 }
2135
2136 static struct backlight_controller aty_backlight_controller = {
2137         aty_set_backlight_enable,
2138         aty_set_backlight_level
2139 };
2140 #endif /* CONFIG_PMAC_BACKLIGHT */
2141
2142 static void __init aty_calc_mem_refresh(struct atyfb_par *par, int xclk)
2143 {
2144         const int ragepro_tbl[] = {
2145                 44, 50, 55, 66, 75, 80, 100
2146         };
2147         const int ragexl_tbl[] = {
2148                 50, 66, 75, 83, 90, 95, 100, 105,
2149                 110, 115, 120, 125, 133, 143, 166
2150         };
2151         const int *refresh_tbl;
2152         int i, size;
2153
2154         if (IS_XL(par->pci_id) || IS_MOBILITY(par->pci_id)) {
2155                 refresh_tbl = ragexl_tbl;
2156                 size = sizeof(ragexl_tbl)/sizeof(int);
2157         } else {
2158                 refresh_tbl = ragepro_tbl;
2159                 size = sizeof(ragepro_tbl)/sizeof(int);
2160         }
2161
2162         for (i=0; i < size; i++) {
2163                 if (xclk < refresh_tbl[i])
2164                 break;
2165         }
2166         par->mem_refresh_rate = i;
2167 }
2168
2169     /*
2170      *  Initialisation
2171      */
2172
2173 static struct fb_info *fb_list = NULL;
2174
2175 static int __init aty_init(struct fb_info *info, const char *name)
2176 {
2177         struct atyfb_par *par = (struct atyfb_par *) info->par;
2178         const char *ramname = NULL, *xtal;
2179         int gtb_memsize;
2180         struct fb_var_screeninfo var;
2181         u8 pll_ref_div;
2182         u32 i;
2183 #if defined(CONFIG_PPC)
2184         int sense;
2185 #endif
2186
2187         init_waitqueue_head(&par->vblank.wait);
2188         spin_lock_init(&par->int_lock);
2189
2190         par->aty_cmap_regs =
2191             (struct aty_cmap_regs __iomem *) (par->ati_regbase + 0xc0);
2192
2193 #ifdef CONFIG_PPC_PMAC
2194         /* The Apple iBook1 uses non-standard memory frequencies. We detect it
2195          * and set the frequency manually. */
2196         if (machine_is_compatible("PowerBook2,1")) {
2197                 par->pll_limits.mclk = 70;
2198                 par->pll_limits.xclk = 53;
2199         }
2200 #endif
2201         if (pll)
2202                 par->pll_limits.pll_max = pll;
2203         if (mclk)
2204                 par->pll_limits.mclk = mclk;
2205         if (xclk)
2206                 par->pll_limits.xclk = xclk;
2207
2208         aty_calc_mem_refresh(par, par->pll_limits.xclk);
2209         par->pll_per = 1000000/par->pll_limits.pll_max;
2210         par->mclk_per = 1000000/par->pll_limits.mclk;
2211         par->xclk_per = 1000000/par->pll_limits.xclk;
2212
2213         par->ref_clk_per = 1000000000000ULL / 14318180;
2214         xtal = "14.31818";
2215
2216 #ifdef CONFIG_FB_ATY_GX
2217         if (!M64_HAS(INTEGRATED)) {
2218                 u32 stat0;
2219                 u8 dac_type, dac_subtype, clk_type;
2220                 stat0 = aty_ld_le32(CONFIG_STAT0, par);
2221                 par->bus_type = (stat0 >> 0) & 0x07;
2222                 par->ram_type = (stat0 >> 3) & 0x07;
2223                 ramname = aty_gx_ram[par->ram_type];
2224                 /* FIXME: clockchip/RAMDAC probing? */
2225                 dac_type = (aty_ld_le32(DAC_CNTL, par) >> 16) & 0x07;
2226 #ifdef CONFIG_ATARI
2227                 clk_type = CLK_ATI18818_1;
2228                 dac_type = (stat0 >> 9) & 0x07;
2229                 if (dac_type == 0x07)
2230                         dac_subtype = DAC_ATT20C408;
2231                 else
2232                         dac_subtype = (aty_ld_8(SCRATCH_REG1 + 1, par) & 0xF0) | dac_type;
2233 #else
2234                 dac_type = DAC_IBMRGB514;
2235                 dac_subtype = DAC_IBMRGB514;
2236                 clk_type = CLK_IBMRGB514;
2237 #endif
2238                 switch (dac_subtype) {
2239                 case DAC_IBMRGB514:
2240                         par->dac_ops = &aty_dac_ibm514;
2241                         break;
2242                 case DAC_ATI68860_B:
2243                 case DAC_ATI68860_C:
2244                         par->dac_ops = &aty_dac_ati68860b;
2245                         break;
2246                 case DAC_ATT20C408:
2247                 case DAC_ATT21C498:
2248                         par->dac_ops = &aty_dac_att21c498;
2249                         break;
2250                 default:
2251                         PRINTKI("aty_init: DAC type not implemented yet!\n");
2252                         par->dac_ops = &aty_dac_unsupported;
2253                         break;
2254                 }
2255                 switch (clk_type) {
2256                 case CLK_ATI18818_1:
2257                         par->pll_ops = &aty_pll_ati18818_1;
2258                         break;
2259                 case CLK_STG1703:
2260                         par->pll_ops = &aty_pll_stg1703;
2261                         break;
2262                 case CLK_CH8398:
2263                         par->pll_ops = &aty_pll_ch8398;
2264                         break;
2265                 case CLK_ATT20C408:
2266                         par->pll_ops = &aty_pll_att20c408;
2267                         break;
2268                 case CLK_IBMRGB514:
2269                         par->pll_ops = &aty_pll_ibm514;
2270                         break;
2271                 default:
2272                         PRINTKI("aty_init: CLK type not implemented yet!");
2273                         par->pll_ops = &aty_pll_unsupported;
2274                         break;
2275                 }
2276         }
2277 #endif /* CONFIG_FB_ATY_GX */
2278 #ifdef CONFIG_FB_ATY_CT
2279         if (M64_HAS(INTEGRATED)) {
2280                 par->dac_ops = &aty_dac_ct;
2281                 par->pll_ops = &aty_pll_ct;
2282                 par->bus_type = PCI;
2283 #ifdef CONFIG_FB_ATY_XL_INIT
2284                 if (IS_XL(par->pci_id))
2285                         atyfb_xl_init(info);
2286 #endif
2287                 par->ram_type = (aty_ld_le32(CONFIG_STAT0, par) & 0x07);
2288                 ramname = aty_ct_ram[par->ram_type];
2289                 /* for many chips, the mclk is 67 MHz for SDRAM, 63 MHz otherwise */
2290                 if (par->pll_limits.mclk == 67 && par->ram_type < SDRAM)
2291                         par->pll_limits.mclk = 63;
2292         }
2293
2294         if (M64_HAS(GTB_DSP)
2295             && (pll_ref_div = aty_ld_pll_ct(PLL_REF_DIV, par))) {
2296                 int diff1, diff2;
2297                 diff1 = 510 * 14 / pll_ref_div - par->pll_limits.pll_max;
2298                 diff2 = 510 * 29 / pll_ref_div - par->pll_limits.pll_max;
2299                 if (diff1 < 0)
2300                         diff1 = -diff1;
2301                 if (diff2 < 0)
2302                         diff2 = -diff2;
2303                 if (diff2 < diff1) {
2304                         par->ref_clk_per = 1000000000000ULL / 29498928;
2305                         xtal = "29.498928";
2306                 }
2307         }
2308 #endif /* CONFIG_FB_ATY_CT */
2309
2310         /* save previous video mode */
2311         aty_get_crtc(par, &saved_crtc);
2312         if(par->pll_ops->get_pll)
2313                 par->pll_ops->get_pll(info, &saved_pll);
2314
2315         i = aty_ld_le32(MEM_CNTL, par);
2316         gtb_memsize = M64_HAS(GTB_DSP);
2317         if (gtb_memsize)
2318                 switch (i & 0xF) {      /* 0xF used instead of MEM_SIZE_ALIAS */
2319                 case MEM_SIZE_512K:
2320                         info->fix.smem_len = 0x80000;
2321                         break;
2322                 case MEM_SIZE_1M:
2323                         info->fix.smem_len = 0x100000;
2324                         break;
2325                 case MEM_SIZE_2M_GTB:
2326                         info->fix.smem_len = 0x200000;
2327                         break;
2328                 case MEM_SIZE_4M_GTB:
2329                         info->fix.smem_len = 0x400000;
2330                         break;
2331                 case MEM_SIZE_6M_GTB:
2332                         info->fix.smem_len = 0x600000;
2333                         break;
2334                 case MEM_SIZE_8M_GTB:
2335                         info->fix.smem_len = 0x800000;
2336                         break;
2337                 default:
2338                         info->fix.smem_len = 0x80000;
2339         } else
2340                 switch (i & MEM_SIZE_ALIAS) {
2341                 case MEM_SIZE_512K:
2342                         info->fix.smem_len = 0x80000;
2343                         break;
2344                 case MEM_SIZE_1M:
2345                         info->fix.smem_len = 0x100000;
2346                         break;
2347                 case MEM_SIZE_2M:
2348                         info->fix.smem_len = 0x200000;
2349                         break;
2350                 case MEM_SIZE_4M:
2351                         info->fix.smem_len = 0x400000;
2352                         break;
2353                 case MEM_SIZE_6M:
2354                         info->fix.smem_len = 0x600000;
2355                         break;
2356                 case MEM_SIZE_8M:
2357                         info->fix.smem_len = 0x800000;
2358                         break;
2359                 default:
2360                         info->fix.smem_len = 0x80000;
2361                 }
2362
2363         if (M64_HAS(MAGIC_VRAM_SIZE)) {
2364                 if (aty_ld_le32(CONFIG_STAT1, par) & 0x40000000)
2365                         info->fix.smem_len += 0x400000;
2366         }
2367
2368         if (vram) {
2369                 info->fix.smem_len = vram * 1024;
2370                 i = i & ~(gtb_memsize ? 0xF : MEM_SIZE_ALIAS);
2371                 if (info->fix.smem_len <= 0x80000)
2372                         i |= MEM_SIZE_512K;
2373                 else if (info->fix.smem_len <= 0x100000)
2374                         i |= MEM_SIZE_1M;
2375                 else if (info->fix.smem_len <= 0x200000)
2376                         i |= gtb_memsize ? MEM_SIZE_2M_GTB : MEM_SIZE_2M;
2377                 else if (info->fix.smem_len <= 0x400000)
2378                         i |= gtb_memsize ? MEM_SIZE_4M_GTB : MEM_SIZE_4M;
2379                 else if (info->fix.smem_len <= 0x600000)
2380                         i |= gtb_memsize ? MEM_SIZE_6M_GTB : MEM_SIZE_6M;
2381                 else
2382                         i |= gtb_memsize ? MEM_SIZE_8M_GTB : MEM_SIZE_8M;
2383                 aty_st_le32(MEM_CNTL, i, par);
2384         }
2385
2386         /*
2387          *  Reg Block 0 (CT-compatible block) is at mmio_start
2388          *  Reg Block 1 (multimedia extensions) is at mmio_start - 0x400
2389          */
2390         if (M64_HAS(GX)) {
2391                 info->fix.mmio_len = 0x400;
2392                 info->fix.accel = FB_ACCEL_ATI_MACH64GX;
2393         } else if (M64_HAS(CT)) {
2394                 info->fix.mmio_len = 0x400;
2395                 info->fix.accel = FB_ACCEL_ATI_MACH64CT;
2396         } else if (M64_HAS(VT)) {
2397                 info->fix.mmio_start -= 0x400;
2398                 info->fix.mmio_len = 0x800;
2399                 info->fix.accel = FB_ACCEL_ATI_MACH64VT;
2400         } else {/* GT */
2401                 info->fix.mmio_start -= 0x400;
2402                 info->fix.mmio_len = 0x800;
2403                 info->fix.accel = FB_ACCEL_ATI_MACH64GT;
2404         }
2405
2406         PRINTKI("%d%c %s, %s MHz XTAL, %d MHz PLL, %d Mhz MCLK, %d MHz XCLK\n",
2407                info->fix.smem_len == 0x80000 ? 512 : (info->fix.smem_len >> 20),
2408                info->fix.smem_len == 0x80000 ? 'K' : 'M', ramname, xtal, par->pll_limits.pll_max,
2409                par->pll_limits.mclk, par->pll_limits.xclk);
2410
2411 #if defined(DEBUG) && defined(CONFIG_ATY_CT)
2412         if (M64_HAS(INTEGRATED)) {
2413                 int i;
2414                 printk("debug atyfb: BUS_CNTL DAC_CNTL MEM_CNTL EXT_MEM_CNTL CRTC_GEN_CNTL "
2415                        "DSP_CONFIG DSP_ON_OFF CLOCK_CNTL\n"
2416                        "debug atyfb: %08x %08x %08x %08x     %08x      %08x   %08x   %08x\n"
2417                        "debug atyfb: PLL",
2418                         aty_ld_le32(BUS_CNTL, par), aty_ld_le32(DAC_CNTL, par),
2419                         aty_ld_le32(MEM_CNTL, par), aty_ld_le32(EXT_MEM_CNTL, par),
2420                         aty_ld_le32(CRTC_GEN_CNTL, par), aty_ld_le32(DSP_CONFIG, par),
2421                         aty_ld_le32(DSP_ON_OFF, par), aty_ld_le32(CLOCK_CNTL, par));
2422                 for (i = 0; i < 40; i++)
2423                         printk(" %02x", aty_ld_pll_ct(i, par));
2424                 printk("\n");
2425         }
2426 #endif
2427         if(par->pll_ops->init_pll)
2428                 par->pll_ops->init_pll(info, &par->pll);
2429
2430         /*
2431          *  Last page of 8 MB (4 MB on ISA) aperture is MMIO
2432          *  FIXME: we should use the auxiliary aperture instead so we can access
2433          *  the full 8 MB of video RAM on 8 MB boards
2434          */
2435
2436         if (!par->aux_start &&
2437                 (info->fix.smem_len == 0x800000 || (par->bus_type == ISA && info->fix.smem_len == 0x400000)))
2438                 info->fix.smem_len -= GUI_RESERVE;
2439
2440         /*
2441          *  Disable register access through the linear aperture
2442          *  if the auxiliary aperture is used so we can access
2443          *  the full 8 MB of video RAM on 8 MB boards.
2444          */
2445         if (par->aux_start)
2446                 aty_st_le32(BUS_CNTL, aty_ld_le32(BUS_CNTL, par) | BUS_APER_REG_DIS, par);
2447
2448 #ifdef CONFIG_MTRR
2449         par->mtrr_aper = -1;
2450         par->mtrr_reg = -1;
2451         if (!nomtrr) {
2452                 /* Cover the whole resource. */
2453                  par->mtrr_aper = mtrr_add(par->res_start, par->res_size, MTRR_TYPE_WRCOMB, 1);
2454                  if (par->mtrr_aper >= 0 && !par->aux_start) {
2455                         /* Make a hole for mmio. */
2456                         par->mtrr_reg = mtrr_add(par->res_start + 0x800000 - GUI_RESERVE,
2457                                 GUI_RESERVE, MTRR_TYPE_UNCACHABLE, 1);
2458                         if (par->mtrr_reg < 0) {
2459                                 mtrr_del(par->mtrr_aper, 0, 0);
2460                                 par->mtrr_aper = -1;
2461                         }
2462                  }
2463         }
2464 #endif
2465
2466         info->fbops = &atyfb_ops;
2467         info->pseudo_palette = pseudo_palette;
2468         info->flags = FBINFO_FLAG_DEFAULT;
2469
2470 #ifdef CONFIG_PMAC_BACKLIGHT
2471         if (M64_HAS(G3_PB_1_1) && machine_is_compatible("PowerBook1,1")) {
2472                 /* these bits let the 101 powerbook wake up from sleep -- paulus */
2473                 aty_st_lcd(POWER_MANAGEMENT, aty_ld_lcd(POWER_MANAGEMENT, par)
2474                            | (USE_F32KHZ | TRISTATE_MEM_EN), par);
2475         } else if (M64_HAS(MOBIL_BUS))
2476                 register_backlight_controller(&aty_backlight_controller, info, "ati");
2477 #endif /* CONFIG_PMAC_BACKLIGHT */
2478
2479         memset(&var, 0, sizeof(var));
2480 #ifdef CONFIG_PPC
2481         if (_machine == _MACH_Pmac) {
2482                 /*
2483                  *  FIXME: The NVRAM stuff should be put in a Mac-specific file, as it
2484                  *         applies to all Mac video cards
2485                  */
2486                 if (mode) {
2487                         if (!mac_find_mode(&var, info, mode, 8))
2488                                 var = default_var;
2489                 } else {
2490                         if (default_vmode == VMODE_CHOOSE) {
2491                                 if (M64_HAS(G3_PB_1024x768))
2492                                         /* G3 PowerBook with 1024x768 LCD */
2493                                         default_vmode = VMODE_1024_768_60;
2494                                 else if (machine_is_compatible("iMac"))
2495                                         default_vmode = VMODE_1024_768_75;
2496                                 else if (machine_is_compatible
2497                                          ("PowerBook2,1"))
2498                                         /* iBook with 800x600 LCD */
2499                                         default_vmode = VMODE_800_600_60;
2500                                 else
2501                                         default_vmode = VMODE_640_480_67;
2502                                 sense = read_aty_sense(par);
2503                                 PRINTKI("monitor sense=%x, mode %d\n",
2504                                         sense,  mac_map_monitor_sense(sense));
2505                         }
2506                         if (default_vmode <= 0 || default_vmode > VMODE_MAX)
2507                                 default_vmode = VMODE_640_480_60;
2508                         if (default_cmode < CMODE_8 || default_cmode > CMODE_32)
2509                                 default_cmode = CMODE_8;
2510                         if (mac_vmode_to_var(default_vmode, default_cmode, &var))
2511                                 var = default_var;
2512                 }
2513         } else
2514 #endif /* !CONFIG_PPC */
2515         if (
2516 #if defined(CONFIG_SPARC32) || defined(CONFIG_SPARC64)
2517            /* On Sparc, unless the user gave a specific mode
2518             * specification, use the PROM probed values in
2519             * default_var.
2520             */
2521             !mode ||
2522 #endif
2523             !fb_find_mode(&var, info, mode, NULL, 0, &defmode, 8))
2524                 var = default_var;
2525
2526         if (noaccel)
2527                 var.accel_flags &= ~FB_ACCELF_TEXT;
2528         else
2529                 var.accel_flags |= FB_ACCELF_TEXT;
2530
2531         if (comp_sync != -1) {
2532                 if (!comp_sync)
2533                         var.sync &= ~FB_SYNC_COMP_HIGH_ACT;
2534                 else
2535                         var.sync |= FB_SYNC_COMP_HIGH_ACT;
2536         }
2537
2538         if (var.yres == var.yres_virtual) {
2539                 u32 videoram = (info->fix.smem_len - (PAGE_SIZE << 2));
2540                 var.yres_virtual = ((videoram * 8) / var.bits_per_pixel) / var.xres_virtual;
2541                 if (var.yres_virtual < var.yres)
2542                         var.yres_virtual = var.yres;
2543         }
2544
2545         if (atyfb_check_var(&var, info)) {
2546                 PRINTKE("can't set default video mode\n");
2547                 goto aty_init_exit;
2548         }
2549
2550 #ifdef __sparc__
2551         atyfb_save_palette(par, 0);
2552 #endif
2553
2554 #ifdef CONFIG_FB_ATY_CT
2555         if (!noaccel && M64_HAS(INTEGRATED))
2556                 aty_init_cursor(info);
2557 #endif /* CONFIG_FB_ATY_CT */
2558         info->var = var;
2559
2560         fb_alloc_cmap(&info->cmap, 256, 0);
2561
2562         if (register_framebuffer(info) < 0)
2563                 goto aty_init_exit;
2564
2565         fb_list = info;
2566
2567         PRINTKI("fb%d: %s frame buffer device on %s\n",
2568                info->node, info->fix.id, name);
2569         return 0;
2570
2571 aty_init_exit:
2572         /* restore video mode */
2573         aty_set_crtc(par, &saved_crtc);
2574         par->pll_ops->set_pll(info, &saved_pll);
2575
2576 #ifdef CONFIG_MTRR
2577         if (par->mtrr_reg >= 0) {
2578             mtrr_del(par->mtrr_reg, 0, 0);
2579             par->mtrr_reg = -1;
2580         }
2581         if (par->mtrr_aper >= 0) {
2582             mtrr_del(par->mtrr_aper, 0, 0);
2583             par->mtrr_aper = -1;
2584         }
2585 #endif
2586         return -1;
2587 }
2588
2589 #ifdef CONFIG_ATARI
2590 static int __init store_video_par(char *video_str, unsigned char m64_num)
2591 {
2592         char *p;
2593         unsigned long vmembase, size, guiregbase;
2594
2595         PRINTKI("store_video_par() '%s' \n", video_str);
2596
2597         if (!(p = strsep(&video_str, ";")) || !*p)
2598                 goto mach64_invalid;
2599         vmembase = simple_strtoul(p, NULL, 0);
2600         if (!(p = strsep(&video_str, ";")) || !*p)
2601                 goto mach64_invalid;
2602         size = simple_strtoul(p, NULL, 0);
2603         if (!(p = strsep(&video_str, ";")) || !*p)
2604                 goto mach64_invalid;
2605         guiregbase = simple_strtoul(p, NULL, 0);
2606
2607         phys_vmembase[m64_num] = vmembase;
2608         phys_size[m64_num] = size;
2609         phys_guiregbase[m64_num] = guiregbase;
2610         PRINTKI("stored them all: $%08lX $%08lX $%08lX \n", vmembase, size,
2611                guiregbase);
2612         return 0;
2613
2614       mach64_invalid:
2615         phys_vmembase[m64_num] = 0;
2616         return -1;
2617 }
2618 #endif /* CONFIG_ATARI */
2619
2620     /*
2621      *  Blank the display.
2622      */
2623
2624 static int atyfb_blank(int blank, struct fb_info *info)
2625 {
2626         struct atyfb_par *par = (struct atyfb_par *) info->par;
2627         u8 gen_cntl;
2628
2629         if (par->lock_blank || par->asleep)
2630                 return 0;
2631
2632 #ifdef CONFIG_PMAC_BACKLIGHT
2633         if ((_machine == _MACH_Pmac) && blank)
2634                 set_backlight_enable(0);
2635 #elif defined(CONFIG_FB_ATY_GENERIC_LCD)
2636         if (par->lcd_table && blank &&
2637             (aty_ld_lcd(LCD_GEN_CNTL, par) & LCD_ON)) {
2638                 u32 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
2639                 pm &= ~PWR_BLON;
2640                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
2641         }
2642 #endif
2643
2644         gen_cntl = aty_ld_8(CRTC_GEN_CNTL, par);
2645         switch (blank) {
2646                 case FB_BLANK_UNBLANK:
2647                         gen_cntl &= ~(0x4c);
2648                         break;
2649                 case FB_BLANK_NORMAL:
2650                         gen_cntl |= 0x40;
2651                         break;
2652                 case FB_BLANK_VSYNC_SUSPEND:
2653                         gen_cntl |= 0x8;
2654                         break;
2655                 case FB_BLANK_HSYNC_SUSPEND:
2656                         gen_cntl |= 0x4;
2657                         break;
2658                 case FB_BLANK_POWERDOWN:
2659                         gen_cntl |= 0x4c;
2660                         break;
2661         }
2662         aty_st_8(CRTC_GEN_CNTL, gen_cntl, par);
2663
2664 #ifdef CONFIG_PMAC_BACKLIGHT
2665         if ((_machine == _MACH_Pmac) && !blank)
2666                 set_backlight_enable(1);
2667 #elif defined(CONFIG_FB_ATY_GENERIC_LCD)
2668         if (par->lcd_table && !blank &&
2669             (aty_ld_lcd(LCD_GEN_CNTL, par) & LCD_ON)) {
2670                 u32 pm = aty_ld_lcd(POWER_MANAGEMENT, par);
2671                 pm |= PWR_BLON;
2672                 aty_st_lcd(POWER_MANAGEMENT, pm, par);
2673         }
2674 #endif
2675
2676         return 0;
2677 }
2678
2679 static void aty_st_pal(u_int regno, u_int red, u_int green, u_int blue,
2680                        const struct atyfb_par *par)
2681 {
2682 #ifdef CONFIG_ATARI
2683         out_8(&par->aty_cmap_regs->windex, regno);
2684         out_8(&par->aty_cmap_regs->lut, red);
2685         out_8(&par->aty_cmap_regs->lut, green);
2686         out_8(&par->aty_cmap_regs->lut, blue);
2687 #else
2688         writeb(regno, &par->aty_cmap_regs->windex);
2689         writeb(red, &par->aty_cmap_regs->lut);
2690         writeb(green, &par->aty_cmap_regs->lut);
2691         writeb(blue, &par->aty_cmap_regs->lut);
2692 #endif
2693 }
2694
2695     /*
2696      *  Set a single color register. The values supplied are already
2697      *  rounded down to the hardware's capabilities (according to the
2698      *  entries in the var structure). Return != 0 for invalid regno.
2699      *  !! 4 & 8 =  PSEUDO, > 8 = DIRECTCOLOR
2700      */
2701
2702 static int atyfb_setcolreg(u_int regno, u_int red, u_int green, u_int blue,
2703         u_int transp, struct fb_info *info)
2704 {
2705         struct atyfb_par *par = (struct atyfb_par *) info->par;
2706         int i, depth;
2707         u32 *pal = info->pseudo_palette;
2708
2709         depth = info->var.bits_per_pixel;
2710         if (depth == 16)
2711                 depth = (info->var.green.length == 5) ? 15 : 16;
2712
2713         if (par->asleep)
2714                 return 0;
2715
2716         if (regno > 255 ||
2717             (depth == 16 && regno > 63) ||
2718             (depth == 15 && regno > 31))
2719                 return 1;
2720
2721         red >>= 8;
2722         green >>= 8;
2723         blue >>= 8;
2724
2725         par->palette[regno].red = red;
2726         par->palette[regno].green = green;
2727         par->palette[regno].blue = blue;
2728
2729         if (regno < 16) {
2730                 switch (depth) {
2731                 case 15:
2732                         pal[regno] = (regno << 10) | (regno << 5) | regno;
2733                         break;
2734                 case 16:
2735                         pal[regno] = (regno << 11) | (regno << 5) | regno;
2736                         break;
2737                 case 24:
2738                         pal[regno] = (regno << 16) | (regno << 8) | regno;
2739                         break;
2740                 case 32:
2741                         i = (regno << 8) | regno;
2742                         pal[regno] = (i << 16) | i;
2743                         break;
2744                 }
2745         }
2746
2747         i = aty_ld_8(DAC_CNTL, par) & 0xfc;
2748         if (M64_HAS(EXTRA_BRIGHT))
2749                 i |= 0x2; /* DAC_CNTL | 0x2 turns off the extra brightness for gt */
2750         aty_st_8(DAC_CNTL, i, par);
2751         aty_st_8(DAC_MASK, 0xff, par);
2752
2753         if (M64_HAS(INTEGRATED)) {
2754                 if (depth == 16) {
2755                         if (regno < 32)
2756                                 aty_st_pal(regno << 3, red,
2757                                            par->palette[regno<<1].green,
2758                                            blue, par);
2759                         red = par->palette[regno>>1].red;
2760                         blue = par->palette[regno>>1].blue;
2761                         regno <<= 2;
2762                 } else if (depth == 15) {
2763                         regno <<= 3;
2764                         for(i = 0; i < 8; i++) {
2765                             aty_st_pal(regno + i, red, green, blue, par);
2766                         }
2767                 }
2768         }
2769         aty_st_pal(regno, red, green, blue, par);
2770
2771         return 0;
2772 }
2773
2774 #ifdef CONFIG_PCI
2775
2776 #ifdef __sparc__
2777
2778 extern void (*prom_palette) (int);
2779
2780 static int __devinit atyfb_setup_sparc(struct pci_dev *pdev,
2781                         struct fb_info *info, unsigned long addr)
2782 {
2783         extern int con_is_present(void);
2784
2785         struct atyfb_par *par = info->par;
2786         struct pcidev_cookie *pcp;
2787         char prop[128];
2788         int node, len, i, j, ret;
2789         u32 mem, chip_id;
2790
2791         /* Do not attach when we have a serial console. */
2792         if (!con_is_present())
2793                 return -ENXIO;
2794
2795         /*
2796          * Map memory-mapped registers.
2797          */
2798         par->ati_regbase = (void *)addr + 0x7ffc00UL;
2799         info->fix.mmio_start = addr + 0x7ffc00UL;
2800
2801         /*
2802          * Map in big-endian aperture.
2803          */
2804         info->screen_base = (char *) (addr + 0x800000UL);
2805         info->fix.smem_start = addr + 0x800000UL;
2806
2807         /*
2808          * Figure mmap addresses from PCI config space.
2809          * Split Framebuffer in big- and little-endian halfs.
2810          */
2811         for (i = 0; i < 6 && pdev->resource[i].start; i++)
2812                 /* nothing */ ;
2813         j = i + 4;
2814
2815         par->mmap_map = kmalloc(j * sizeof(*par->mmap_map), GFP_ATOMIC);
2816         if (!par->mmap_map) {
2817                 PRINTKE("atyfb_setup_sparc() can't alloc mmap_map\n");
2818                 return -ENOMEM;
2819         }
2820         memset(par->mmap_map, 0, j * sizeof(*par->mmap_map));
2821
2822         for (i = 0, j = 2; i < 6 && pdev->resource[i].start; i++) {
2823                 struct resource *rp = &pdev->resource[i];
2824                 int io, breg = PCI_BASE_ADDRESS_0 + (i << 2);
2825                 unsigned long base;
2826                 u32 size, pbase;
2827
2828                 base = rp->start;
2829
2830                 io = (rp->flags & IORESOURCE_IO);
2831
2832                 size = rp->end - base + 1;
2833
2834                 pci_read_config_dword(pdev, breg, &pbase);
2835
2836                 if (io)
2837                         size &= ~1;
2838
2839                 /*
2840                  * Map the framebuffer a second time, this time without
2841                  * the braindead _PAGE_IE setting. This is used by the
2842                  * fixed Xserver, but we need to maintain the old mapping
2843                  * to stay compatible with older ones...
2844                  */
2845                 if (base == addr) {
2846                         par->mmap_map[j].voff = (pbase + 0x10000000) & PAGE_MASK;
2847                         par->mmap_map[j].poff = base & PAGE_MASK;
2848                         par->mmap_map[j].size = (size + ~PAGE_MASK) & PAGE_MASK;
2849                         par->mmap_map[j].prot_mask = _PAGE_CACHE;
2850                         par->mmap_map[j].prot_flag = _PAGE_E;
2851                         j++;
2852                 }
2853
2854                 /*
2855                  * Here comes the old framebuffer mapping with _PAGE_IE
2856                  * set for the big endian half of the framebuffer...
2857                  */
2858                 if (base == addr) {
2859                         par->mmap_map[j].voff = (pbase + 0x800000) & PAGE_MASK;
2860                         par->mmap_map[j].poff = (base + 0x800000) & PAGE_MASK;
2861                         par->mmap_map[j].size = 0x800000;
2862                         par->mmap_map[j].prot_mask = _PAGE_CACHE;
2863                         par->mmap_map[j].prot_flag = _PAGE_E | _PAGE_IE;
2864                         size -= 0x800000;
2865                         j++;
2866                 }
2867
2868                 par->mmap_map[j].voff = pbase & PAGE_MASK;
2869                 par->mmap_map[j].poff = base & PAGE_MASK;
2870                 par->mmap_map[j].size = (size + ~PAGE_MASK) & PAGE_MASK;
2871                 par->mmap_map[j].prot_mask = _PAGE_CACHE;
2872                 par->mmap_map[j].prot_flag = _PAGE_E;
2873                 j++;
2874         }
2875
2876         if((ret = correct_chipset(par)))
2877                 return ret;
2878
2879         if (IS_XL(pdev->device)) {
2880                 /*
2881                  * Fix PROMs idea of MEM_CNTL settings...
2882                  */
2883                 mem = aty_ld_le32(MEM_CNTL, par);
2884                 chip_id = aty_ld_le32(CONFIG_CHIP_ID, par);
2885                 if (((chip_id & CFG_CHIP_TYPE) == VT_CHIP_ID) && !((chip_id >> 24) & 1)) {
2886                         switch (mem & 0x0f) {
2887                         case 3:
2888                                 mem = (mem & ~(0x0f)) | 2;
2889                                 break;
2890                         case 7:
2891                                 mem = (mem & ~(0x0f)) | 3;
2892                                 break;
2893                         case 9:
2894                                 mem = (mem & ~(0x0f)) | 4;
2895                                 break;
2896                         case 11:
2897                                 mem = (mem & ~(0x0f)) | 5;
2898                                 break;
2899                         default:
2900                                 break;
2901                         }
2902                         if ((aty_ld_le32(CONFIG_STAT0, par) & 7) >= SDRAM)
2903                                 mem &= ~(0x00700000);
2904                 }
2905                 mem &= ~(0xcf80e000);   /* Turn off all undocumented bits. */
2906                 aty_st_le32(MEM_CNTL, mem, par);
2907         }
2908
2909         /*
2910          * If this is the console device, we will set default video
2911          * settings to what the PROM left us with.
2912          */
2913         node = prom_getchild(prom_root_node);
2914         node = prom_searchsiblings(node, "aliases");
2915         if (node) {
2916                 len = prom_getproperty(node, "screen", prop, sizeof(prop));
2917                 if (len > 0) {
2918                         prop[len] = '\0';
2919                         node = prom_finddevice(prop);
2920                 } else
2921                         node = 0;
2922         }
2923
2924         pcp = pdev->sysdata;
2925         if (node == pcp->prom_node) {
2926                 struct fb_var_screeninfo *var = &default_var;
2927                 unsigned int N, P, Q, M, T, R;
2928                 u32 v_total, h_total;
2929                 struct crtc crtc;
2930                 u8 pll_regs[16];
2931                 u8 clock_cntl;
2932
2933                 crtc.vxres = prom_getintdefault(node, "width", 1024);
2934                 crtc.vyres = prom_getintdefault(node, "height", 768);
2935                 var->bits_per_pixel = prom_getintdefault(node, "depth", 8);
2936                 var->xoffset = var->yoffset = 0;
2937                 crtc.h_tot_disp = aty_ld_le32(CRTC_H_TOTAL_DISP, par);
2938                 crtc.h_sync_strt_wid = aty_ld_le32(CRTC_H_SYNC_STRT_WID, par);
2939                 crtc.v_tot_disp = aty_ld_le32(CRTC_V_TOTAL_DISP, par);
2940                 crtc.v_sync_strt_wid = aty_ld_le32(CRTC_V_SYNC_STRT_WID, par);
2941                 crtc.gen_cntl = aty_ld_le32(CRTC_GEN_CNTL, par);
2942                 aty_crtc_to_var(&crtc, var);
2943
2944                 h_total = var->xres + var->right_margin + var->hsync_len + var->left_margin;
2945                 v_total = var->yres + var->lower_margin + var->vsync_len + var->upper_margin;
2946
2947                 /*
2948                  * Read the PLL to figure actual Refresh Rate.
2949                  */
2950                 clock_cntl = aty_ld_8(CLOCK_CNTL, par);
2951                 /* DPRINTK("CLOCK_CNTL %02x\n", clock_cntl); */
2952                 for (i = 0; i < 16; i++)
2953                         pll_regs[i] = aty_ld_pll_ct(i, par);
2954
2955                 /*
2956                  * PLL Reference Divider M:
2957                  */
2958                 M = pll_regs[2];
2959
2960                 /*
2961                  * PLL Feedback Divider N (Dependant on CLOCK_CNTL):
2962                  */
2963                 N = pll_regs[7 + (clock_cntl & 3)];
2964
2965                 /*
2966                  * PLL Post Divider P (Dependant on CLOCK_CNTL):
2967                  */
2968                 P = 1 << (pll_regs[6] >> ((clock_cntl & 3) << 1));
2969
2970                 /*
2971                  * PLL Divider Q:
2972                  */
2973                 Q = N / P;
2974
2975                 /*
2976                  * Target Frequency:
2977                  *
2978                  *      T * M
2979                  * Q = -------
2980                  *      2 * R
2981                  *
2982                  * where R is XTALIN (= 14318 or 29498 kHz).
2983                  */
2984                 if (IS_XL(pdev->device))
2985                         R = 29498;
2986                 else
2987                         R = 14318;
2988
2989                 T = 2 * Q * R / M;
2990
2991                 default_var.pixclock = 1000000000 / T;
2992         }
2993
2994         return 0;
2995 }
2996
2997 #else /* __sparc__ */
2998
2999 #ifdef __i386__
3000 #ifdef CONFIG_FB_ATY_GENERIC_LCD
3001 static void aty_init_lcd(struct atyfb_par *par, u32 bios_base)
3002 {
3003         u32 driv_inf_tab, sig;
3004         u16 lcd_ofs;
3005
3006         /* To support an LCD panel, we should know it's dimensions and
3007          *  it's desired pixel clock.
3008          * There are two ways to do it:
3009          *  - Check the startup video mode and calculate the panel
3010          *    size from it. This is unreliable.
3011          *  - Read it from the driver information table in the video BIOS.
3012         */
3013         /* Address of driver information table is at offset 0x78. */
3014         driv_inf_tab = bios_base + *((u16 *)(bios_base+0x78));
3015
3016         /* Check for the driver information table signature. */
3017         sig = (*(u32 *)driv_inf_tab);
3018         if ((sig == 0x54504c24) || /* Rage LT pro */
3019                 (sig == 0x544d5224) || /* Rage mobility */
3020                 (sig == 0x54435824) || /* Rage XC */
3021                 (sig == 0x544c5824)) { /* Rage XL */
3022                 PRINTKI("BIOS contains driver information table.\n");
3023                 lcd_ofs = (*(u16 *)(driv_inf_tab + 10));
3024                 par->lcd_table = 0;
3025                 if (lcd_ofs != 0) {
3026                         par->lcd_table = bios_base + lcd_ofs;
3027                 }
3028         }
3029
3030         if (par->lcd_table != 0) {
3031                 char model[24];
3032                 char strbuf[16];
3033                 char refresh_rates_buf[100];
3034                 int id, tech, f, i, m, default_refresh_rate;
3035                 char *txtcolour;
3036                 char *txtmonitor;
3037                 char *txtdual;
3038                 char *txtformat;
3039                 u16 width, height, panel_type, refresh_rates;
3040                 u16 *lcdmodeptr;
3041                 u32 format;
3042                 u8 lcd_refresh_rates[16] = {50,56,60,67,70,72,75,76,85,90,100,120,140,150,160,200};
3043                 /* The most important information is the panel size at
3044                  * offset 25 and 27, but there's some other nice information
3045                  * which we print to the screen.
3046                  */
3047                 id = *(u8 *)par->lcd_table;
3048                 strncpy(model,(char *)par->lcd_table+1,24);
3049                 model[23]=0;
3050
3051                 width = par->lcd_width = *(u16 *)(par->lcd_table+25);
3052                 height = par->lcd_height = *(u16 *)(par->lcd_table+27);
3053                 panel_type = *(u16 *)(par->lcd_table+29);
3054                 if (panel_type & 1)
3055                         txtcolour = "colour";
3056                 else
3057                         txtcolour = "monochrome";
3058                 if (panel_type & 2)
3059                         txtdual = "dual (split) ";
3060                 else
3061                         txtdual = "";
3062                 tech = (panel_type>>2) & 63;
3063                 switch (tech) {
3064                 case 0:
3065                         txtmonitor = "passive matrix";
3066                         break;
3067                 case 1:
3068                         txtmonitor = "active matrix";
3069                         break;
3070                 case 2:
3071                         txtmonitor = "active addressed STN";
3072                         break;
3073                 case 3:
3074                         txtmonitor = "EL";
3075                         break;
3076                 case 4:
3077                         txtmonitor = "plasma";
3078                         break;
3079                 default:
3080                         txtmonitor = "unknown";
3081                 }
3082                 format = *(u32 *)(par->lcd_table+57);
3083                 if (tech == 0 || tech == 2) {
3084                         switch (format & 7) {
3085                         case 0:
3086                                 txtformat = "12 bit interface";
3087                                 break;
3088                         case 1:
3089                                 txtformat = "16 bit interface";
3090                                 break;
3091                         case 2:
3092                                 txtformat = "24 bit interface";
3093                                 break;
3094                         default:
3095                                 txtformat = "unkown format";
3096                         }
3097                 } else {
3098                         switch (format & 7) {
3099                         case 0:
3100                                 txtformat = "8 colours";
3101                                 break;
3102                         case 1:
3103                                 txtformat = "512 colours";
3104                                 break;
3105                         case 2:
3106                                 txtformat = "4096 colours";
3107                                 break;
3108                         case 4:
3109                                 txtformat = "262144 colours (LT mode)";
3110                                 break;
3111                         case 5:
3112                                 txtformat = "16777216 colours";
3113                                 break;
3114                         case 6:
3115                                 txtformat = "262144 colours (FDPI-2 mode)";
3116                                 break;
3117                         default:
3118                                 txtformat = "unkown format";
3119                         }
3120                 }
3121                 PRINTKI("%s%s %s monitor detected: %s\n",
3122                         txtdual ,txtcolour, txtmonitor, model);
3123                 PRINTKI("       id=%d, %dx%d pixels, %s\n",
3124                         id, width, height, txtformat);
3125                 refresh_rates_buf[0] = 0;
3126                 refresh_rates = *(u16 *)(par->lcd_table+62);
3127                 m = 1;
3128                 f = 0;
3129                 for (i=0;i<16;i++) {
3130                         if (refresh_rates & m) {
3131                                 if (f == 0) {
3132                                         sprintf(strbuf, "%d", lcd_refresh_rates[i]);
3133                                         f++;
3134                                 } else {
3135                                         sprintf(strbuf, ",%d", lcd_refresh_rates[i]);
3136                                 }
3137                                 strcat(refresh_rates_buf,strbuf);
3138                         }
3139                         m = m << 1;
3140                 }
3141                 default_refresh_rate = (*(u8 *)(par->lcd_table+61) & 0xf0) >> 4;
3142                 PRINTKI("       supports refresh rates [%s], default %d Hz\n",
3143                         refresh_rates_buf, lcd_refresh_rates[default_refresh_rate]);
3144                 par->lcd_refreshrate = lcd_refresh_rates[default_refresh_rate];
3145                 /* We now need to determine the crtc parameters for the
3146                  * lcd monitor. This is tricky, because they are not stored
3147                  * individually in the BIOS. Instead, the BIOS contains a
3148                  * table of display modes that work for this monitor.
3149                  *
3150                  * The idea is that we search for a mode of the same dimensions
3151                  * as the dimensions of the lcd monitor. Say our lcd monitor
3152                  * is 800x600 pixels, we search for a 800x600 monitor.
3153                  * The CRTC parameters we find here are the ones that we need
3154                  * to use to simulate other resolutions on the lcd screen.
3155                  */
3156                 lcdmodeptr = (u16 *)(par->lcd_table + 64);
3157                 while (*lcdmodeptr != 0) {
3158                         u32 modeptr;
3159                         u16 mwidth, mheight, lcd_hsync_start, lcd_vsync_start;
3160                         modeptr = bios_base + *lcdmodeptr;
3161
3162                         mwidth = *((u16 *)(modeptr+0));
3163                         mheight = *((u16 *)(modeptr+2));
3164
3165                         if (mwidth == width && mheight == height) {
3166                                 par->lcd_pixclock = 100000000 / *((u16 *)(modeptr+9));
3167                                 par->lcd_htotal = *((u16 *)(modeptr+17)) & 511;
3168                                 par->lcd_hdisp = *((u16 *)(modeptr+19)) & 511;
3169                                 lcd_hsync_start = *((u16 *)(modeptr+21)) & 511;
3170                                 par->lcd_hsync_dly = (*((u16 *)(modeptr+21)) >> 9) & 7;
3171                                 par->lcd_hsync_len = *((u8 *)(modeptr+23)) & 63;
3172
3173                                 par->lcd_vtotal = *((u16 *)(modeptr+24)) & 2047;
3174                                 par->lcd_vdisp = *((u16 *)(modeptr+26)) & 2047;
3175                                 lcd_vsync_start = *((u16 *)(modeptr+28)) & 2047;
3176                                 par->lcd_vsync_len = (*((u16 *)(modeptr+28)) >> 11) & 31;
3177
3178                                 par->lcd_htotal = (par->lcd_htotal + 1) * 8;
3179                                 par->lcd_hdisp = (par->lcd_hdisp + 1) * 8;
3180                                 lcd_hsync_start = (lcd_hsync_start + 1) * 8;
3181                                 par->lcd_hsync_len = par->lcd_hsync_len * 8;
3182
3183                                 par->lcd_vtotal++;
3184                                 par->lcd_vdisp++;
3185                                 lcd_vsync_start++;
3186
3187                                 par->lcd_right_margin = lcd_hsync_start - par->lcd_hdisp;
3188                                 par->lcd_lower_margin = lcd_vsync_start - par->lcd_vdisp;
3189                                 par->lcd_hblank_len = par->lcd_htotal - par->lcd_hdisp;
3190                                 par->lcd_vblank_len = par->lcd_vtotal - par->lcd_vdisp;
3191                                 break;
3192                         }
3193
3194                         lcdmodeptr++;
3195                 }
3196                 if (*lcdmodeptr == 0) {
3197                         PRINTKE("LCD monitor CRTC parameters not found!!!\n");
3198                         /* To do: Switch to CRT if possible. */
3199                 } else {
3200                         PRINTKI("       LCD CRTC parameters: %d.%d  %d %d %d %d  %d %d %d %d\n",
3201                                 1000000 / par->lcd_pixclock, 1000000 % par->lcd_pixclock,
3202                                 par->lcd_hdisp,
3203                                 par->lcd_hdisp + par->lcd_right_margin,
3204                                 par->lcd_hdisp + par->lcd_right_margin
3205                                         + par->lcd_hsync_dly + par->lcd_hsync_len,
3206                                 par->lcd_htotal,
3207                                 par->lcd_vdisp,
3208                                 par->lcd_vdisp + par->lcd_lower_margin,
3209                                 par->lcd_vdisp + par->lcd_lower_margin + par->lcd_vsync_len,
3210                                 par->lcd_vtotal);
3211                         PRINTKI("                          : %d %d %d %d %d %d %d %d %d\n",
3212                                 par->lcd_pixclock,
3213                                 par->lcd_hblank_len - (par->lcd_right_margin +
3214                                         par->lcd_hsync_dly + par->lcd_hsync_len),
3215                                 par->lcd_hdisp,
3216                                 par->lcd_right_margin,
3217                                 par->lcd_hsync_len,
3218                                 par->lcd_vblank_len - (par->lcd_lower_margin + par->lcd_vsync_len),
3219                                 par->lcd_vdisp,
3220                                 par->lcd_lower_margin,
3221                                 par->lcd_vsync_len);
3222                 }
3223         }
3224 }
3225 #endif /* CONFIG_FB_ATY_GENERIC_LCD */
3226
3227 static int __devinit init_from_bios(struct atyfb_par *par)
3228 {
3229         u32 bios_base, rom_addr;
3230         int ret;
3231
3232         rom_addr = 0xc0000 + ((aty_ld_le32(SCRATCH_REG1, par) & 0x7f) << 11);
3233         bios_base = (unsigned long)ioremap(rom_addr, 0x10000);
3234
3235         /* The BIOS starts with 0xaa55. */
3236         if (*((u16 *)bios_base) == 0xaa55) {
3237
3238                 u8 *bios_ptr;
3239                 u16 rom_table_offset, freq_table_offset;
3240                 PLL_BLOCK_MACH64 pll_block;
3241
3242                 PRINTKI("Mach64 BIOS is located at %x, mapped at %x.\n", rom_addr, bios_base);
3243
3244                 /* check for frequncy table */
3245                 bios_ptr = (u8*)bios_base;
3246                 rom_table_offset = (u16)(bios_ptr[0x48] | (bios_ptr[0x49] << 8));
3247                 freq_table_offset = bios_ptr[rom_table_offset + 16] | (bios_ptr[rom_table_offset + 17] << 8);
3248                 memcpy(&pll_block, bios_ptr + freq_table_offset, sizeof(PLL_BLOCK_MACH64));
3249
3250                 PRINTKI("BIOS frequency table:\n");
3251                 PRINTKI("PCLK_min_freq %d, PCLK_max_freq %d, ref_freq %d, ref_divider %d\n",
3252                         pll_block.PCLK_min_freq, pll_block.PCLK_max_freq,
3253                         pll_block.ref_freq, pll_block.ref_divider);
3254                 PRINTKI("MCLK_pwd %d, MCLK_max_freq %d, XCLK_max_freq %d, SCLK_freq %d\n",
3255                         pll_block.MCLK_pwd, pll_block.MCLK_max_freq,
3256                         pll_block.XCLK_max_freq, pll_block.SCLK_freq);
3257
3258                 par->pll_limits.pll_min = pll_block.PCLK_min_freq/100;
3259                 par->pll_limits.pll_max = pll_block.PCLK_max_freq/100;
3260                 par->pll_limits.ref_clk = pll_block.ref_freq/100;
3261                 par->pll_limits.ref_div = pll_block.ref_divider;
3262                 par->pll_limits.sclk = pll_block.SCLK_freq/100;
3263                 par->pll_limits.mclk = pll_block.MCLK_max_freq/100;
3264                 par->pll_limits.mclk_pm = pll_block.MCLK_pwd/100;
3265                 par->pll_limits.xclk = pll_block.XCLK_max_freq/100;
3266 #ifdef CONFIG_FB_ATY_GENERIC_LCD
3267                 aty_init_lcd(par, bios_base);
3268 #endif
3269                 ret = 0;
3270         } else {
3271                 PRINTKE("no BIOS frequency table found, use parameters\n");
3272                 ret = -ENXIO;
3273         }
3274         iounmap((void* __iomem )bios_base);
3275
3276         return ret;
3277 }
3278 #endif /* __i386__ */
3279
3280 static int __devinit atyfb_setup_generic(struct pci_dev *pdev, struct fb_info *info, unsigned long addr)
3281 {
3282         struct atyfb_par *par = info->par;
3283         u16 tmp;
3284         unsigned long raddr;
3285         struct resource *rrp;
3286         int ret = 0;
3287
3288         raddr = addr + 0x7ff000UL;
3289         rrp = &pdev->resource[2];
3290         if ((rrp->flags & IORESOURCE_MEM) && request_mem_region(rrp->start, rrp->end - rrp->start + 1, "atyfb")) {
3291                 par->aux_start = rrp->start;
3292                 par->aux_size = rrp->end - rrp->start + 1;
3293                 raddr = rrp->start;
3294                 PRINTKI("using auxiliary register aperture\n");
3295         }
3296
3297         info->fix.mmio_start = raddr;
3298         par->ati_regbase = ioremap(info->fix.mmio_start, 0x1000);
3299         if (par->ati_regbase == 0)
3300                 return -ENOMEM;
3301
3302         info->fix.mmio_start += par->aux_start ? 0x400 : 0xc00;
3303         par->ati_regbase += par->aux_start ? 0x400 : 0xc00;
3304
3305         /*
3306          * Enable memory-space accesses using config-space
3307          * command register.
3308          */
3309         pci_read_config_word(pdev, PCI_COMMAND, &tmp);
3310         if (!(tmp & PCI_COMMAND_MEMORY)) {
3311                 tmp |= PCI_COMMAND_MEMORY;
3312                 pci_write_config_word(pdev, PCI_COMMAND, tmp);
3313         }
3314 #ifdef __BIG_ENDIAN
3315         /* Use the big-endian aperture */
3316         addr += 0x800000;
3317 #endif
3318
3319         /* Map in frame buffer */
3320         info->fix.smem_start = addr;
3321         info->screen_base = ioremap(addr, 0x800000);
3322         if (info->screen_base == NULL) {
3323                 ret = -ENOMEM;
3324                 goto atyfb_setup_generic_fail;
3325         }
3326
3327         if((ret = correct_chipset(par)))
3328                 goto atyfb_setup_generic_fail;
3329 #ifdef __i386__
3330         if((ret = init_from_bios(par)))
3331                 goto atyfb_setup_generic_fail;
3332 #endif
3333         if (!(aty_ld_le32(CRTC_GEN_CNTL, par) & CRTC_EXT_DISP_EN))
3334                 par->clk_wr_offset = (inb(R_GENMO) & 0x0CU) >> 2;
3335         else
3336                 par->clk_wr_offset = aty_ld_8(CLOCK_CNTL, par) & 0x03U;
3337
3338         /* according to ATI, we should use clock 3 for acelerated mode */
3339         par->clk_wr_offset = 3;
3340
3341         return 0;
3342
3343 atyfb_setup_generic_fail:
3344         iounmap(par->ati_regbase);
3345         par->ati_regbase = NULL;
3346         return ret;
3347 }
3348
3349 #endif /* !__sparc__ */
3350
3351 static int __devinit atyfb_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
3352 {
3353         unsigned long addr, res_start, res_size;
3354         struct fb_info *info;
3355         struct resource *rp;
3356         struct atyfb_par *par;
3357         int i, rc = -ENOMEM;
3358
3359         for (i = sizeof(aty_chips) / sizeof(*aty_chips) - 1; i >= 0; i--)
3360                 if (pdev->device == aty_chips[i].pci_id)
3361                         break;
3362
3363         if (i < 0)
3364                 return -ENODEV;
3365
3366         /* Enable device in PCI config */
3367         if (pci_enable_device(pdev)) {
3368                 PRINTKE("Cannot enable PCI device\n");
3369                 return -ENXIO;
3370         }
3371
3372         /* Find which resource to use */
3373         rp = &pdev->resource[0];
3374         if (rp->flags & IORESOURCE_IO)
3375                 rp = &pdev->resource[1];
3376         addr = rp->start;
3377         if (!addr)
3378                 return -ENXIO;
3379
3380         /* Reserve space */
3381         res_start = rp->start;
3382         res_size = rp->end - rp->start + 1;
3383         if (!request_mem_region (res_start, res_size, "atyfb"))
3384                 return -EBUSY;
3385
3386         /* Allocate framebuffer */
3387         info = framebuffer_alloc(sizeof(struct atyfb_par), &pdev->dev);
3388         if (!info) {
3389                 PRINTKE("atyfb_pci_probe() can't alloc fb_info\n");
3390                 return -ENOMEM;
3391         }
3392         par = info->par;
3393         info->fix = atyfb_fix;
3394         info->device = &pdev->dev;
3395         par->pci_id = aty_chips[i].pci_id;
3396         par->res_start = res_start;
3397         par->res_size = res_size;
3398         par->irq = pdev->irq;
3399
3400         /* Setup "info" structure */
3401 #ifdef __sparc__
3402         rc = atyfb_setup_sparc(pdev, info, addr);
3403 #else
3404         rc = atyfb_setup_generic(pdev, info, addr);
3405 #endif
3406         if (rc)
3407                 goto err_release_mem;
3408
3409         pci_set_drvdata(pdev, info);
3410
3411         /* Init chip & register framebuffer */
3412         if (aty_init(info, "PCI"))
3413                 goto err_release_io;
3414
3415 #ifdef __sparc__
3416         if (!prom_palette)
3417                 prom_palette = atyfb_palette;
3418
3419         /*
3420          * Add /dev/fb mmap values.
3421          */
3422         par->mmap_map[0].voff = 0x8000000000000000UL;
3423         par->mmap_map[0].poff = (unsigned long) info->screen_base & PAGE_MASK;
3424         par->mmap_map[0].size = info->fix.smem_len;
3425         par->mmap_map[0].prot_mask = _PAGE_CACHE;
3426         par->mmap_map[0].prot_flag = _PAGE_E;
3427         par->mmap_map[1].voff = par->mmap_map[0].voff + info->fix.smem_len;
3428         par->mmap_map[1].poff = (long)par->ati_regbase & PAGE_MASK;
3429         par->mmap_map[1].size = PAGE_SIZE;
3430         par->mmap_map[1].prot_mask = _PAGE_CACHE;
3431         par->mmap_map[1].prot_flag = _PAGE_E;
3432 #endif /* __sparc__ */
3433
3434         return 0;
3435
3436 err_release_io:
3437 #ifdef __sparc__
3438         kfree(par->mmap_map);
3439 #else
3440         if (par->ati_regbase)
3441                 iounmap(par->ati_regbase);
3442         if (info->screen_base)
3443                 iounmap(info->screen_base);
3444 #endif
3445 err_release_mem:
3446         if (par->aux_start)
3447                 release_mem_region(par->aux_start, par->aux_size);
3448
3449         release_mem_region(par->res_start, par->res_size);
3450         framebuffer_release(info);
3451
3452         return rc;
3453 }
3454
3455 #endif /* CONFIG_PCI */
3456
3457 #ifdef CONFIG_ATARI
3458
3459 static int __devinit atyfb_atari_probe(void)
3460 {
3461         struct aty_par *par;
3462         struct fb_info *info;
3463         int m64_num;
3464         u32 clock_r;
3465
3466         for (m64_num = 0; m64_num < mach64_count; m64_num++) {
3467                 if (!phys_vmembase[m64_num] || !phys_size[m64_num] ||
3468                     !phys_guiregbase[m64_num]) {
3469                     PRINTKI("phys_*[%d] parameters not set => returning early. \n", m64_num);
3470                         continue;
3471                 }
3472
3473                 info = framebuffer_alloc(sizeof(struct atyfb_par), NULL);
3474                 if (!info) {
3475                         PRINTKE("atyfb_atari_probe() can't alloc fb_info\n");
3476                         return -ENOMEM;
3477                 }
3478                 par = info->par;
3479
3480                 info->fix = atyfb_fix;
3481
3482                 par->irq = (unsigned int) -1; /* something invalid */
3483
3484                 /*
3485                  *  Map the video memory (physical address given) to somewhere in the
3486                  *  kernel address space.
3487                  */
3488                 info->screen_base = ioremap(phys_vmembase[m64_num], phys_size[m64_num]);
3489                 info->fix.smem_start = (unsigned long)info->screen_base; /* Fake! */
3490                 par->ati_regbase = ioremap(phys_guiregbase[m64_num], 0x10000) +
3491                                                 0xFC00ul;
3492                 info->fix.mmio_start = (unsigned long)par->ati_regbase; /* Fake! */
3493
3494                 aty_st_le32(CLOCK_CNTL, 0x12345678, par);
3495                 clock_r = aty_ld_le32(CLOCK_CNTL, par);
3496
3497                 switch (clock_r & 0x003F) {
3498                 case 0x12:
3499                         par->clk_wr_offset = 3; /*  */
3500                         break;
3501                 case 0x34:
3502                         par->clk_wr_offset = 2; /* Medusa ST-IO ISA Adapter etc. */
3503                         break;
3504                 case 0x16:
3505                         par->clk_wr_offset = 1; /*  */
3506                         break;
3507                 case 0x38:
3508                         par->clk_wr_offset = 0; /* Panther 1 ISA Adapter (Gerald) */
3509                         break;
3510                 }
3511
3512                 if (aty_init(info, "ISA bus")) {
3513                         framebuffer_release(info);
3514                         /* This is insufficient! kernel_map has added two large chunks!! */
3515                         return -ENXIO;
3516                 }
3517         }
3518 }
3519
3520 #endif /* CONFIG_ATARI */
3521
3522 static void __devexit atyfb_remove(struct fb_info *info)
3523 {
3524         struct atyfb_par *par = (struct atyfb_par *) info->par;
3525
3526         /* restore video mode */
3527         aty_set_crtc(par, &saved_crtc);
3528         par->pll_ops->set_pll(info, &saved_pll);
3529
3530         unregister_framebuffer(info);
3531
3532 #ifdef CONFIG_MTRR
3533         if (par->mtrr_reg >= 0) {
3534             mtrr_del(par->mtrr_reg, 0, 0);
3535             par->mtrr_reg = -1;
3536         }
3537         if (par->mtrr_aper >= 0) {
3538             mtrr_del(par->mtrr_aper, 0, 0);
3539             par->mtrr_aper = -1;
3540         }
3541 #endif
3542 #ifndef __sparc__
3543         if (par->ati_regbase)
3544                 iounmap(par->ati_regbase);
3545         if (info->screen_base)
3546                 iounmap(info->screen_base);
3547 #ifdef __BIG_ENDIAN
3548         if (info->sprite.addr)
3549                 iounmap(info->sprite.addr);
3550 #endif
3551 #endif
3552 #ifdef __sparc__
3553         kfree(par->mmap_map);
3554 #endif
3555         if (par->aux_start)
3556                 release_mem_region(par->aux_start, par->aux_size);
3557
3558         if (par->res_start)
3559                 release_mem_region(par->res_start, par->res_size);
3560
3561         framebuffer_release(info);
3562 }
3563
3564 #ifdef CONFIG_PCI
3565
3566 static void __devexit atyfb_pci_remove(struct pci_dev *pdev)
3567 {
3568         struct fb_info *info = pci_get_drvdata(pdev);
3569
3570         atyfb_remove(info);
3571 }
3572
3573 /*
3574  * This driver uses its own matching table. That will be more difficult
3575  * to fix, so for now, we just match against any ATI ID and let the
3576  * probe() function find out what's up. That also mean we don't have
3577  * a module ID table though.
3578  */
3579 static struct pci_device_id atyfb_pci_tbl[] = {
3580         { PCI_VENDOR_ID_ATI, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID,
3581           PCI_BASE_CLASS_DISPLAY << 16, 0xff0000, 0 },
3582         { 0, }
3583 };
3584
3585 static struct pci_driver atyfb_driver = {
3586         .name           = "atyfb",
3587         .id_table       = atyfb_pci_tbl,
3588         .probe          = atyfb_pci_probe,
3589         .remove         = __devexit_p(atyfb_pci_remove),
3590 #ifdef CONFIG_PM
3591         .suspend        = atyfb_pci_suspend,
3592         .resume         = atyfb_pci_resume,
3593 #endif /* CONFIG_PM */
3594 };
3595
3596 #endif /* CONFIG_PCI */
3597
3598 #ifndef MODULE
3599 static int __init atyfb_setup(char *options)
3600 {
3601         char *this_opt;
3602
3603         if (!options || !*options)
3604                 return 0;
3605
3606         while ((this_opt = strsep(&options, ",")) != NULL) {
3607                 if (!strncmp(this_opt, "noaccel", 7)) {
3608                         noaccel = 1;
3609 #ifdef CONFIG_MTRR
3610                 } else if (!strncmp(this_opt, "nomtrr", 6)) {
3611                         nomtrr = 1;
3612 #endif
3613                 } else if (!strncmp(this_opt, "vram:", 5))
3614                         vram = simple_strtoul(this_opt + 5, NULL, 0);
3615                 else if (!strncmp(this_opt, "pll:", 4))
3616                         pll = simple_strtoul(this_opt + 4, NULL, 0);
3617                 else if (!strncmp(this_opt, "mclk:", 5))
3618                         mclk = simple_strtoul(this_opt + 5, NULL, 0);
3619                 else if (!strncmp(this_opt, "xclk:", 5))
3620                         xclk = simple_strtoul(this_opt+5, NULL, 0);
3621                 else if (!strncmp(this_opt, "comp_sync:", 10))
3622                         comp_sync = simple_strtoul(this_opt+10, NULL, 0);
3623 #ifdef CONFIG_PPC
3624                 else if (!strncmp(this_opt, "vmode:", 6)) {
3625                         unsigned int vmode =
3626                             simple_strtoul(this_opt + 6, NULL, 0);
3627                         if (vmode > 0 && vmode <= VMODE_MAX)
3628                                 default_vmode = vmode;
3629                 } else if (!strncmp(this_opt, "cmode:", 6)) {
3630                         unsigned int cmode =
3631                             simple_strtoul(this_opt + 6, NULL, 0);
3632                         switch (cmode) {
3633                         case 0:
3634                         case 8:
3635                                 default_cmode = CMODE_8;
3636                                 break;
3637                         case 15:
3638                         case 16:
3639                                 default_cmode = CMODE_16;
3640                                 break;
3641                         case 24:
3642                         case 32:
3643                                 default_cmode = CMODE_32;
3644                                 break;
3645                         }
3646                 }
3647 #endif
3648 #ifdef CONFIG_ATARI
3649                 /*
3650                  * Why do we need this silly Mach64 argument?
3651                  * We are already here because of mach64= so its redundant.
3652                  */
3653                 else if (MACH_IS_ATARI
3654                          && (!strncmp(this_opt, "Mach64:", 7))) {
3655                         static unsigned char m64_num;
3656                         static char mach64_str[80];
3657                         strlcpy(mach64_str, this_opt + 7, sizeof(mach64_str));
3658                         if (!store_video_par(mach64_str, m64_num)) {
3659                                 m64_num++;
3660                                 mach64_count = m64_num;
3661                         }
3662                 }
3663 #endif
3664                 else
3665                         mode = this_opt;
3666         }
3667         return 0;
3668 }
3669 #endif  /*  MODULE  */
3670
3671 static int __init atyfb_init(void)
3672 {
3673 #ifndef MODULE
3674     char *option = NULL;
3675
3676     if (fb_get_options("atyfb", &option))
3677         return -ENODEV;
3678     atyfb_setup(option);
3679 #endif
3680
3681 #ifdef CONFIG_PCI
3682     pci_register_driver(&atyfb_driver);
3683 #endif
3684 #ifdef CONFIG_ATARI
3685     atyfb_atari_probe();
3686 #endif
3687     return 0;
3688 }
3689
3690 static void __exit atyfb_exit(void)
3691 {
3692 #ifdef CONFIG_PCI
3693         pci_unregister_driver(&atyfb_driver);
3694 #endif
3695 }
3696
3697 module_init(atyfb_init);
3698 module_exit(atyfb_exit);
3699
3700 MODULE_DESCRIPTION("FBDev driver for ATI Mach64 cards");
3701 MODULE_LICENSE("GPL");
3702 module_param(noaccel, bool, 0);
3703 MODULE_PARM_DESC(noaccel, "bool: disable acceleration");
3704 module_param(vram, int, 0);
3705 MODULE_PARM_DESC(vram, "int: override size of video ram");
3706 module_param(pll, int, 0);
3707 MODULE_PARM_DESC(pll, "int: override video clock");
3708 module_param(mclk, int, 0);
3709 MODULE_PARM_DESC(mclk, "int: override memory clock");
3710 module_param(xclk, int, 0);
3711 MODULE_PARM_DESC(xclk, "int: override accelerated engine clock");
3712 module_param(comp_sync, int, 0);
3713 MODULE_PARM_DESC(comp_sync,
3714                  "Set composite sync signal to low (0) or high (1)");
3715 module_param(mode, charp, 0);
3716 MODULE_PARM_DESC(mode, "Specify resolution as \"<xres>x<yres>[-<bpp>][@<refresh>]\" ");
3717 #ifdef CONFIG_MTRR
3718 module_param(nomtrr, bool, 0);
3719 MODULE_PARM_DESC(nomtrr, "bool: disable use of MTRR registers");
3720 #endif