xref: /openbmc/linux/drivers/video/fbdev/cirrusfb.c (revision 37002bc6)
1 /*
2  * drivers/video/cirrusfb.c - driver for Cirrus Logic chipsets
3  *
4  * Copyright 1999-2001 Jeff Garzik <jgarzik@pobox.com>
5  *
6  * Contributors (thanks, all!)
7  *
8  *	David Eger:
9  *	Overhaul for Linux 2.6
10  *
11  *      Jeff Rugen:
12  *      Major contributions;  Motorola PowerStack (PPC and PCI) support,
13  *      GD54xx, 1280x1024 mode support, change MCLK based on VCLK.
14  *
15  *	Geert Uytterhoeven:
16  *	Excellent code review.
17  *
18  *	Lars Hecking:
19  *	Amiga updates and testing.
20  *
21  * Original cirrusfb author:  Frank Neumann
22  *
23  * Based on retz3fb.c and cirrusfb.c:
24  *      Copyright (C) 1997 Jes Sorensen
25  *      Copyright (C) 1996 Frank Neumann
26  *
27  ***************************************************************
28  *
29  * Format this code with GNU indent '-kr -i8 -pcs' options.
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
33  * for more details.
34  *
35  */
36 
37 #include <linux/aperture.h>
38 #include <linux/module.h>
39 #include <linux/kernel.h>
40 #include <linux/errno.h>
41 #include <linux/string.h>
42 #include <linux/mm.h>
43 #include <linux/delay.h>
44 #include <linux/fb.h>
45 #include <linux/init.h>
46 
47 #ifdef CONFIG_ZORRO
48 #include <linux/zorro.h>
49 #endif
50 #ifdef CONFIG_PCI
51 #include <linux/pci.h>
52 #endif
53 #ifdef CONFIG_AMIGA
54 #include <asm/amigahw.h>
55 #endif
56 
57 #include <video/vga.h>
58 #include <video/cirrus.h>
59 
60 /*****************************************************************
61  *
62  * debugging and utility macros
63  *
64  */
65 
66 /* disable runtime assertions? */
67 /* #define CIRRUSFB_NDEBUG */
68 
69 /* debugging assertions */
70 #ifndef CIRRUSFB_NDEBUG
71 #define assert(expr) \
72 	if (!(expr)) { \
73 		printk("Assertion failed! %s,%s,%s,line=%d\n", \
74 		#expr, __FILE__, __func__, __LINE__); \
75 	}
76 #else
77 #define assert(expr)
78 #endif
79 
80 #define MB_ (1024 * 1024)
81 
82 /*****************************************************************
83  *
84  * chipset information
85  *
86  */
87 
88 /* board types */
89 enum cirrus_board {
90 	BT_NONE = 0,
91 	BT_SD64,	/* GD5434 */
92 	BT_PICCOLO,	/* GD5426 */
93 	BT_PICASSO,	/* GD5426 or GD5428 */
94 	BT_SPECTRUM,	/* GD5426 or GD5428 */
95 	BT_PICASSO4,	/* GD5446 */
96 	BT_ALPINE,	/* GD543x/4x */
97 	BT_GD5480,
98 	BT_LAGUNA,	/* GD5462/64 */
99 	BT_LAGUNAB,	/* GD5465 */
100 };
101 
102 /*
103  * per-board-type information, used for enumerating and abstracting
104  * chip-specific information
105  * NOTE: MUST be in the same order as enum cirrus_board in order to
106  * use direct indexing on this array
107  * NOTE: '__initdata' cannot be used as some of this info
108  * is required at runtime.  Maybe separate into an init-only and
109  * a run-time table?
110  */
111 static const struct cirrusfb_board_info_rec {
112 	char *name;		/* ASCII name of chipset */
113 	long maxclock[5];		/* maximum video clock */
114 	/* for  1/4bpp, 8bpp 15/16bpp, 24bpp, 32bpp - numbers from xorg code */
115 	bool init_sr07 : 1; /* init SR07 during init_vgachip() */
116 	bool init_sr1f : 1; /* write SR1F during init_vgachip() */
117 	/* construct bit 19 of screen start address */
118 	bool scrn_start_bit19 : 1;
119 
120 	/* initial SR07 value, then for each mode */
121 	unsigned char sr07;
122 	unsigned char sr07_1bpp;
123 	unsigned char sr07_1bpp_mux;
124 	unsigned char sr07_8bpp;
125 	unsigned char sr07_8bpp_mux;
126 
127 	unsigned char sr1f;	/* SR1F VGA initial register value */
128 } cirrusfb_board_info[] = {
129 	[BT_SD64] = {
130 		.name			= "CL SD64",
131 		.maxclock		= {
132 			/* guess */
133 			/* the SD64/P4 have a higher max. videoclock */
134 			135100, 135100, 85500, 85500, 0
135 		},
136 		.init_sr07		= true,
137 		.init_sr1f		= true,
138 		.scrn_start_bit19	= true,
139 		.sr07			= 0xF0,
140 		.sr07_1bpp		= 0xF0,
141 		.sr07_1bpp_mux		= 0xF6,
142 		.sr07_8bpp		= 0xF1,
143 		.sr07_8bpp_mux		= 0xF7,
144 		.sr1f			= 0x1E
145 	},
146 	[BT_PICCOLO] = {
147 		.name			= "CL Piccolo",
148 		.maxclock		= {
149 			/* guess */
150 			90000, 90000, 90000, 90000, 90000
151 		},
152 		.init_sr07		= true,
153 		.init_sr1f		= true,
154 		.scrn_start_bit19	= false,
155 		.sr07			= 0x80,
156 		.sr07_1bpp		= 0x80,
157 		.sr07_8bpp		= 0x81,
158 		.sr1f			= 0x22
159 	},
160 	[BT_PICASSO] = {
161 		.name			= "CL Picasso",
162 		.maxclock		= {
163 			/* guess */
164 			90000, 90000, 90000, 90000, 90000
165 		},
166 		.init_sr07		= true,
167 		.init_sr1f		= true,
168 		.scrn_start_bit19	= false,
169 		.sr07			= 0x20,
170 		.sr07_1bpp		= 0x20,
171 		.sr07_8bpp		= 0x21,
172 		.sr1f			= 0x22
173 	},
174 	[BT_SPECTRUM] = {
175 		.name			= "CL Spectrum",
176 		.maxclock		= {
177 			/* guess */
178 			90000, 90000, 90000, 90000, 90000
179 		},
180 		.init_sr07		= true,
181 		.init_sr1f		= true,
182 		.scrn_start_bit19	= false,
183 		.sr07			= 0x80,
184 		.sr07_1bpp		= 0x80,
185 		.sr07_8bpp		= 0x81,
186 		.sr1f			= 0x22
187 	},
188 	[BT_PICASSO4] = {
189 		.name			= "CL Picasso4",
190 		.maxclock		= {
191 			135100, 135100, 85500, 85500, 0
192 		},
193 		.init_sr07		= true,
194 		.init_sr1f		= false,
195 		.scrn_start_bit19	= true,
196 		.sr07			= 0xA0,
197 		.sr07_1bpp		= 0xA0,
198 		.sr07_1bpp_mux		= 0xA6,
199 		.sr07_8bpp		= 0xA1,
200 		.sr07_8bpp_mux		= 0xA7,
201 		.sr1f			= 0
202 	},
203 	[BT_ALPINE] = {
204 		.name			= "CL Alpine",
205 		.maxclock		= {
206 			/* for the GD5430.  GD5446 can do more... */
207 			85500, 85500, 50000, 28500, 0
208 		},
209 		.init_sr07		= true,
210 		.init_sr1f		= true,
211 		.scrn_start_bit19	= true,
212 		.sr07			= 0xA0,
213 		.sr07_1bpp		= 0xA0,
214 		.sr07_1bpp_mux		= 0xA6,
215 		.sr07_8bpp		= 0xA1,
216 		.sr07_8bpp_mux		= 0xA7,
217 		.sr1f			= 0x1C
218 	},
219 	[BT_GD5480] = {
220 		.name			= "CL GD5480",
221 		.maxclock		= {
222 			135100, 200000, 200000, 135100, 135100
223 		},
224 		.init_sr07		= true,
225 		.init_sr1f		= true,
226 		.scrn_start_bit19	= true,
227 		.sr07			= 0x10,
228 		.sr07_1bpp		= 0x11,
229 		.sr07_8bpp		= 0x11,
230 		.sr1f			= 0x1C
231 	},
232 	[BT_LAGUNA] = {
233 		.name			= "CL Laguna",
234 		.maxclock		= {
235 			/* taken from X11 code */
236 			170000, 170000, 170000, 170000, 135100,
237 		},
238 		.init_sr07		= false,
239 		.init_sr1f		= false,
240 		.scrn_start_bit19	= true,
241 	},
242 	[BT_LAGUNAB] = {
243 		.name			= "CL Laguna AGP",
244 		.maxclock		= {
245 			/* taken from X11 code */
246 			170000, 250000, 170000, 170000, 135100,
247 		},
248 		.init_sr07		= false,
249 		.init_sr1f		= false,
250 		.scrn_start_bit19	= true,
251 	}
252 };
253 
254 #ifdef CONFIG_PCI
255 #define CHIP(id, btype) \
256 	{ PCI_VENDOR_ID_CIRRUS, id, PCI_ANY_ID, PCI_ANY_ID, 0, 0, (btype) }
257 
258 static struct pci_device_id cirrusfb_pci_table[] = {
259 	CHIP(PCI_DEVICE_ID_CIRRUS_5436, BT_ALPINE),
260 	CHIP(PCI_DEVICE_ID_CIRRUS_5434_8, BT_SD64),
261 	CHIP(PCI_DEVICE_ID_CIRRUS_5434_4, BT_SD64),
262 	CHIP(PCI_DEVICE_ID_CIRRUS_5430, BT_ALPINE), /* GD-5440 is same id */
263 	CHIP(PCI_DEVICE_ID_CIRRUS_7543, BT_ALPINE),
264 	CHIP(PCI_DEVICE_ID_CIRRUS_7548, BT_ALPINE),
265 	CHIP(PCI_DEVICE_ID_CIRRUS_5480, BT_GD5480), /* MacPicasso likely */
266 	CHIP(PCI_DEVICE_ID_CIRRUS_5446, BT_PICASSO4), /* Picasso 4 is 5446 */
267 	CHIP(PCI_DEVICE_ID_CIRRUS_5462, BT_LAGUNA), /* CL Laguna */
268 	CHIP(PCI_DEVICE_ID_CIRRUS_5464, BT_LAGUNA), /* CL Laguna 3D */
269 	CHIP(PCI_DEVICE_ID_CIRRUS_5465, BT_LAGUNAB), /* CL Laguna 3DA*/
270 	{ 0, }
271 };
272 MODULE_DEVICE_TABLE(pci, cirrusfb_pci_table);
273 #undef CHIP
274 #endif /* CONFIG_PCI */
275 
276 #ifdef CONFIG_ZORRO
277 struct zorrocl {
278 	enum cirrus_board type;	/* Board type */
279 	u32 regoffset;		/* Offset of registers in first Zorro device */
280 	u32 ramsize;		/* Size of video RAM in first Zorro device */
281 				/* If zero, use autoprobe on RAM device */
282 	u32 ramoffset;		/* Offset of video RAM in first Zorro device */
283 	zorro_id ramid;		/* Zorro ID of RAM device */
284 	zorro_id ramid2;	/* Zorro ID of optional second RAM device */
285 };
286 
287 static const struct zorrocl zcl_sd64 = {
288 	.type		= BT_SD64,
289 	.ramid		= ZORRO_PROD_HELFRICH_SD64_RAM,
290 };
291 
292 static const struct zorrocl zcl_piccolo = {
293 	.type		= BT_PICCOLO,
294 	.ramid		= ZORRO_PROD_HELFRICH_PICCOLO_RAM,
295 };
296 
297 static const struct zorrocl zcl_picasso = {
298 	.type		= BT_PICASSO,
299 	.ramid		= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_II_II_PLUS_RAM,
300 };
301 
302 static const struct zorrocl zcl_spectrum = {
303 	.type		= BT_SPECTRUM,
304 	.ramid		= ZORRO_PROD_GVP_EGS_28_24_SPECTRUM_RAM,
305 };
306 
307 static const struct zorrocl zcl_picasso4_z3 = {
308 	.type		= BT_PICASSO4,
309 	.regoffset	= 0x00600000,
310 	.ramsize	= 4 * MB_,
311 	.ramoffset	= 0x01000000,	/* 0x02000000 for 64 MiB boards */
312 };
313 
314 static const struct zorrocl zcl_picasso4_z2 = {
315 	.type		= BT_PICASSO4,
316 	.regoffset	= 0x10000,
317 	.ramid		= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_IV_Z2_RAM1,
318 	.ramid2		= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_IV_Z2_RAM2,
319 };
320 
321 
322 static const struct zorro_device_id cirrusfb_zorro_table[] = {
323 	{
324 		.id		= ZORRO_PROD_HELFRICH_SD64_REG,
325 		.driver_data	= (unsigned long)&zcl_sd64,
326 	}, {
327 		.id		= ZORRO_PROD_HELFRICH_PICCOLO_REG,
328 		.driver_data	= (unsigned long)&zcl_piccolo,
329 	}, {
330 		.id	= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_II_II_PLUS_REG,
331 		.driver_data	= (unsigned long)&zcl_picasso,
332 	}, {
333 		.id		= ZORRO_PROD_GVP_EGS_28_24_SPECTRUM_REG,
334 		.driver_data	= (unsigned long)&zcl_spectrum,
335 	}, {
336 		.id		= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_IV_Z3,
337 		.driver_data	= (unsigned long)&zcl_picasso4_z3,
338 	}, {
339 		.id		= ZORRO_PROD_VILLAGE_TRONIC_PICASSO_IV_Z2_REG,
340 		.driver_data	= (unsigned long)&zcl_picasso4_z2,
341 	},
342 	{ 0 }
343 };
344 MODULE_DEVICE_TABLE(zorro, cirrusfb_zorro_table);
345 #endif /* CONFIG_ZORRO */
346 
347 #ifdef CIRRUSFB_DEBUG
348 enum cirrusfb_dbg_reg_class {
349 	CRT,
350 	SEQ
351 };
352 #endif		/* CIRRUSFB_DEBUG */
353 
354 /* info about board */
355 struct cirrusfb_info {
356 	u8 __iomem *regbase;
357 	u8 __iomem *laguna_mmio;
358 	enum cirrus_board btype;
359 	unsigned char SFR;	/* Shadow of special function register */
360 
361 	int multiplexing;
362 	int doubleVCLK;
363 	int blank_mode;
364 	u32 pseudo_palette[16];
365 
366 	void (*unmap)(struct fb_info *info);
367 };
368 
369 static bool noaccel;
370 static char *mode_option = "640x480@60";
371 
372 /****************************************************************************/
373 /**** BEGIN PROTOTYPES ******************************************************/
374 
375 /*--- Interface used by the world ------------------------------------------*/
376 static int cirrusfb_pan_display(struct fb_var_screeninfo *var,
377 				struct fb_info *info);
378 
379 /*--- Internal routines ----------------------------------------------------*/
380 static void init_vgachip(struct fb_info *info);
381 static void switch_monitor(struct cirrusfb_info *cinfo, int on);
382 static void WGen(const struct cirrusfb_info *cinfo,
383 		 int regnum, unsigned char val);
384 static unsigned char RGen(const struct cirrusfb_info *cinfo, int regnum);
385 static void AttrOn(const struct cirrusfb_info *cinfo);
386 static void WHDR(const struct cirrusfb_info *cinfo, unsigned char val);
387 static void WSFR(struct cirrusfb_info *cinfo, unsigned char val);
388 static void WSFR2(struct cirrusfb_info *cinfo, unsigned char val);
389 static void WClut(struct cirrusfb_info *cinfo, unsigned char regnum,
390 		  unsigned char red, unsigned char green, unsigned char blue);
391 #if 0
392 static void RClut(struct cirrusfb_info *cinfo, unsigned char regnum,
393 		  unsigned char *red, unsigned char *green,
394 		  unsigned char *blue);
395 #endif
396 static void cirrusfb_WaitBLT(u8 __iomem *regbase);
397 static void cirrusfb_BitBLT(u8 __iomem *regbase, int bits_per_pixel,
398 			    u_short curx, u_short cury,
399 			    u_short destx, u_short desty,
400 			    u_short width, u_short height,
401 			    u_short line_length);
402 static void cirrusfb_RectFill(u8 __iomem *regbase, int bits_per_pixel,
403 			      u_short x, u_short y,
404 			      u_short width, u_short height,
405 			      u32 fg_color, u32 bg_color,
406 			      u_short line_length, u_char blitmode);
407 
408 static void bestclock(long freq, int *nom, int *den, int *div);
409 
410 #ifdef CIRRUSFB_DEBUG
411 static void cirrusfb_dbg_reg_dump(struct fb_info *info, caddr_t regbase);
412 static void cirrusfb_dbg_print_regs(struct fb_info *info,
413 				    caddr_t regbase,
414 				    enum cirrusfb_dbg_reg_class reg_class, ...);
415 #endif /* CIRRUSFB_DEBUG */
416 
417 /*** END   PROTOTYPES ********************************************************/
418 /*****************************************************************************/
419 /*** BEGIN Interface Used by the World ***************************************/
420 
421 static inline int is_laguna(const struct cirrusfb_info *cinfo)
422 {
423 	return cinfo->btype == BT_LAGUNA || cinfo->btype == BT_LAGUNAB;
424 }
425 
426 static int opencount;
427 
428 /*--- Open /dev/fbx ---------------------------------------------------------*/
429 static int cirrusfb_open(struct fb_info *info, int user)
430 {
431 	if (opencount++ == 0)
432 		switch_monitor(info->par, 1);
433 	return 0;
434 }
435 
436 /*--- Close /dev/fbx --------------------------------------------------------*/
437 static int cirrusfb_release(struct fb_info *info, int user)
438 {
439 	if (--opencount == 0)
440 		switch_monitor(info->par, 0);
441 	return 0;
442 }
443 
444 /**** END   Interface used by the World *************************************/
445 /****************************************************************************/
446 /**** BEGIN Hardware specific Routines **************************************/
447 
448 /* Check if the MCLK is not a better clock source */
449 static int cirrusfb_check_mclk(struct fb_info *info, long freq)
450 {
451 	struct cirrusfb_info *cinfo = info->par;
452 	long mclk = vga_rseq(cinfo->regbase, CL_SEQR1F) & 0x3f;
453 
454 	/* Read MCLK value */
455 	mclk = (14318 * mclk) >> 3;
456 	dev_dbg(info->device, "Read MCLK of %ld kHz\n", mclk);
457 
458 	/* Determine if we should use MCLK instead of VCLK, and if so, what we
459 	 * should divide it by to get VCLK
460 	 */
461 
462 	if (abs(freq - mclk) < 250) {
463 		dev_dbg(info->device, "Using VCLK = MCLK\n");
464 		return 1;
465 	} else if (abs(freq - (mclk / 2)) < 250) {
466 		dev_dbg(info->device, "Using VCLK = MCLK/2\n");
467 		return 2;
468 	}
469 
470 	return 0;
471 }
472 
473 static int cirrusfb_check_pixclock(struct fb_var_screeninfo *var,
474 				   struct fb_info *info)
475 {
476 	long freq;
477 	long maxclock;
478 	struct cirrusfb_info *cinfo = info->par;
479 	unsigned maxclockidx = var->bits_per_pixel >> 3;
480 
481 	/* convert from ps to kHz */
482 	freq = PICOS2KHZ(var->pixclock ? : 1);
483 
484 	maxclock = cirrusfb_board_info[cinfo->btype].maxclock[maxclockidx];
485 	cinfo->multiplexing = 0;
486 
487 	/* If the frequency is greater than we can support, we might be able
488 	 * to use multiplexing for the video mode */
489 	if (freq > maxclock) {
490 		var->pixclock = KHZ2PICOS(maxclock);
491 
492 		while ((freq = PICOS2KHZ(var->pixclock)) > maxclock)
493 			var->pixclock++;
494 	}
495 	dev_dbg(info->device, "desired pixclock: %ld kHz\n", freq);
496 
497 	/*
498 	 * Additional constraint: 8bpp uses DAC clock doubling to allow maximum
499 	 * pixel clock
500 	 */
501 	if (var->bits_per_pixel == 8) {
502 		switch (cinfo->btype) {
503 		case BT_ALPINE:
504 		case BT_SD64:
505 		case BT_PICASSO4:
506 			if (freq > 85500)
507 				cinfo->multiplexing = 1;
508 			break;
509 		case BT_GD5480:
510 			if (freq > 135100)
511 				cinfo->multiplexing = 1;
512 			break;
513 
514 		default:
515 			break;
516 		}
517 	}
518 
519 	/* If we have a 1MB 5434, we need to put ourselves in a mode where
520 	 * the VCLK is double the pixel clock. */
521 	cinfo->doubleVCLK = 0;
522 	if (cinfo->btype == BT_SD64 && info->fix.smem_len <= MB_ &&
523 	    var->bits_per_pixel == 16) {
524 		cinfo->doubleVCLK = 1;
525 	}
526 
527 	return 0;
528 }
529 
530 static int cirrusfb_check_var(struct fb_var_screeninfo *var,
531 			      struct fb_info *info)
532 {
533 	int yres;
534 	/* memory size in pixels */
535 	unsigned int pixels;
536 	struct cirrusfb_info *cinfo = info->par;
537 
538 	switch (var->bits_per_pixel) {
539 	case 1:
540 		var->red.offset = 0;
541 		var->red.length = 1;
542 		var->green = var->red;
543 		var->blue = var->red;
544 		break;
545 
546 	case 8:
547 		var->red.offset = 0;
548 		var->red.length = 8;
549 		var->green = var->red;
550 		var->blue = var->red;
551 		break;
552 
553 	case 16:
554 		var->red.offset = 11;
555 		var->green.offset = 5;
556 		var->blue.offset = 0;
557 		var->red.length = 5;
558 		var->green.length = 6;
559 		var->blue.length = 5;
560 		break;
561 
562 	case 24:
563 		var->red.offset = 16;
564 		var->green.offset = 8;
565 		var->blue.offset = 0;
566 		var->red.length = 8;
567 		var->green.length = 8;
568 		var->blue.length = 8;
569 		break;
570 
571 	default:
572 		dev_dbg(info->device,
573 			"Unsupported bpp size: %d\n", var->bits_per_pixel);
574 		return -EINVAL;
575 	}
576 
577 	pixels = info->screen_size * 8 / var->bits_per_pixel;
578 	if (var->xres_virtual < var->xres)
579 		var->xres_virtual = var->xres;
580 	/* use highest possible virtual resolution */
581 	if (var->yres_virtual == -1) {
582 		var->yres_virtual = pixels / var->xres_virtual;
583 
584 		dev_info(info->device,
585 			 "virtual resolution set to maximum of %dx%d\n",
586 			 var->xres_virtual, var->yres_virtual);
587 	}
588 	if (var->yres_virtual < var->yres)
589 		var->yres_virtual = var->yres;
590 
591 	if (var->xres_virtual * var->yres_virtual > pixels) {
592 		dev_err(info->device, "mode %dx%dx%d rejected... "
593 		      "virtual resolution too high to fit into video memory!\n",
594 			var->xres_virtual, var->yres_virtual,
595 			var->bits_per_pixel);
596 		return -EINVAL;
597 	}
598 
599 	/* truncate xoffset and yoffset to maximum if too high */
600 	if (var->xoffset > var->xres_virtual - var->xres)
601 		var->xoffset = var->xres_virtual - var->xres - 1;
602 	if (var->yoffset > var->yres_virtual - var->yres)
603 		var->yoffset = var->yres_virtual - var->yres - 1;
604 
605 	var->red.msb_right =
606 	    var->green.msb_right =
607 	    var->blue.msb_right =
608 	    var->transp.offset =
609 	    var->transp.length =
610 	    var->transp.msb_right = 0;
611 
612 	yres = var->yres;
613 	if (var->vmode & FB_VMODE_DOUBLE)
614 		yres *= 2;
615 	else if (var->vmode & FB_VMODE_INTERLACED)
616 		yres = (yres + 1) / 2;
617 
618 	if (yres >= 1280) {
619 		dev_err(info->device, "ERROR: VerticalTotal >= 1280; "
620 			"special treatment required! (TODO)\n");
621 		return -EINVAL;
622 	}
623 
624 	if (cirrusfb_check_pixclock(var, info))
625 		return -EINVAL;
626 
627 	if (!is_laguna(cinfo))
628 		var->accel_flags = FB_ACCELF_TEXT;
629 
630 	return 0;
631 }
632 
633 static void cirrusfb_set_mclk_as_source(const struct fb_info *info, int div)
634 {
635 	struct cirrusfb_info *cinfo = info->par;
636 	unsigned char old1f, old1e;
637 
638 	assert(cinfo != NULL);
639 	old1f = vga_rseq(cinfo->regbase, CL_SEQR1F) & ~0x40;
640 
641 	if (div) {
642 		dev_dbg(info->device, "Set %s as pixclock source.\n",
643 			(div == 2) ? "MCLK/2" : "MCLK");
644 		old1f |= 0x40;
645 		old1e = vga_rseq(cinfo->regbase, CL_SEQR1E) & ~0x1;
646 		if (div == 2)
647 			old1e |= 1;
648 
649 		vga_wseq(cinfo->regbase, CL_SEQR1E, old1e);
650 	}
651 	vga_wseq(cinfo->regbase, CL_SEQR1F, old1f);
652 }
653 
654 /*************************************************************************
655 	cirrusfb_set_par_foo()
656 
657 	actually writes the values for a new video mode into the hardware,
658 **************************************************************************/
659 static int cirrusfb_set_par_foo(struct fb_info *info)
660 {
661 	struct cirrusfb_info *cinfo = info->par;
662 	struct fb_var_screeninfo *var = &info->var;
663 	u8 __iomem *regbase = cinfo->regbase;
664 	unsigned char tmp;
665 	int pitch;
666 	const struct cirrusfb_board_info_rec *bi;
667 	int hdispend, hsyncstart, hsyncend, htotal;
668 	int yres, vdispend, vsyncstart, vsyncend, vtotal;
669 	long freq;
670 	int nom, den, div;
671 	unsigned int control = 0, format = 0, threshold = 0;
672 
673 	dev_dbg(info->device, "Requested mode: %dx%dx%d\n",
674 	       var->xres, var->yres, var->bits_per_pixel);
675 
676 	switch (var->bits_per_pixel) {
677 	case 1:
678 		info->fix.line_length = var->xres_virtual / 8;
679 		info->fix.visual = FB_VISUAL_MONO10;
680 		break;
681 
682 	case 8:
683 		info->fix.line_length = var->xres_virtual;
684 		info->fix.visual = FB_VISUAL_PSEUDOCOLOR;
685 		break;
686 
687 	case 16:
688 	case 24:
689 		info->fix.line_length = var->xres_virtual *
690 					var->bits_per_pixel >> 3;
691 		info->fix.visual = FB_VISUAL_TRUECOLOR;
692 		break;
693 	}
694 	info->fix.type = FB_TYPE_PACKED_PIXELS;
695 
696 	init_vgachip(info);
697 
698 	bi = &cirrusfb_board_info[cinfo->btype];
699 
700 	hsyncstart = var->xres + var->right_margin;
701 	hsyncend = hsyncstart + var->hsync_len;
702 	htotal = (hsyncend + var->left_margin) / 8;
703 	hdispend = var->xres / 8;
704 	hsyncstart = hsyncstart / 8;
705 	hsyncend = hsyncend / 8;
706 
707 	vdispend = var->yres;
708 	vsyncstart = vdispend + var->lower_margin;
709 	vsyncend = vsyncstart + var->vsync_len;
710 	vtotal = vsyncend + var->upper_margin;
711 
712 	if (var->vmode & FB_VMODE_DOUBLE) {
713 		vdispend *= 2;
714 		vsyncstart *= 2;
715 		vsyncend *= 2;
716 		vtotal *= 2;
717 	} else if (var->vmode & FB_VMODE_INTERLACED) {
718 		vdispend = (vdispend + 1) / 2;
719 		vsyncstart = (vsyncstart + 1) / 2;
720 		vsyncend = (vsyncend + 1) / 2;
721 		vtotal = (vtotal + 1) / 2;
722 	}
723 	yres = vdispend;
724 	if (yres >= 1024) {
725 		vtotal /= 2;
726 		vsyncstart /= 2;
727 		vsyncend /= 2;
728 		vdispend /= 2;
729 	}
730 
731 	vdispend -= 1;
732 	vsyncstart -= 1;
733 	vsyncend -= 1;
734 	vtotal -= 2;
735 
736 	if (cinfo->multiplexing) {
737 		htotal /= 2;
738 		hsyncstart /= 2;
739 		hsyncend /= 2;
740 		hdispend /= 2;
741 	}
742 
743 	htotal -= 5;
744 	hdispend -= 1;
745 	hsyncstart += 1;
746 	hsyncend += 1;
747 
748 	/* unlock register VGA_CRTC_H_TOTAL..CRT7 */
749 	vga_wcrt(regbase, VGA_CRTC_V_SYNC_END, 0x20);	/* previously: 0x00) */
750 
751 	/* if debugging is enabled, all parameters get output before writing */
752 	dev_dbg(info->device, "CRT0: %d\n", htotal);
753 	vga_wcrt(regbase, VGA_CRTC_H_TOTAL, htotal);
754 
755 	dev_dbg(info->device, "CRT1: %d\n", hdispend);
756 	vga_wcrt(regbase, VGA_CRTC_H_DISP, hdispend);
757 
758 	dev_dbg(info->device, "CRT2: %d\n", var->xres / 8);
759 	vga_wcrt(regbase, VGA_CRTC_H_BLANK_START, var->xres / 8);
760 
761 	/*  + 128: Compatible read */
762 	dev_dbg(info->device, "CRT3: 128+%d\n", (htotal + 5) % 32);
763 	vga_wcrt(regbase, VGA_CRTC_H_BLANK_END,
764 		 128 + ((htotal + 5) % 32));
765 
766 	dev_dbg(info->device, "CRT4: %d\n", hsyncstart);
767 	vga_wcrt(regbase, VGA_CRTC_H_SYNC_START, hsyncstart);
768 
769 	tmp = hsyncend % 32;
770 	if ((htotal + 5) & 32)
771 		tmp += 128;
772 	dev_dbg(info->device, "CRT5: %d\n", tmp);
773 	vga_wcrt(regbase, VGA_CRTC_H_SYNC_END, tmp);
774 
775 	dev_dbg(info->device, "CRT6: %d\n", vtotal & 0xff);
776 	vga_wcrt(regbase, VGA_CRTC_V_TOTAL, vtotal & 0xff);
777 
778 	tmp = 16;		/* LineCompare bit #9 */
779 	if (vtotal & 256)
780 		tmp |= 1;
781 	if (vdispend & 256)
782 		tmp |= 2;
783 	if (vsyncstart & 256)
784 		tmp |= 4;
785 	if ((vdispend + 1) & 256)
786 		tmp |= 8;
787 	if (vtotal & 512)
788 		tmp |= 32;
789 	if (vdispend & 512)
790 		tmp |= 64;
791 	if (vsyncstart & 512)
792 		tmp |= 128;
793 	dev_dbg(info->device, "CRT7: %d\n", tmp);
794 	vga_wcrt(regbase, VGA_CRTC_OVERFLOW, tmp);
795 
796 	tmp = 0x40;		/* LineCompare bit #8 */
797 	if ((vdispend + 1) & 512)
798 		tmp |= 0x20;
799 	if (var->vmode & FB_VMODE_DOUBLE)
800 		tmp |= 0x80;
801 	dev_dbg(info->device, "CRT9: %d\n", tmp);
802 	vga_wcrt(regbase, VGA_CRTC_MAX_SCAN, tmp);
803 
804 	dev_dbg(info->device, "CRT10: %d\n", vsyncstart & 0xff);
805 	vga_wcrt(regbase, VGA_CRTC_V_SYNC_START, vsyncstart & 0xff);
806 
807 	dev_dbg(info->device, "CRT11: 64+32+%d\n", vsyncend % 16);
808 	vga_wcrt(regbase, VGA_CRTC_V_SYNC_END, vsyncend % 16 + 64 + 32);
809 
810 	dev_dbg(info->device, "CRT12: %d\n", vdispend & 0xff);
811 	vga_wcrt(regbase, VGA_CRTC_V_DISP_END, vdispend & 0xff);
812 
813 	dev_dbg(info->device, "CRT15: %d\n", (vdispend + 1) & 0xff);
814 	vga_wcrt(regbase, VGA_CRTC_V_BLANK_START, (vdispend + 1) & 0xff);
815 
816 	dev_dbg(info->device, "CRT16: %d\n", vtotal & 0xff);
817 	vga_wcrt(regbase, VGA_CRTC_V_BLANK_END, vtotal & 0xff);
818 
819 	dev_dbg(info->device, "CRT18: 0xff\n");
820 	vga_wcrt(regbase, VGA_CRTC_LINE_COMPARE, 0xff);
821 
822 	tmp = 0;
823 	if (var->vmode & FB_VMODE_INTERLACED)
824 		tmp |= 1;
825 	if ((htotal + 5) & 64)
826 		tmp |= 16;
827 	if ((htotal + 5) & 128)
828 		tmp |= 32;
829 	if (vtotal & 256)
830 		tmp |= 64;
831 	if (vtotal & 512)
832 		tmp |= 128;
833 
834 	dev_dbg(info->device, "CRT1a: %d\n", tmp);
835 	vga_wcrt(regbase, CL_CRT1A, tmp);
836 
837 	freq = PICOS2KHZ(var->pixclock);
838 	if (var->bits_per_pixel == 24)
839 		if (cinfo->btype == BT_ALPINE || cinfo->btype == BT_SD64)
840 			freq *= 3;
841 	if (cinfo->multiplexing)
842 		freq /= 2;
843 	if (cinfo->doubleVCLK)
844 		freq *= 2;
845 
846 	bestclock(freq, &nom, &den, &div);
847 
848 	dev_dbg(info->device, "VCLK freq: %ld kHz  nom: %d  den: %d  div: %d\n",
849 		freq, nom, den, div);
850 
851 	/* set VCLK0 */
852 	/* hardware RefClock: 14.31818 MHz */
853 	/* formula: VClk = (OSC * N) / (D * (1+P)) */
854 	/* Example: VClk = (14.31818 * 91) / (23 * (1+1)) = 28.325 MHz */
855 
856 	if (cinfo->btype == BT_ALPINE || cinfo->btype == BT_PICASSO4 ||
857 	    cinfo->btype == BT_SD64) {
858 		/* if freq is close to mclk or mclk/2 select mclk
859 		 * as clock source
860 		 */
861 		int divMCLK = cirrusfb_check_mclk(info, freq);
862 		if (divMCLK)
863 			nom = 0;
864 		cirrusfb_set_mclk_as_source(info, divMCLK);
865 	}
866 	if (is_laguna(cinfo)) {
867 		long pcifc = fb_readl(cinfo->laguna_mmio + 0x3fc);
868 		unsigned char tile = fb_readb(cinfo->laguna_mmio + 0x407);
869 		unsigned short tile_control;
870 
871 		if (cinfo->btype == BT_LAGUNAB) {
872 			tile_control = fb_readw(cinfo->laguna_mmio + 0x2c4);
873 			tile_control &= ~0x80;
874 			fb_writew(tile_control, cinfo->laguna_mmio + 0x2c4);
875 		}
876 
877 		fb_writel(pcifc | 0x10000000l, cinfo->laguna_mmio + 0x3fc);
878 		fb_writeb(tile & 0x3f, cinfo->laguna_mmio + 0x407);
879 		control = fb_readw(cinfo->laguna_mmio + 0x402);
880 		threshold = fb_readw(cinfo->laguna_mmio + 0xea);
881 		control &= ~0x6800;
882 		format = 0;
883 		threshold &= 0xffc0 & 0x3fbf;
884 	}
885 	if (nom) {
886 		tmp = den << 1;
887 		if (div != 0)
888 			tmp |= 1;
889 		/* 6 bit denom; ONLY 5434!!! (bugged me 10 days) */
890 		if ((cinfo->btype == BT_SD64) ||
891 		    (cinfo->btype == BT_ALPINE) ||
892 		    (cinfo->btype == BT_GD5480))
893 			tmp |= 0x80;
894 
895 		/* Laguna chipset has reversed clock registers */
896 		if (is_laguna(cinfo)) {
897 			vga_wseq(regbase, CL_SEQRE, tmp);
898 			vga_wseq(regbase, CL_SEQR1E, nom);
899 		} else {
900 			vga_wseq(regbase, CL_SEQRE, nom);
901 			vga_wseq(regbase, CL_SEQR1E, tmp);
902 		}
903 	}
904 
905 	if (yres >= 1024)
906 		/* 1280x1024 */
907 		vga_wcrt(regbase, VGA_CRTC_MODE, 0xc7);
908 	else
909 		/* mode control: VGA_CRTC_START_HI enable, ROTATE(?), 16bit
910 		 * address wrap, no compat. */
911 		vga_wcrt(regbase, VGA_CRTC_MODE, 0xc3);
912 
913 	/* don't know if it would hurt to also program this if no interlaced */
914 	/* mode is used, but I feel better this way.. :-) */
915 	if (var->vmode & FB_VMODE_INTERLACED)
916 		vga_wcrt(regbase, VGA_CRTC_REGS, htotal / 2);
917 	else
918 		vga_wcrt(regbase, VGA_CRTC_REGS, 0x00);	/* interlace control */
919 
920 	/* adjust horizontal/vertical sync type (low/high), use VCLK3 */
921 	/* enable display memory & CRTC I/O address for color mode */
922 	tmp = 0x03 | 0xc;
923 	if (var->sync & FB_SYNC_HOR_HIGH_ACT)
924 		tmp |= 0x40;
925 	if (var->sync & FB_SYNC_VERT_HIGH_ACT)
926 		tmp |= 0x80;
927 	WGen(cinfo, VGA_MIS_W, tmp);
928 
929 	/* text cursor on and start line */
930 	vga_wcrt(regbase, VGA_CRTC_CURSOR_START, 0);
931 	/* text cursor end line */
932 	vga_wcrt(regbase, VGA_CRTC_CURSOR_END, 31);
933 
934 	/******************************************************
935 	 *
936 	 * 1 bpp
937 	 *
938 	 */
939 
940 	/* programming for different color depths */
941 	if (var->bits_per_pixel == 1) {
942 		dev_dbg(info->device, "preparing for 1 bit deep display\n");
943 		vga_wgfx(regbase, VGA_GFX_MODE, 0);	/* mode register */
944 
945 		/* SR07 */
946 		switch (cinfo->btype) {
947 		case BT_SD64:
948 		case BT_PICCOLO:
949 		case BT_PICASSO:
950 		case BT_SPECTRUM:
951 		case BT_PICASSO4:
952 		case BT_ALPINE:
953 		case BT_GD5480:
954 			vga_wseq(regbase, CL_SEQR7,
955 				 cinfo->multiplexing ?
956 					bi->sr07_1bpp_mux : bi->sr07_1bpp);
957 			break;
958 
959 		case BT_LAGUNA:
960 		case BT_LAGUNAB:
961 			vga_wseq(regbase, CL_SEQR7,
962 				vga_rseq(regbase, CL_SEQR7) & ~0x01);
963 			break;
964 
965 		default:
966 			dev_warn(info->device, "unknown Board\n");
967 			break;
968 		}
969 
970 		/* Extended Sequencer Mode */
971 		switch (cinfo->btype) {
972 
973 		case BT_PICCOLO:
974 		case BT_SPECTRUM:
975 			/* evtl d0 bei 1 bit? avoid FIFO underruns..? */
976 			vga_wseq(regbase, CL_SEQRF, 0xb0);
977 			break;
978 
979 		case BT_PICASSO:
980 			/* ## vorher d0 avoid FIFO underruns..? */
981 			vga_wseq(regbase, CL_SEQRF, 0xd0);
982 			break;
983 
984 		case BT_SD64:
985 		case BT_PICASSO4:
986 		case BT_ALPINE:
987 		case BT_GD5480:
988 		case BT_LAGUNA:
989 		case BT_LAGUNAB:
990 			/* do nothing */
991 			break;
992 
993 		default:
994 			dev_warn(info->device, "unknown Board\n");
995 			break;
996 		}
997 
998 		/* pixel mask: pass-through for first plane */
999 		WGen(cinfo, VGA_PEL_MSK, 0x01);
1000 		if (cinfo->multiplexing)
1001 			/* hidden dac reg: 1280x1024 */
1002 			WHDR(cinfo, 0x4a);
1003 		else
1004 			/* hidden dac: nothing */
1005 			WHDR(cinfo, 0);
1006 		/* memory mode: odd/even, ext. memory */
1007 		vga_wseq(regbase, VGA_SEQ_MEMORY_MODE, 0x06);
1008 		/* plane mask: only write to first plane */
1009 		vga_wseq(regbase, VGA_SEQ_PLANE_WRITE, 0x01);
1010 	}
1011 
1012 	/******************************************************
1013 	 *
1014 	 * 8 bpp
1015 	 *
1016 	 */
1017 
1018 	else if (var->bits_per_pixel == 8) {
1019 		dev_dbg(info->device, "preparing for 8 bit deep display\n");
1020 		switch (cinfo->btype) {
1021 		case BT_SD64:
1022 		case BT_PICCOLO:
1023 		case BT_PICASSO:
1024 		case BT_SPECTRUM:
1025 		case BT_PICASSO4:
1026 		case BT_ALPINE:
1027 		case BT_GD5480:
1028 			vga_wseq(regbase, CL_SEQR7,
1029 				  cinfo->multiplexing ?
1030 					bi->sr07_8bpp_mux : bi->sr07_8bpp);
1031 			break;
1032 
1033 		case BT_LAGUNA:
1034 		case BT_LAGUNAB:
1035 			vga_wseq(regbase, CL_SEQR7,
1036 				vga_rseq(regbase, CL_SEQR7) | 0x01);
1037 			threshold |= 0x10;
1038 			break;
1039 
1040 		default:
1041 			dev_warn(info->device, "unknown Board\n");
1042 			break;
1043 		}
1044 
1045 		switch (cinfo->btype) {
1046 		case BT_PICCOLO:
1047 		case BT_PICASSO:
1048 		case BT_SPECTRUM:
1049 			/* Fast Page-Mode writes */
1050 			vga_wseq(regbase, CL_SEQRF, 0xb0);
1051 			break;
1052 
1053 		case BT_PICASSO4:
1054 #ifdef CONFIG_ZORRO
1055 			/* ### INCOMPLETE!! */
1056 			vga_wseq(regbase, CL_SEQRF, 0xb8);
1057 #endif
1058 		case BT_ALPINE:
1059 		case BT_SD64:
1060 		case BT_GD5480:
1061 		case BT_LAGUNA:
1062 		case BT_LAGUNAB:
1063 			/* do nothing */
1064 			break;
1065 
1066 		default:
1067 			dev_warn(info->device, "unknown board\n");
1068 			break;
1069 		}
1070 
1071 		/* mode register: 256 color mode */
1072 		vga_wgfx(regbase, VGA_GFX_MODE, 64);
1073 		if (cinfo->multiplexing)
1074 			/* hidden dac reg: 1280x1024 */
1075 			WHDR(cinfo, 0x4a);
1076 		else
1077 			/* hidden dac: nothing */
1078 			WHDR(cinfo, 0);
1079 	}
1080 
1081 	/******************************************************
1082 	 *
1083 	 * 16 bpp
1084 	 *
1085 	 */
1086 
1087 	else if (var->bits_per_pixel == 16) {
1088 		dev_dbg(info->device, "preparing for 16 bit deep display\n");
1089 		switch (cinfo->btype) {
1090 		case BT_PICCOLO:
1091 		case BT_SPECTRUM:
1092 			vga_wseq(regbase, CL_SEQR7, 0x87);
1093 			/* Fast Page-Mode writes */
1094 			vga_wseq(regbase, CL_SEQRF, 0xb0);
1095 			break;
1096 
1097 		case BT_PICASSO:
1098 			vga_wseq(regbase, CL_SEQR7, 0x27);
1099 			/* Fast Page-Mode writes */
1100 			vga_wseq(regbase, CL_SEQRF, 0xb0);
1101 			break;
1102 
1103 		case BT_SD64:
1104 		case BT_PICASSO4:
1105 		case BT_ALPINE:
1106 			/* Extended Sequencer Mode: 256c col. mode */
1107 			vga_wseq(regbase, CL_SEQR7,
1108 					cinfo->doubleVCLK ? 0xa3 : 0xa7);
1109 			break;
1110 
1111 		case BT_GD5480:
1112 			vga_wseq(regbase, CL_SEQR7, 0x17);
1113 			/* We already set SRF and SR1F */
1114 			break;
1115 
1116 		case BT_LAGUNA:
1117 		case BT_LAGUNAB:
1118 			vga_wseq(regbase, CL_SEQR7,
1119 				vga_rseq(regbase, CL_SEQR7) & ~0x01);
1120 			control |= 0x2000;
1121 			format |= 0x1400;
1122 			threshold |= 0x10;
1123 			break;
1124 
1125 		default:
1126 			dev_warn(info->device, "unknown Board\n");
1127 			break;
1128 		}
1129 
1130 		/* mode register: 256 color mode */
1131 		vga_wgfx(regbase, VGA_GFX_MODE, 64);
1132 #ifdef CONFIG_PCI
1133 		WHDR(cinfo, cinfo->doubleVCLK ? 0xe1 : 0xc1);
1134 #elif defined(CONFIG_ZORRO)
1135 		/* FIXME: CONFIG_PCI and CONFIG_ZORRO may be defined both */
1136 		WHDR(cinfo, 0xa0);	/* hidden dac reg: nothing special */
1137 #endif
1138 	}
1139 
1140 	/******************************************************
1141 	 *
1142 	 * 24 bpp
1143 	 *
1144 	 */
1145 
1146 	else if (var->bits_per_pixel == 24) {
1147 		dev_dbg(info->device, "preparing for 24 bit deep display\n");
1148 		switch (cinfo->btype) {
1149 		case BT_PICCOLO:
1150 		case BT_SPECTRUM:
1151 			vga_wseq(regbase, CL_SEQR7, 0x85);
1152 			/* Fast Page-Mode writes */
1153 			vga_wseq(regbase, CL_SEQRF, 0xb0);
1154 			break;
1155 
1156 		case BT_PICASSO:
1157 			vga_wseq(regbase, CL_SEQR7, 0x25);
1158 			/* Fast Page-Mode writes */
1159 			vga_wseq(regbase, CL_SEQRF, 0xb0);
1160 			break;
1161 
1162 		case BT_SD64:
1163 		case BT_PICASSO4:
1164 		case BT_ALPINE:
1165 			/* Extended Sequencer Mode: 256c col. mode */
1166 			vga_wseq(regbase, CL_SEQR7, 0xa5);
1167 			break;
1168 
1169 		case BT_GD5480:
1170 			vga_wseq(regbase, CL_SEQR7, 0x15);
1171 			/* We already set SRF and SR1F */
1172 			break;
1173 
1174 		case BT_LAGUNA:
1175 		case BT_LAGUNAB:
1176 			vga_wseq(regbase, CL_SEQR7,
1177 				vga_rseq(regbase, CL_SEQR7) & ~0x01);
1178 			control |= 0x4000;
1179 			format |= 0x2400;
1180 			threshold |= 0x20;
1181 			break;
1182 
1183 		default:
1184 			dev_warn(info->device, "unknown Board\n");
1185 			break;
1186 		}
1187 
1188 		/* mode register: 256 color mode */
1189 		vga_wgfx(regbase, VGA_GFX_MODE, 64);
1190 		/* hidden dac reg: 8-8-8 mode (24 or 32) */
1191 		WHDR(cinfo, 0xc5);
1192 	}
1193 
1194 	/******************************************************
1195 	 *
1196 	 * unknown/unsupported bpp
1197 	 *
1198 	 */
1199 
1200 	else
1201 		dev_err(info->device,
1202 			"What's this? requested color depth == %d.\n",
1203 			var->bits_per_pixel);
1204 
1205 	pitch = info->fix.line_length >> 3;
1206 	vga_wcrt(regbase, VGA_CRTC_OFFSET, pitch & 0xff);
1207 	tmp = 0x22;
1208 	if (pitch & 0x100)
1209 		tmp |= 0x10;	/* offset overflow bit */
1210 
1211 	/* screen start addr #16-18, fastpagemode cycles */
1212 	vga_wcrt(regbase, CL_CRT1B, tmp);
1213 
1214 	/* screen start address bit 19 */
1215 	if (cirrusfb_board_info[cinfo->btype].scrn_start_bit19)
1216 		vga_wcrt(regbase, CL_CRT1D, (pitch >> 9) & 1);
1217 
1218 	if (is_laguna(cinfo)) {
1219 		tmp = 0;
1220 		if ((htotal + 5) & 256)
1221 			tmp |= 128;
1222 		if (hdispend & 256)
1223 			tmp |= 64;
1224 		if (hsyncstart & 256)
1225 			tmp |= 48;
1226 		if (vtotal & 1024)
1227 			tmp |= 8;
1228 		if (vdispend & 1024)
1229 			tmp |= 4;
1230 		if (vsyncstart & 1024)
1231 			tmp |= 3;
1232 
1233 		vga_wcrt(regbase, CL_CRT1E, tmp);
1234 		dev_dbg(info->device, "CRT1e: %d\n", tmp);
1235 	}
1236 
1237 	/* pixel panning */
1238 	vga_wattr(regbase, CL_AR33, 0);
1239 
1240 	/* [ EGS: SetOffset(); ] */
1241 	/* From SetOffset(): Turn on VideoEnable bit in Attribute controller */
1242 	AttrOn(cinfo);
1243 
1244 	if (is_laguna(cinfo)) {
1245 		/* no tiles */
1246 		fb_writew(control | 0x1000, cinfo->laguna_mmio + 0x402);
1247 		fb_writew(format, cinfo->laguna_mmio + 0xc0);
1248 		fb_writew(threshold, cinfo->laguna_mmio + 0xea);
1249 	}
1250 	/* finally, turn on everything - turn off "FullBandwidth" bit */
1251 	/* also, set "DotClock%2" bit where requested */
1252 	tmp = 0x01;
1253 
1254 /*** FB_VMODE_CLOCK_HALVE in linux/fb.h not defined anymore ?
1255     if (var->vmode & FB_VMODE_CLOCK_HALVE)
1256 	tmp |= 0x08;
1257 */
1258 
1259 	vga_wseq(regbase, VGA_SEQ_CLOCK_MODE, tmp);
1260 	dev_dbg(info->device, "CL_SEQR1: %d\n", tmp);
1261 
1262 #ifdef CIRRUSFB_DEBUG
1263 	cirrusfb_dbg_reg_dump(info, NULL);
1264 #endif
1265 
1266 	return 0;
1267 }
1268 
1269 /* for some reason incomprehensible to me, cirrusfb requires that you write
1270  * the registers twice for the settings to take..grr. -dte */
1271 static int cirrusfb_set_par(struct fb_info *info)
1272 {
1273 	cirrusfb_set_par_foo(info);
1274 	return cirrusfb_set_par_foo(info);
1275 }
1276 
1277 static int cirrusfb_setcolreg(unsigned regno, unsigned red, unsigned green,
1278 			      unsigned blue, unsigned transp,
1279 			      struct fb_info *info)
1280 {
1281 	struct cirrusfb_info *cinfo = info->par;
1282 
1283 	if (regno > 255)
1284 		return -EINVAL;
1285 
1286 	if (info->fix.visual == FB_VISUAL_TRUECOLOR) {
1287 		u32 v;
1288 		red >>= (16 - info->var.red.length);
1289 		green >>= (16 - info->var.green.length);
1290 		blue >>= (16 - info->var.blue.length);
1291 
1292 		if (regno >= 16)
1293 			return 1;
1294 		v = (red << info->var.red.offset) |
1295 		    (green << info->var.green.offset) |
1296 		    (blue << info->var.blue.offset);
1297 
1298 		cinfo->pseudo_palette[regno] = v;
1299 		return 0;
1300 	}
1301 
1302 	if (info->var.bits_per_pixel == 8)
1303 		WClut(cinfo, regno, red >> 10, green >> 10, blue >> 10);
1304 
1305 	return 0;
1306 
1307 }
1308 
1309 /*************************************************************************
1310 	cirrusfb_pan_display()
1311 
1312 	performs display panning - provided hardware permits this
1313 **************************************************************************/
1314 static int cirrusfb_pan_display(struct fb_var_screeninfo *var,
1315 				struct fb_info *info)
1316 {
1317 	int xoffset;
1318 	unsigned long base;
1319 	unsigned char tmp, xpix;
1320 	struct cirrusfb_info *cinfo = info->par;
1321 
1322 	/* no range checks for xoffset and yoffset,   */
1323 	/* as fb_pan_display has already done this */
1324 	if (var->vmode & FB_VMODE_YWRAP)
1325 		return -EINVAL;
1326 
1327 	xoffset = var->xoffset * info->var.bits_per_pixel / 8;
1328 
1329 	base = var->yoffset * info->fix.line_length + xoffset;
1330 
1331 	if (info->var.bits_per_pixel == 1) {
1332 		/* base is already correct */
1333 		xpix = (unsigned char) (var->xoffset % 8);
1334 	} else {
1335 		base /= 4;
1336 		xpix = (unsigned char) ((xoffset % 4) * 2);
1337 	}
1338 
1339 	if (!is_laguna(cinfo))
1340 		cirrusfb_WaitBLT(cinfo->regbase);
1341 
1342 	/* lower 8 + 8 bits of screen start address */
1343 	vga_wcrt(cinfo->regbase, VGA_CRTC_START_LO, base & 0xff);
1344 	vga_wcrt(cinfo->regbase, VGA_CRTC_START_HI, (base >> 8) & 0xff);
1345 
1346 	/* 0xf2 is %11110010, exclude tmp bits */
1347 	tmp = vga_rcrt(cinfo->regbase, CL_CRT1B) & 0xf2;
1348 	/* construct bits 16, 17 and 18 of screen start address */
1349 	if (base & 0x10000)
1350 		tmp |= 0x01;
1351 	if (base & 0x20000)
1352 		tmp |= 0x04;
1353 	if (base & 0x40000)
1354 		tmp |= 0x08;
1355 
1356 	vga_wcrt(cinfo->regbase, CL_CRT1B, tmp);
1357 
1358 	/* construct bit 19 of screen start address */
1359 	if (cirrusfb_board_info[cinfo->btype].scrn_start_bit19) {
1360 		tmp = vga_rcrt(cinfo->regbase, CL_CRT1D);
1361 		if (is_laguna(cinfo))
1362 			tmp = (tmp & ~0x18) | ((base >> 16) & 0x18);
1363 		else
1364 			tmp = (tmp & ~0x80) | ((base >> 12) & 0x80);
1365 		vga_wcrt(cinfo->regbase, CL_CRT1D, tmp);
1366 	}
1367 
1368 	/* write pixel panning value to AR33; this does not quite work in 8bpp
1369 	 *
1370 	 * ### Piccolo..? Will this work?
1371 	 */
1372 	if (info->var.bits_per_pixel == 1)
1373 		vga_wattr(cinfo->regbase, CL_AR33, xpix);
1374 
1375 	return 0;
1376 }
1377 
1378 static int cirrusfb_blank(int blank_mode, struct fb_info *info)
1379 {
1380 	/*
1381 	 * Blank the screen if blank_mode != 0, else unblank. If blank == NULL
1382 	 * then the caller blanks by setting the CLUT (Color Look Up Table)
1383 	 * to all black. Return 0 if blanking succeeded, != 0 if un-/blanking
1384 	 * failed due to e.g. a video mode which doesn't support it.
1385 	 * Implements VESA suspend and powerdown modes on hardware that
1386 	 * supports disabling hsync/vsync:
1387 	 *   blank_mode == 2: suspend vsync
1388 	 *   blank_mode == 3: suspend hsync
1389 	 *   blank_mode == 4: powerdown
1390 	 */
1391 	unsigned char val;
1392 	struct cirrusfb_info *cinfo = info->par;
1393 	int current_mode = cinfo->blank_mode;
1394 
1395 	dev_dbg(info->device, "ENTER, blank mode = %d\n", blank_mode);
1396 
1397 	if (info->state != FBINFO_STATE_RUNNING ||
1398 	    current_mode == blank_mode) {
1399 		dev_dbg(info->device, "EXIT, returning 0\n");
1400 		return 0;
1401 	}
1402 
1403 	/* Undo current */
1404 	if (current_mode == FB_BLANK_NORMAL ||
1405 	    current_mode == FB_BLANK_UNBLANK)
1406 		/* clear "FullBandwidth" bit */
1407 		val = 0;
1408 	else
1409 		/* set "FullBandwidth" bit */
1410 		val = 0x20;
1411 
1412 	val |= vga_rseq(cinfo->regbase, VGA_SEQ_CLOCK_MODE) & 0xdf;
1413 	vga_wseq(cinfo->regbase, VGA_SEQ_CLOCK_MODE, val);
1414 
1415 	switch (blank_mode) {
1416 	case FB_BLANK_UNBLANK:
1417 	case FB_BLANK_NORMAL:
1418 		val = 0x00;
1419 		break;
1420 	case FB_BLANK_VSYNC_SUSPEND:
1421 		val = 0x04;
1422 		break;
1423 	case FB_BLANK_HSYNC_SUSPEND:
1424 		val = 0x02;
1425 		break;
1426 	case FB_BLANK_POWERDOWN:
1427 		val = 0x06;
1428 		break;
1429 	default:
1430 		dev_dbg(info->device, "EXIT, returning 1\n");
1431 		return 1;
1432 	}
1433 
1434 	vga_wgfx(cinfo->regbase, CL_GRE, val);
1435 
1436 	cinfo->blank_mode = blank_mode;
1437 	dev_dbg(info->device, "EXIT, returning 0\n");
1438 
1439 	/* Let fbcon do a soft blank for us */
1440 	return (blank_mode == FB_BLANK_NORMAL) ? 1 : 0;
1441 }
1442 
1443 /**** END   Hardware specific Routines **************************************/
1444 /****************************************************************************/
1445 /**** BEGIN Internal Routines ***********************************************/
1446 
1447 static void init_vgachip(struct fb_info *info)
1448 {
1449 	struct cirrusfb_info *cinfo = info->par;
1450 	const struct cirrusfb_board_info_rec *bi;
1451 
1452 	assert(cinfo != NULL);
1453 
1454 	bi = &cirrusfb_board_info[cinfo->btype];
1455 
1456 	/* reset board globally */
1457 	switch (cinfo->btype) {
1458 	case BT_PICCOLO:
1459 		WSFR(cinfo, 0x01);
1460 		udelay(500);
1461 		WSFR(cinfo, 0x51);
1462 		udelay(500);
1463 		break;
1464 	case BT_PICASSO:
1465 		WSFR2(cinfo, 0xff);
1466 		udelay(500);
1467 		break;
1468 	case BT_SD64:
1469 	case BT_SPECTRUM:
1470 		WSFR(cinfo, 0x1f);
1471 		udelay(500);
1472 		WSFR(cinfo, 0x4f);
1473 		udelay(500);
1474 		break;
1475 	case BT_PICASSO4:
1476 		/* disable flickerfixer */
1477 		vga_wcrt(cinfo->regbase, CL_CRT51, 0x00);
1478 		mdelay(100);
1479 		/* mode */
1480 		vga_wgfx(cinfo->regbase, CL_GR31, 0x00);
1481 		fallthrough;
1482 	case BT_GD5480:
1483 		/* from Klaus' NetBSD driver: */
1484 		vga_wgfx(cinfo->regbase, CL_GR2F, 0x00);
1485 		fallthrough;
1486 	case BT_ALPINE:
1487 		/* put blitter into 542x compat */
1488 		vga_wgfx(cinfo->regbase, CL_GR33, 0x00);
1489 		break;
1490 
1491 	case BT_LAGUNA:
1492 	case BT_LAGUNAB:
1493 		/* Nothing to do to reset the board. */
1494 		break;
1495 
1496 	default:
1497 		dev_err(info->device, "Warning: Unknown board type\n");
1498 		break;
1499 	}
1500 
1501 	/* make sure RAM size set by this point */
1502 	assert(info->screen_size > 0);
1503 
1504 	/* the P4 is not fully initialized here; I rely on it having been */
1505 	/* inited under AmigaOS already, which seems to work just fine    */
1506 	/* (Klaus advised to do it this way)			      */
1507 
1508 	if (cinfo->btype != BT_PICASSO4) {
1509 		WGen(cinfo, CL_VSSM, 0x10);	/* EGS: 0x16 */
1510 		WGen(cinfo, CL_POS102, 0x01);
1511 		WGen(cinfo, CL_VSSM, 0x08);	/* EGS: 0x0e */
1512 
1513 		if (cinfo->btype != BT_SD64)
1514 			WGen(cinfo, CL_VSSM2, 0x01);
1515 
1516 		/* reset sequencer logic */
1517 		vga_wseq(cinfo->regbase, VGA_SEQ_RESET, 0x03);
1518 
1519 		/* FullBandwidth (video off) and 8/9 dot clock */
1520 		vga_wseq(cinfo->regbase, VGA_SEQ_CLOCK_MODE, 0x21);
1521 
1522 		/* "magic cookie" - doesn't make any sense to me.. */
1523 /*      vga_wgfx(cinfo->regbase, CL_GRA, 0xce);   */
1524 		/* unlock all extension registers */
1525 		vga_wseq(cinfo->regbase, CL_SEQR6, 0x12);
1526 
1527 		switch (cinfo->btype) {
1528 		case BT_GD5480:
1529 			vga_wseq(cinfo->regbase, CL_SEQRF, 0x98);
1530 			break;
1531 		case BT_ALPINE:
1532 		case BT_LAGUNA:
1533 		case BT_LAGUNAB:
1534 			break;
1535 		case BT_SD64:
1536 #ifdef CONFIG_ZORRO
1537 			vga_wseq(cinfo->regbase, CL_SEQRF, 0xb8);
1538 #endif
1539 			break;
1540 		default:
1541 			vga_wseq(cinfo->regbase, CL_SEQR16, 0x0f);
1542 			vga_wseq(cinfo->regbase, CL_SEQRF, 0xb0);
1543 			break;
1544 		}
1545 	}
1546 	/* plane mask: nothing */
1547 	vga_wseq(cinfo->regbase, VGA_SEQ_PLANE_WRITE, 0xff);
1548 	/* character map select: doesn't even matter in gx mode */
1549 	vga_wseq(cinfo->regbase, VGA_SEQ_CHARACTER_MAP, 0x00);
1550 	/* memory mode: chain4, ext. memory */
1551 	vga_wseq(cinfo->regbase, VGA_SEQ_MEMORY_MODE, 0x0a);
1552 
1553 	/* controller-internal base address of video memory */
1554 	if (bi->init_sr07)
1555 		vga_wseq(cinfo->regbase, CL_SEQR7, bi->sr07);
1556 
1557 	/*  vga_wseq(cinfo->regbase, CL_SEQR8, 0x00); */
1558 	/* EEPROM control: shouldn't be necessary to write to this at all.. */
1559 
1560 	/* graphics cursor X position (incomplete; position gives rem. 3 bits */
1561 	vga_wseq(cinfo->regbase, CL_SEQR10, 0x00);
1562 	/* graphics cursor Y position (..."... ) */
1563 	vga_wseq(cinfo->regbase, CL_SEQR11, 0x00);
1564 	/* graphics cursor attributes */
1565 	vga_wseq(cinfo->regbase, CL_SEQR12, 0x00);
1566 	/* graphics cursor pattern address */
1567 	vga_wseq(cinfo->regbase, CL_SEQR13, 0x00);
1568 
1569 	/* writing these on a P4 might give problems..  */
1570 	if (cinfo->btype != BT_PICASSO4) {
1571 		/* configuration readback and ext. color */
1572 		vga_wseq(cinfo->regbase, CL_SEQR17, 0x00);
1573 		/* signature generator */
1574 		vga_wseq(cinfo->regbase, CL_SEQR18, 0x02);
1575 	}
1576 
1577 	/* Screen A preset row scan: none */
1578 	vga_wcrt(cinfo->regbase, VGA_CRTC_PRESET_ROW, 0x00);
1579 	/* Text cursor start: disable text cursor */
1580 	vga_wcrt(cinfo->regbase, VGA_CRTC_CURSOR_START, 0x20);
1581 	/* Text cursor end: - */
1582 	vga_wcrt(cinfo->regbase, VGA_CRTC_CURSOR_END, 0x00);
1583 	/* text cursor location high: 0 */
1584 	vga_wcrt(cinfo->regbase, VGA_CRTC_CURSOR_HI, 0x00);
1585 	/* text cursor location low: 0 */
1586 	vga_wcrt(cinfo->regbase, VGA_CRTC_CURSOR_LO, 0x00);
1587 
1588 	/* Underline Row scanline: - */
1589 	vga_wcrt(cinfo->regbase, VGA_CRTC_UNDERLINE, 0x00);
1590 	/* ### add 0x40 for text modes with > 30 MHz pixclock */
1591 	/* ext. display controls: ext.adr. wrap */
1592 	vga_wcrt(cinfo->regbase, CL_CRT1B, 0x02);
1593 
1594 	/* Set/Reset registers: - */
1595 	vga_wgfx(cinfo->regbase, VGA_GFX_SR_VALUE, 0x00);
1596 	/* Set/Reset enable: - */
1597 	vga_wgfx(cinfo->regbase, VGA_GFX_SR_ENABLE, 0x00);
1598 	/* Color Compare: - */
1599 	vga_wgfx(cinfo->regbase, VGA_GFX_COMPARE_VALUE, 0x00);
1600 	/* Data Rotate: - */
1601 	vga_wgfx(cinfo->regbase, VGA_GFX_DATA_ROTATE, 0x00);
1602 	/* Read Map Select: - */
1603 	vga_wgfx(cinfo->regbase, VGA_GFX_PLANE_READ, 0x00);
1604 	/* Mode: conf. for 16/4/2 color mode, no odd/even, read/write mode 0 */
1605 	vga_wgfx(cinfo->regbase, VGA_GFX_MODE, 0x00);
1606 	/* Miscellaneous: memory map base address, graphics mode */
1607 	vga_wgfx(cinfo->regbase, VGA_GFX_MISC, 0x01);
1608 	/* Color Don't care: involve all planes */
1609 	vga_wgfx(cinfo->regbase, VGA_GFX_COMPARE_MASK, 0x0f);
1610 	/* Bit Mask: no mask at all */
1611 	vga_wgfx(cinfo->regbase, VGA_GFX_BIT_MASK, 0xff);
1612 
1613 	if (cinfo->btype == BT_ALPINE || cinfo->btype == BT_SD64 ||
1614 	    is_laguna(cinfo))
1615 		/* (5434 can't have bit 3 set for bitblt) */
1616 		vga_wgfx(cinfo->regbase, CL_GRB, 0x20);
1617 	else
1618 	/* Graphics controller mode extensions: finer granularity,
1619 	 * 8byte data latches
1620 	 */
1621 		vga_wgfx(cinfo->regbase, CL_GRB, 0x28);
1622 
1623 	vga_wgfx(cinfo->regbase, CL_GRC, 0xff);	/* Color Key compare: - */
1624 	vga_wgfx(cinfo->regbase, CL_GRD, 0x00);	/* Color Key compare mask: - */
1625 	vga_wgfx(cinfo->regbase, CL_GRE, 0x00);	/* Miscellaneous control: - */
1626 	/* Background color byte 1: - */
1627 	/*  vga_wgfx (cinfo->regbase, CL_GR10, 0x00); */
1628 	/*  vga_wgfx (cinfo->regbase, CL_GR11, 0x00); */
1629 
1630 	/* Attribute Controller palette registers: "identity mapping" */
1631 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE0, 0x00);
1632 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE1, 0x01);
1633 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE2, 0x02);
1634 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE3, 0x03);
1635 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE4, 0x04);
1636 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE5, 0x05);
1637 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE6, 0x06);
1638 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE7, 0x07);
1639 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE8, 0x08);
1640 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTE9, 0x09);
1641 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTEA, 0x0a);
1642 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTEB, 0x0b);
1643 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTEC, 0x0c);
1644 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTED, 0x0d);
1645 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTEE, 0x0e);
1646 	vga_wattr(cinfo->regbase, VGA_ATC_PALETTEF, 0x0f);
1647 
1648 	/* Attribute Controller mode: graphics mode */
1649 	vga_wattr(cinfo->regbase, VGA_ATC_MODE, 0x01);
1650 	/* Overscan color reg.: reg. 0 */
1651 	vga_wattr(cinfo->regbase, VGA_ATC_OVERSCAN, 0x00);
1652 	/* Color Plane enable: Enable all 4 planes */
1653 	vga_wattr(cinfo->regbase, VGA_ATC_PLANE_ENABLE, 0x0f);
1654 	/* Color Select: - */
1655 	vga_wattr(cinfo->regbase, VGA_ATC_COLOR_PAGE, 0x00);
1656 
1657 	WGen(cinfo, VGA_PEL_MSK, 0xff);	/* Pixel mask: no mask */
1658 
1659 	/* BLT Start/status: Blitter reset */
1660 	vga_wgfx(cinfo->regbase, CL_GR31, 0x04);
1661 	/* - " -	   : "end-of-reset" */
1662 	vga_wgfx(cinfo->regbase, CL_GR31, 0x00);
1663 
1664 	/* misc... */
1665 	WHDR(cinfo, 0);	/* Hidden DAC register: - */
1666 	return;
1667 }
1668 
1669 static void switch_monitor(struct cirrusfb_info *cinfo, int on)
1670 {
1671 #ifdef CONFIG_ZORRO /* only works on Zorro boards */
1672 	static int IsOn = 0;	/* XXX not ok for multiple boards */
1673 
1674 	if (cinfo->btype == BT_PICASSO4)
1675 		return;		/* nothing to switch */
1676 	if (cinfo->btype == BT_ALPINE)
1677 		return;		/* nothing to switch */
1678 	if (cinfo->btype == BT_GD5480)
1679 		return;		/* nothing to switch */
1680 	if (cinfo->btype == BT_PICASSO) {
1681 		if ((on && !IsOn) || (!on && IsOn))
1682 			WSFR(cinfo, 0xff);
1683 		return;
1684 	}
1685 	if (on) {
1686 		switch (cinfo->btype) {
1687 		case BT_SD64:
1688 			WSFR(cinfo, cinfo->SFR | 0x21);
1689 			break;
1690 		case BT_PICCOLO:
1691 			WSFR(cinfo, cinfo->SFR | 0x28);
1692 			break;
1693 		case BT_SPECTRUM:
1694 			WSFR(cinfo, 0x6f);
1695 			break;
1696 		default: /* do nothing */ break;
1697 		}
1698 	} else {
1699 		switch (cinfo->btype) {
1700 		case BT_SD64:
1701 			WSFR(cinfo, cinfo->SFR & 0xde);
1702 			break;
1703 		case BT_PICCOLO:
1704 			WSFR(cinfo, cinfo->SFR & 0xd7);
1705 			break;
1706 		case BT_SPECTRUM:
1707 			WSFR(cinfo, 0x4f);
1708 			break;
1709 		default: /* do nothing */
1710 			break;
1711 		}
1712 	}
1713 #endif /* CONFIG_ZORRO */
1714 }
1715 
1716 /******************************************/
1717 /* Linux 2.6-style  accelerated functions */
1718 /******************************************/
1719 
1720 static int cirrusfb_sync(struct fb_info *info)
1721 {
1722 	struct cirrusfb_info *cinfo = info->par;
1723 
1724 	if (!is_laguna(cinfo)) {
1725 		while (vga_rgfx(cinfo->regbase, CL_GR31) & 0x03)
1726 			cpu_relax();
1727 	}
1728 	return 0;
1729 }
1730 
1731 static void cirrusfb_fillrect(struct fb_info *info,
1732 			      const struct fb_fillrect *region)
1733 {
1734 	struct fb_fillrect modded;
1735 	int vxres, vyres;
1736 	struct cirrusfb_info *cinfo = info->par;
1737 	int m = info->var.bits_per_pixel;
1738 	u32 color = (info->fix.visual == FB_VISUAL_TRUECOLOR) ?
1739 		cinfo->pseudo_palette[region->color] : region->color;
1740 
1741 	if (info->state != FBINFO_STATE_RUNNING)
1742 		return;
1743 	if (info->flags & FBINFO_HWACCEL_DISABLED) {
1744 		cfb_fillrect(info, region);
1745 		return;
1746 	}
1747 
1748 	vxres = info->var.xres_virtual;
1749 	vyres = info->var.yres_virtual;
1750 
1751 	memcpy(&modded, region, sizeof(struct fb_fillrect));
1752 
1753 	if (!modded.width || !modded.height ||
1754 	   modded.dx >= vxres || modded.dy >= vyres)
1755 		return;
1756 
1757 	if (modded.dx + modded.width  > vxres)
1758 		modded.width  = vxres - modded.dx;
1759 	if (modded.dy + modded.height > vyres)
1760 		modded.height = vyres - modded.dy;
1761 
1762 	cirrusfb_RectFill(cinfo->regbase,
1763 			  info->var.bits_per_pixel,
1764 			  (region->dx * m) / 8, region->dy,
1765 			  (region->width * m) / 8, region->height,
1766 			  color, color,
1767 			  info->fix.line_length, 0x40);
1768 }
1769 
1770 static void cirrusfb_copyarea(struct fb_info *info,
1771 			      const struct fb_copyarea *area)
1772 {
1773 	struct fb_copyarea modded;
1774 	u32 vxres, vyres;
1775 	struct cirrusfb_info *cinfo = info->par;
1776 	int m = info->var.bits_per_pixel;
1777 
1778 	if (info->state != FBINFO_STATE_RUNNING)
1779 		return;
1780 	if (info->flags & FBINFO_HWACCEL_DISABLED) {
1781 		cfb_copyarea(info, area);
1782 		return;
1783 	}
1784 
1785 	vxres = info->var.xres_virtual;
1786 	vyres = info->var.yres_virtual;
1787 	memcpy(&modded, area, sizeof(struct fb_copyarea));
1788 
1789 	if (!modded.width || !modded.height ||
1790 	   modded.sx >= vxres || modded.sy >= vyres ||
1791 	   modded.dx >= vxres || modded.dy >= vyres)
1792 		return;
1793 
1794 	if (modded.sx + modded.width > vxres)
1795 		modded.width = vxres - modded.sx;
1796 	if (modded.dx + modded.width > vxres)
1797 		modded.width = vxres - modded.dx;
1798 	if (modded.sy + modded.height > vyres)
1799 		modded.height = vyres - modded.sy;
1800 	if (modded.dy + modded.height > vyres)
1801 		modded.height = vyres - modded.dy;
1802 
1803 	cirrusfb_BitBLT(cinfo->regbase, info->var.bits_per_pixel,
1804 			(area->sx * m) / 8, area->sy,
1805 			(area->dx * m) / 8, area->dy,
1806 			(area->width * m) / 8, area->height,
1807 			info->fix.line_length);
1808 
1809 }
1810 
1811 static void cirrusfb_imageblit(struct fb_info *info,
1812 			       const struct fb_image *image)
1813 {
1814 	struct cirrusfb_info *cinfo = info->par;
1815 	unsigned char op = (info->var.bits_per_pixel == 24) ? 0xc : 0x4;
1816 
1817 	if (info->state != FBINFO_STATE_RUNNING)
1818 		return;
1819 	/* Alpine/SD64 does not work at 24bpp ??? */
1820 	if (info->flags & FBINFO_HWACCEL_DISABLED || image->depth != 1)
1821 		cfb_imageblit(info, image);
1822 	else if ((cinfo->btype == BT_ALPINE || cinfo->btype == BT_SD64) &&
1823 		  op == 0xc)
1824 		cfb_imageblit(info, image);
1825 	else {
1826 		unsigned size = ((image->width + 7) >> 3) * image->height;
1827 		int m = info->var.bits_per_pixel;
1828 		u32 fg, bg;
1829 
1830 		if (info->var.bits_per_pixel == 8) {
1831 			fg = image->fg_color;
1832 			bg = image->bg_color;
1833 		} else {
1834 			fg = ((u32 *)(info->pseudo_palette))[image->fg_color];
1835 			bg = ((u32 *)(info->pseudo_palette))[image->bg_color];
1836 		}
1837 		if (info->var.bits_per_pixel == 24) {
1838 			/* clear background first */
1839 			cirrusfb_RectFill(cinfo->regbase,
1840 					  info->var.bits_per_pixel,
1841 					  (image->dx * m) / 8, image->dy,
1842 					  (image->width * m) / 8,
1843 					  image->height,
1844 					  bg, bg,
1845 					  info->fix.line_length, 0x40);
1846 		}
1847 		cirrusfb_RectFill(cinfo->regbase,
1848 				  info->var.bits_per_pixel,
1849 				  (image->dx * m) / 8, image->dy,
1850 				  (image->width * m) / 8, image->height,
1851 				  fg, bg,
1852 				  info->fix.line_length, op);
1853 		memcpy(info->screen_base, image->data, size);
1854 	}
1855 }
1856 
1857 #ifdef CONFIG_PCI
1858 static int release_io_ports;
1859 
1860 /* Pulled the logic from XFree86 Cirrus driver to get the memory size,
1861  * based on the DRAM bandwidth bit and DRAM bank switching bit.  This
1862  * works with 1MB, 2MB and 4MB configurations (which the Motorola boards
1863  * seem to have. */
1864 static unsigned int cirrusfb_get_memsize(struct fb_info *info,
1865 					 u8 __iomem *regbase)
1866 {
1867 	unsigned long mem;
1868 	struct cirrusfb_info *cinfo = info->par;
1869 
1870 	if (is_laguna(cinfo)) {
1871 		unsigned char SR14 = vga_rseq(regbase, CL_SEQR14);
1872 
1873 		mem = ((SR14 & 7) + 1) << 20;
1874 	} else {
1875 		unsigned char SRF = vga_rseq(regbase, CL_SEQRF);
1876 		switch ((SRF & 0x18)) {
1877 		case 0x08:
1878 			mem = 512 * 1024;
1879 			break;
1880 		case 0x10:
1881 			mem = 1024 * 1024;
1882 			break;
1883 		/* 64-bit DRAM data bus width; assume 2MB.
1884 		 * Also indicates 2MB memory on the 5430.
1885 		 */
1886 		case 0x18:
1887 			mem = 2048 * 1024;
1888 			break;
1889 		default:
1890 			dev_warn(info->device, "Unknown memory size!\n");
1891 			mem = 1024 * 1024;
1892 		}
1893 		/* If DRAM bank switching is enabled, there must be
1894 		 * twice as much memory installed. (4MB on the 5434)
1895 		 */
1896 		if (cinfo->btype != BT_ALPINE && (SRF & 0x80) != 0)
1897 			mem *= 2;
1898 	}
1899 
1900 	/* TODO: Handling of GD5446/5480 (see XF86 sources ...) */
1901 	return mem;
1902 }
1903 
1904 static void get_pci_addrs(const struct pci_dev *pdev,
1905 			  unsigned long *display, unsigned long *registers)
1906 {
1907 	assert(pdev != NULL);
1908 	assert(display != NULL);
1909 	assert(registers != NULL);
1910 
1911 	*display = 0;
1912 	*registers = 0;
1913 
1914 	/* This is a best-guess for now */
1915 
1916 	if (pci_resource_flags(pdev, 0) & IORESOURCE_IO) {
1917 		*display = pci_resource_start(pdev, 1);
1918 		*registers = pci_resource_start(pdev, 0);
1919 	} else {
1920 		*display = pci_resource_start(pdev, 0);
1921 		*registers = pci_resource_start(pdev, 1);
1922 	}
1923 
1924 	assert(*display != 0);
1925 }
1926 
1927 static void cirrusfb_pci_unmap(struct fb_info *info)
1928 {
1929 	struct pci_dev *pdev = to_pci_dev(info->device);
1930 	struct cirrusfb_info *cinfo = info->par;
1931 
1932 	if (cinfo->laguna_mmio == NULL)
1933 		iounmap(cinfo->laguna_mmio);
1934 	iounmap(info->screen_base);
1935 #if 0 /* if system didn't claim this region, we would... */
1936 	release_mem_region(0xA0000, 65535);
1937 #endif
1938 	if (release_io_ports)
1939 		release_region(0x3C0, 32);
1940 	pci_release_regions(pdev);
1941 }
1942 #endif /* CONFIG_PCI */
1943 
1944 #ifdef CONFIG_ZORRO
1945 static void cirrusfb_zorro_unmap(struct fb_info *info)
1946 {
1947 	struct cirrusfb_info *cinfo = info->par;
1948 	struct zorro_dev *zdev = to_zorro_dev(info->device);
1949 
1950 	if (info->fix.smem_start > 16 * MB_)
1951 		iounmap(info->screen_base);
1952 	if (info->fix.mmio_start > 16 * MB_)
1953 		iounmap(cinfo->regbase);
1954 
1955 	zorro_release_device(zdev);
1956 }
1957 #endif /* CONFIG_ZORRO */
1958 
1959 /* function table of the above functions */
1960 static const struct fb_ops cirrusfb_ops = {
1961 	.owner		= THIS_MODULE,
1962 	.fb_open	= cirrusfb_open,
1963 	.fb_release	= cirrusfb_release,
1964 	.fb_setcolreg	= cirrusfb_setcolreg,
1965 	.fb_check_var	= cirrusfb_check_var,
1966 	.fb_set_par	= cirrusfb_set_par,
1967 	.fb_pan_display = cirrusfb_pan_display,
1968 	.fb_blank	= cirrusfb_blank,
1969 	.fb_fillrect	= cirrusfb_fillrect,
1970 	.fb_copyarea	= cirrusfb_copyarea,
1971 	.fb_sync	= cirrusfb_sync,
1972 	.fb_imageblit	= cirrusfb_imageblit,
1973 };
1974 
1975 static int cirrusfb_set_fbinfo(struct fb_info *info)
1976 {
1977 	struct cirrusfb_info *cinfo = info->par;
1978 	struct fb_var_screeninfo *var = &info->var;
1979 
1980 	info->pseudo_palette = cinfo->pseudo_palette;
1981 	info->flags = FBINFO_DEFAULT
1982 		    | FBINFO_HWACCEL_XPAN
1983 		    | FBINFO_HWACCEL_YPAN
1984 		    | FBINFO_HWACCEL_FILLRECT
1985 		    | FBINFO_HWACCEL_IMAGEBLIT
1986 		    | FBINFO_HWACCEL_COPYAREA;
1987 	if (noaccel || is_laguna(cinfo)) {
1988 		info->flags |= FBINFO_HWACCEL_DISABLED;
1989 		info->fix.accel = FB_ACCEL_NONE;
1990 	} else
1991 		info->fix.accel = FB_ACCEL_CIRRUS_ALPINE;
1992 
1993 	info->fbops = &cirrusfb_ops;
1994 
1995 	if (cinfo->btype == BT_GD5480) {
1996 		if (var->bits_per_pixel == 16)
1997 			info->screen_base += 1 * MB_;
1998 		if (var->bits_per_pixel == 32)
1999 			info->screen_base += 2 * MB_;
2000 	}
2001 
2002 	/* Fill fix common fields */
2003 	strscpy(info->fix.id, cirrusfb_board_info[cinfo->btype].name,
2004 		sizeof(info->fix.id));
2005 
2006 	/* monochrome: only 1 memory plane */
2007 	/* 8 bit and above: Use whole memory area */
2008 	info->fix.smem_len   = info->screen_size;
2009 	if (var->bits_per_pixel == 1)
2010 		info->fix.smem_len /= 4;
2011 	info->fix.type_aux   = 0;
2012 	info->fix.xpanstep   = 1;
2013 	info->fix.ypanstep   = 1;
2014 	info->fix.ywrapstep  = 0;
2015 
2016 	/* FIXME: map region at 0xB8000 if available, fill in here */
2017 	info->fix.mmio_len   = 0;
2018 
2019 	fb_alloc_cmap(&info->cmap, 256, 0);
2020 
2021 	return 0;
2022 }
2023 
2024 static int cirrusfb_register(struct fb_info *info)
2025 {
2026 	struct cirrusfb_info *cinfo = info->par;
2027 	int err;
2028 
2029 	/* sanity checks */
2030 	assert(cinfo->btype != BT_NONE);
2031 
2032 	/* set all the vital stuff */
2033 	cirrusfb_set_fbinfo(info);
2034 
2035 	dev_dbg(info->device, "(RAM start set to: 0x%p)\n", info->screen_base);
2036 
2037 	err = fb_find_mode(&info->var, info, mode_option, NULL, 0, NULL, 8);
2038 	if (!err) {
2039 		dev_dbg(info->device, "wrong initial video mode\n");
2040 		err = -EINVAL;
2041 		goto err_dealloc_cmap;
2042 	}
2043 
2044 	info->var.activate = FB_ACTIVATE_NOW;
2045 
2046 	err = cirrusfb_check_var(&info->var, info);
2047 	if (err < 0) {
2048 		/* should never happen */
2049 		dev_dbg(info->device,
2050 			"choking on default var... umm, no good.\n");
2051 		goto err_dealloc_cmap;
2052 	}
2053 
2054 	err = register_framebuffer(info);
2055 	if (err < 0) {
2056 		dev_err(info->device,
2057 			"could not register fb device; err = %d!\n", err);
2058 		goto err_dealloc_cmap;
2059 	}
2060 
2061 	return 0;
2062 
2063 err_dealloc_cmap:
2064 	fb_dealloc_cmap(&info->cmap);
2065 	return err;
2066 }
2067 
2068 static void cirrusfb_cleanup(struct fb_info *info)
2069 {
2070 	struct cirrusfb_info *cinfo = info->par;
2071 
2072 	switch_monitor(cinfo, 0);
2073 	unregister_framebuffer(info);
2074 	fb_dealloc_cmap(&info->cmap);
2075 	dev_dbg(info->device, "Framebuffer unregistered\n");
2076 	cinfo->unmap(info);
2077 	framebuffer_release(info);
2078 }
2079 
2080 #ifdef CONFIG_PCI
2081 static int cirrusfb_pci_register(struct pci_dev *pdev,
2082 				 const struct pci_device_id *ent)
2083 {
2084 	struct cirrusfb_info *cinfo;
2085 	struct fb_info *info;
2086 	unsigned long board_addr, board_size;
2087 	int ret;
2088 
2089 	ret = aperture_remove_conflicting_pci_devices(pdev, "cirrusfb");
2090 	if (ret)
2091 		return ret;
2092 
2093 	ret = pci_enable_device(pdev);
2094 	if (ret < 0) {
2095 		printk(KERN_ERR "cirrusfb: Cannot enable PCI device\n");
2096 		goto err_out;
2097 	}
2098 
2099 	info = framebuffer_alloc(sizeof(struct cirrusfb_info), &pdev->dev);
2100 	if (!info) {
2101 		ret = -ENOMEM;
2102 		goto err_out;
2103 	}
2104 
2105 	cinfo = info->par;
2106 	cinfo->btype = (enum cirrus_board) ent->driver_data;
2107 
2108 	dev_dbg(info->device,
2109 		" Found PCI device, base address 0 is 0x%Lx, btype set to %d\n",
2110 		(unsigned long long)pdev->resource[0].start,  cinfo->btype);
2111 	dev_dbg(info->device, " base address 1 is 0x%Lx\n",
2112 		(unsigned long long)pdev->resource[1].start);
2113 
2114 	dev_dbg(info->device,
2115 		"Attempt to get PCI info for Cirrus Graphics Card\n");
2116 	get_pci_addrs(pdev, &board_addr, &info->fix.mmio_start);
2117 	/* FIXME: this forces VGA.  alternatives? */
2118 	cinfo->regbase = NULL;
2119 	cinfo->laguna_mmio = ioremap(info->fix.mmio_start, 0x1000);
2120 
2121 	dev_dbg(info->device, "Board address: 0x%lx, register address: 0x%lx\n",
2122 		board_addr, info->fix.mmio_start);
2123 
2124 	board_size = (cinfo->btype == BT_GD5480) ?
2125 		32 * MB_ : cirrusfb_get_memsize(info, cinfo->regbase);
2126 
2127 	ret = pci_request_regions(pdev, "cirrusfb");
2128 	if (ret < 0) {
2129 		dev_err(info->device, "cannot reserve region 0x%lx, abort\n",
2130 			board_addr);
2131 		goto err_release_fb;
2132 	}
2133 #if 0 /* if the system didn't claim this region, we would... */
2134 	if (!request_mem_region(0xA0000, 65535, "cirrusfb")) {
2135 		dev_err(info->device, "cannot reserve region 0x%lx, abort\n",
2136 			0xA0000L);
2137 		ret = -EBUSY;
2138 		goto err_release_regions;
2139 	}
2140 #endif
2141 	if (request_region(0x3C0, 32, "cirrusfb"))
2142 		release_io_ports = 1;
2143 
2144 	info->screen_base = ioremap(board_addr, board_size);
2145 	if (!info->screen_base) {
2146 		ret = -EIO;
2147 		goto err_release_legacy;
2148 	}
2149 
2150 	info->fix.smem_start = board_addr;
2151 	info->screen_size = board_size;
2152 	cinfo->unmap = cirrusfb_pci_unmap;
2153 
2154 	dev_info(info->device,
2155 		 "Cirrus Logic chipset on PCI bus, RAM (%lu kB) at 0x%lx\n",
2156 		 info->screen_size >> 10, board_addr);
2157 	pci_set_drvdata(pdev, info);
2158 
2159 	ret = cirrusfb_register(info);
2160 	if (!ret)
2161 		return 0;
2162 
2163 	iounmap(info->screen_base);
2164 err_release_legacy:
2165 	if (release_io_ports)
2166 		release_region(0x3C0, 32);
2167 #if 0
2168 	release_mem_region(0xA0000, 65535);
2169 err_release_regions:
2170 #endif
2171 	pci_release_regions(pdev);
2172 err_release_fb:
2173 	if (cinfo->laguna_mmio != NULL)
2174 		iounmap(cinfo->laguna_mmio);
2175 	framebuffer_release(info);
2176 err_out:
2177 	return ret;
2178 }
2179 
2180 static void cirrusfb_pci_unregister(struct pci_dev *pdev)
2181 {
2182 	struct fb_info *info = pci_get_drvdata(pdev);
2183 
2184 	cirrusfb_cleanup(info);
2185 }
2186 
2187 static struct pci_driver cirrusfb_pci_driver = {
2188 	.name		= "cirrusfb",
2189 	.id_table	= cirrusfb_pci_table,
2190 	.probe		= cirrusfb_pci_register,
2191 	.remove		= cirrusfb_pci_unregister,
2192 };
2193 #endif /* CONFIG_PCI */
2194 
2195 #ifdef CONFIG_ZORRO
2196 static int cirrusfb_zorro_register(struct zorro_dev *z,
2197 				   const struct zorro_device_id *ent)
2198 {
2199 	struct fb_info *info;
2200 	int error;
2201 	const struct zorrocl *zcl;
2202 	enum cirrus_board btype;
2203 	unsigned long regbase, ramsize, rambase;
2204 	struct cirrusfb_info *cinfo;
2205 
2206 	info = framebuffer_alloc(sizeof(struct cirrusfb_info), &z->dev);
2207 	if (!info)
2208 		return -ENOMEM;
2209 
2210 	zcl = (const struct zorrocl *)ent->driver_data;
2211 	btype = zcl->type;
2212 	regbase = zorro_resource_start(z) + zcl->regoffset;
2213 	ramsize = zcl->ramsize;
2214 	if (ramsize) {
2215 		rambase = zorro_resource_start(z) + zcl->ramoffset;
2216 		if (zorro_resource_len(z) == 64 * MB_) {
2217 			/* Quirk for 64 MiB Picasso IV */
2218 			rambase += zcl->ramoffset;
2219 		}
2220 	} else {
2221 		struct zorro_dev *ram = zorro_find_device(zcl->ramid, NULL);
2222 		if (!ram || !zorro_resource_len(ram)) {
2223 			dev_err(info->device, "No video RAM found\n");
2224 			error = -ENODEV;
2225 			goto err_release_fb;
2226 		}
2227 		rambase = zorro_resource_start(ram);
2228 		ramsize = zorro_resource_len(ram);
2229 		if (zcl->ramid2 &&
2230 		    (ram = zorro_find_device(zcl->ramid2, NULL))) {
2231 			if (zorro_resource_start(ram) != rambase + ramsize) {
2232 				dev_warn(info->device,
2233 					 "Skipping non-contiguous RAM at %pR\n",
2234 					 &ram->resource);
2235 			} else {
2236 				ramsize += zorro_resource_len(ram);
2237 			}
2238 		}
2239 	}
2240 
2241 	dev_info(info->device,
2242 		 "%s board detected, REG at 0x%lx, %lu MiB RAM at 0x%lx\n",
2243 		 cirrusfb_board_info[btype].name, regbase, ramsize / MB_,
2244 		 rambase);
2245 
2246 	if (!zorro_request_device(z, "cirrusfb")) {
2247 		dev_err(info->device, "Cannot reserve %pR\n", &z->resource);
2248 		error = -EBUSY;
2249 		goto err_release_fb;
2250 	}
2251 
2252 	cinfo = info->par;
2253 	cinfo->btype = btype;
2254 
2255 	info->fix.mmio_start = regbase;
2256 	cinfo->regbase = regbase > 16 * MB_ ? ioremap(regbase, 64 * 1024)
2257 					    : ZTWO_VADDR(regbase);
2258 	if (!cinfo->regbase) {
2259 		dev_err(info->device, "Cannot map registers\n");
2260 		error = -EIO;
2261 		goto err_release_dev;
2262 	}
2263 
2264 	info->fix.smem_start = rambase;
2265 	info->screen_size = ramsize;
2266 	info->screen_base = rambase > 16 * MB_ ? ioremap(rambase, ramsize)
2267 					       : ZTWO_VADDR(rambase);
2268 	if (!info->screen_base) {
2269 		dev_err(info->device, "Cannot map video RAM\n");
2270 		error = -EIO;
2271 		goto err_unmap_reg;
2272 	}
2273 
2274 	cinfo->unmap = cirrusfb_zorro_unmap;
2275 
2276 	dev_info(info->device,
2277 		 "Cirrus Logic chipset on Zorro bus, RAM (%lu MiB) at 0x%lx\n",
2278 		 ramsize / MB_, rambase);
2279 
2280 	/* MCLK select etc. */
2281 	if (cirrusfb_board_info[btype].init_sr1f)
2282 		vga_wseq(cinfo->regbase, CL_SEQR1F,
2283 			 cirrusfb_board_info[btype].sr1f);
2284 
2285 	error = cirrusfb_register(info);
2286 	if (error) {
2287 		dev_err(info->device, "Failed to register device, error %d\n",
2288 			error);
2289 		goto err_unmap_ram;
2290 	}
2291 
2292 	zorro_set_drvdata(z, info);
2293 	return 0;
2294 
2295 err_unmap_ram:
2296 	if (rambase > 16 * MB_)
2297 		iounmap(info->screen_base);
2298 
2299 err_unmap_reg:
2300 	if (regbase > 16 * MB_)
2301 		iounmap(cinfo->regbase);
2302 err_release_dev:
2303 	zorro_release_device(z);
2304 err_release_fb:
2305 	framebuffer_release(info);
2306 	return error;
2307 }
2308 
2309 static void cirrusfb_zorro_unregister(struct zorro_dev *z)
2310 {
2311 	struct fb_info *info = zorro_get_drvdata(z);
2312 
2313 	cirrusfb_cleanup(info);
2314 	zorro_set_drvdata(z, NULL);
2315 }
2316 
2317 static struct zorro_driver cirrusfb_zorro_driver = {
2318 	.name		= "cirrusfb",
2319 	.id_table	= cirrusfb_zorro_table,
2320 	.probe		= cirrusfb_zorro_register,
2321 	.remove		= cirrusfb_zorro_unregister,
2322 };
2323 #endif /* CONFIG_ZORRO */
2324 
2325 #ifndef MODULE
2326 static int __init cirrusfb_setup(char *options)
2327 {
2328 	char *this_opt;
2329 
2330 	if (!options || !*options)
2331 		return 0;
2332 
2333 	while ((this_opt = strsep(&options, ",")) != NULL) {
2334 		if (!*this_opt)
2335 			continue;
2336 
2337 		if (!strcmp(this_opt, "noaccel"))
2338 			noaccel = 1;
2339 		else if (!strncmp(this_opt, "mode:", 5))
2340 			mode_option = this_opt + 5;
2341 		else
2342 			mode_option = this_opt;
2343 	}
2344 	return 0;
2345 }
2346 #endif
2347 
2348     /*
2349      *  Modularization
2350      */
2351 
2352 MODULE_AUTHOR("Copyright 1999,2000 Jeff Garzik <jgarzik@pobox.com>");
2353 MODULE_DESCRIPTION("Accelerated FBDev driver for Cirrus Logic chips");
2354 MODULE_LICENSE("GPL");
2355 
2356 static int __init cirrusfb_init(void)
2357 {
2358 	int error = 0;
2359 
2360 #ifndef MODULE
2361 	char *option = NULL;
2362 #endif
2363 
2364 	if (fb_modesetting_disabled("cirrusfb"))
2365 		return -ENODEV;
2366 
2367 #ifndef MODULE
2368 	if (fb_get_options("cirrusfb", &option))
2369 		return -ENODEV;
2370 	cirrusfb_setup(option);
2371 #endif
2372 
2373 #ifdef CONFIG_ZORRO
2374 	error |= zorro_register_driver(&cirrusfb_zorro_driver);
2375 #endif
2376 #ifdef CONFIG_PCI
2377 	error |= pci_register_driver(&cirrusfb_pci_driver);
2378 #endif
2379 	return error;
2380 }
2381 
2382 static void __exit cirrusfb_exit(void)
2383 {
2384 #ifdef CONFIG_PCI
2385 	pci_unregister_driver(&cirrusfb_pci_driver);
2386 #endif
2387 #ifdef CONFIG_ZORRO
2388 	zorro_unregister_driver(&cirrusfb_zorro_driver);
2389 #endif
2390 }
2391 
2392 module_init(cirrusfb_init);
2393 
2394 module_param(mode_option, charp, 0);
2395 MODULE_PARM_DESC(mode_option, "Initial video mode e.g. '648x480-8@60'");
2396 module_param(noaccel, bool, 0);
2397 MODULE_PARM_DESC(noaccel, "Disable acceleration");
2398 
2399 #ifdef MODULE
2400 module_exit(cirrusfb_exit);
2401 #endif
2402 
2403 /**********************************************************************/
2404 /* about the following functions - I have used the same names for the */
2405 /* functions as Markus Wild did in his Retina driver for NetBSD as    */
2406 /* they just made sense for this purpose. Apart from that, I wrote    */
2407 /* these functions myself.					    */
2408 /**********************************************************************/
2409 
2410 /*** WGen() - write into one of the external/general registers ***/
2411 static void WGen(const struct cirrusfb_info *cinfo,
2412 		  int regnum, unsigned char val)
2413 {
2414 	unsigned long regofs = 0;
2415 
2416 	if (cinfo->btype == BT_PICASSO) {
2417 		/* Picasso II specific hack */
2418 /*	      if (regnum == VGA_PEL_IR || regnum == VGA_PEL_D ||
2419 		  regnum == CL_VSSM2) */
2420 		if (regnum == VGA_PEL_IR || regnum == VGA_PEL_D)
2421 			regofs = 0xfff;
2422 	}
2423 
2424 	vga_w(cinfo->regbase, regofs + regnum, val);
2425 }
2426 
2427 /*** RGen() - read out one of the external/general registers ***/
2428 static unsigned char RGen(const struct cirrusfb_info *cinfo, int regnum)
2429 {
2430 	unsigned long regofs = 0;
2431 
2432 	if (cinfo->btype == BT_PICASSO) {
2433 		/* Picasso II specific hack */
2434 /*	      if (regnum == VGA_PEL_IR || regnum == VGA_PEL_D ||
2435 		  regnum == CL_VSSM2) */
2436 		if (regnum == VGA_PEL_IR || regnum == VGA_PEL_D)
2437 			regofs = 0xfff;
2438 	}
2439 
2440 	return vga_r(cinfo->regbase, regofs + regnum);
2441 }
2442 
2443 /*** AttrOn() - turn on VideoEnable for Attribute controller ***/
2444 static void AttrOn(const struct cirrusfb_info *cinfo)
2445 {
2446 	assert(cinfo != NULL);
2447 
2448 	if (vga_rcrt(cinfo->regbase, CL_CRT24) & 0x80) {
2449 		/* if we're just in "write value" mode, write back the */
2450 		/* same value as before to not modify anything */
2451 		vga_w(cinfo->regbase, VGA_ATT_IW,
2452 		      vga_r(cinfo->regbase, VGA_ATT_R));
2453 	}
2454 	/* turn on video bit */
2455 /*      vga_w(cinfo->regbase, VGA_ATT_IW, 0x20); */
2456 	vga_w(cinfo->regbase, VGA_ATT_IW, 0x33);
2457 
2458 	/* dummy write on Reg0 to be on "write index" mode next time */
2459 	vga_w(cinfo->regbase, VGA_ATT_IW, 0x00);
2460 }
2461 
2462 /*** WHDR() - write into the Hidden DAC register ***/
2463 /* as the HDR is the only extension register that requires special treatment
2464  * (the other extension registers are accessible just like the "ordinary"
2465  * registers of their functional group) here is a specialized routine for
2466  * accessing the HDR
2467  */
2468 static void WHDR(const struct cirrusfb_info *cinfo, unsigned char val)
2469 {
2470 	if (is_laguna(cinfo))
2471 		return;
2472 	if (cinfo->btype == BT_PICASSO) {
2473 		/* Klaus' hint for correct access to HDR on some boards */
2474 		/* first write 0 to pixel mask (3c6) */
2475 		WGen(cinfo, VGA_PEL_MSK, 0x00);
2476 		udelay(200);
2477 		/* next read dummy from pixel address (3c8) */
2478 		RGen(cinfo, VGA_PEL_IW);
2479 		udelay(200);
2480 	}
2481 	/* now do the usual stuff to access the HDR */
2482 
2483 	RGen(cinfo, VGA_PEL_MSK);
2484 	udelay(200);
2485 	RGen(cinfo, VGA_PEL_MSK);
2486 	udelay(200);
2487 	RGen(cinfo, VGA_PEL_MSK);
2488 	udelay(200);
2489 	RGen(cinfo, VGA_PEL_MSK);
2490 	udelay(200);
2491 
2492 	WGen(cinfo, VGA_PEL_MSK, val);
2493 	udelay(200);
2494 
2495 	if (cinfo->btype == BT_PICASSO) {
2496 		/* now first reset HDR access counter */
2497 		RGen(cinfo, VGA_PEL_IW);
2498 		udelay(200);
2499 
2500 		/* and at the end, restore the mask value */
2501 		/* ## is this mask always 0xff? */
2502 		WGen(cinfo, VGA_PEL_MSK, 0xff);
2503 		udelay(200);
2504 	}
2505 }
2506 
2507 /*** WSFR() - write to the "special function register" (SFR) ***/
2508 static void WSFR(struct cirrusfb_info *cinfo, unsigned char val)
2509 {
2510 #ifdef CONFIG_ZORRO
2511 	assert(cinfo->regbase != NULL);
2512 	cinfo->SFR = val;
2513 	z_writeb(val, cinfo->regbase + 0x8000);
2514 #endif
2515 }
2516 
2517 /* The Picasso has a second register for switching the monitor bit */
2518 static void WSFR2(struct cirrusfb_info *cinfo, unsigned char val)
2519 {
2520 #ifdef CONFIG_ZORRO
2521 	/* writing an arbitrary value to this one causes the monitor switcher */
2522 	/* to flip to Amiga display */
2523 	assert(cinfo->regbase != NULL);
2524 	cinfo->SFR = val;
2525 	z_writeb(val, cinfo->regbase + 0x9000);
2526 #endif
2527 }
2528 
2529 /*** WClut - set CLUT entry (range: 0..63) ***/
2530 static void WClut(struct cirrusfb_info *cinfo, unsigned char regnum, unsigned char red,
2531 	    unsigned char green, unsigned char blue)
2532 {
2533 	unsigned int data = VGA_PEL_D;
2534 
2535 	/* address write mode register is not translated.. */
2536 	vga_w(cinfo->regbase, VGA_PEL_IW, regnum);
2537 
2538 	if (cinfo->btype == BT_PICASSO || cinfo->btype == BT_PICASSO4 ||
2539 	    cinfo->btype == BT_ALPINE || cinfo->btype == BT_GD5480 ||
2540 	    cinfo->btype == BT_SD64 || is_laguna(cinfo)) {
2541 		/* but DAC data register IS, at least for Picasso II */
2542 		if (cinfo->btype == BT_PICASSO)
2543 			data += 0xfff;
2544 		vga_w(cinfo->regbase, data, red);
2545 		vga_w(cinfo->regbase, data, green);
2546 		vga_w(cinfo->regbase, data, blue);
2547 	} else {
2548 		vga_w(cinfo->regbase, data, blue);
2549 		vga_w(cinfo->regbase, data, green);
2550 		vga_w(cinfo->regbase, data, red);
2551 	}
2552 }
2553 
2554 #if 0
2555 /*** RClut - read CLUT entry (range 0..63) ***/
2556 static void RClut(struct cirrusfb_info *cinfo, unsigned char regnum, unsigned char *red,
2557 	    unsigned char *green, unsigned char *blue)
2558 {
2559 	unsigned int data = VGA_PEL_D;
2560 
2561 	vga_w(cinfo->regbase, VGA_PEL_IR, regnum);
2562 
2563 	if (cinfo->btype == BT_PICASSO || cinfo->btype == BT_PICASSO4 ||
2564 	    cinfo->btype == BT_ALPINE || cinfo->btype == BT_GD5480) {
2565 		if (cinfo->btype == BT_PICASSO)
2566 			data += 0xfff;
2567 		*red = vga_r(cinfo->regbase, data);
2568 		*green = vga_r(cinfo->regbase, data);
2569 		*blue = vga_r(cinfo->regbase, data);
2570 	} else {
2571 		*blue = vga_r(cinfo->regbase, data);
2572 		*green = vga_r(cinfo->regbase, data);
2573 		*red = vga_r(cinfo->regbase, data);
2574 	}
2575 }
2576 #endif
2577 
2578 /*******************************************************************
2579 	cirrusfb_WaitBLT()
2580 
2581 	Wait for the BitBLT engine to complete a possible earlier job
2582 *********************************************************************/
2583 
2584 /* FIXME: use interrupts instead */
2585 static void cirrusfb_WaitBLT(u8 __iomem *regbase)
2586 {
2587 	while (vga_rgfx(regbase, CL_GR31) & 0x08)
2588 		cpu_relax();
2589 }
2590 
2591 /*******************************************************************
2592 	cirrusfb_BitBLT()
2593 
2594 	perform accelerated "scrolling"
2595 ********************************************************************/
2596 
2597 static void cirrusfb_set_blitter(u8 __iomem *regbase,
2598 			    u_short nwidth, u_short nheight,
2599 			    u_long nsrc, u_long ndest,
2600 			    u_short bltmode, u_short line_length)
2601 
2602 {
2603 	/* pitch: set to line_length */
2604 	/* dest pitch low */
2605 	vga_wgfx(regbase, CL_GR24, line_length & 0xff);
2606 	/* dest pitch hi */
2607 	vga_wgfx(regbase, CL_GR25, line_length >> 8);
2608 	/* source pitch low */
2609 	vga_wgfx(regbase, CL_GR26, line_length & 0xff);
2610 	/* source pitch hi */
2611 	vga_wgfx(regbase, CL_GR27, line_length >> 8);
2612 
2613 	/* BLT width: actual number of pixels - 1 */
2614 	/* BLT width low */
2615 	vga_wgfx(regbase, CL_GR20, nwidth & 0xff);
2616 	/* BLT width hi */
2617 	vga_wgfx(regbase, CL_GR21, nwidth >> 8);
2618 
2619 	/* BLT height: actual number of lines -1 */
2620 	/* BLT height low */
2621 	vga_wgfx(regbase, CL_GR22, nheight & 0xff);
2622 	/* BLT width hi */
2623 	vga_wgfx(regbase, CL_GR23, nheight >> 8);
2624 
2625 	/* BLT destination */
2626 	/* BLT dest low */
2627 	vga_wgfx(regbase, CL_GR28, (u_char) (ndest & 0xff));
2628 	/* BLT dest mid */
2629 	vga_wgfx(regbase, CL_GR29, (u_char) (ndest >> 8));
2630 	/* BLT dest hi */
2631 	vga_wgfx(regbase, CL_GR2A, (u_char) (ndest >> 16));
2632 
2633 	/* BLT source */
2634 	/* BLT src low */
2635 	vga_wgfx(regbase, CL_GR2C, (u_char) (nsrc & 0xff));
2636 	/* BLT src mid */
2637 	vga_wgfx(regbase, CL_GR2D, (u_char) (nsrc >> 8));
2638 	/* BLT src hi */
2639 	vga_wgfx(regbase, CL_GR2E, (u_char) (nsrc >> 16));
2640 
2641 	/* BLT mode */
2642 	vga_wgfx(regbase, CL_GR30, bltmode);	/* BLT mode */
2643 
2644 	/* BLT ROP: SrcCopy */
2645 	vga_wgfx(regbase, CL_GR32, 0x0d);	/* BLT ROP */
2646 
2647 	/* and finally: GO! */
2648 	vga_wgfx(regbase, CL_GR31, 0x02);	/* BLT Start/status */
2649 }
2650 
2651 /*******************************************************************
2652 	cirrusfb_BitBLT()
2653 
2654 	perform accelerated "scrolling"
2655 ********************************************************************/
2656 
2657 static void cirrusfb_BitBLT(u8 __iomem *regbase, int bits_per_pixel,
2658 			    u_short curx, u_short cury,
2659 			    u_short destx, u_short desty,
2660 			    u_short width, u_short height,
2661 			    u_short line_length)
2662 {
2663 	u_short nwidth = width - 1;
2664 	u_short nheight = height - 1;
2665 	u_long nsrc, ndest;
2666 	u_char bltmode;
2667 
2668 	bltmode = 0x00;
2669 	/* if source adr < dest addr, do the Blt backwards */
2670 	if (cury <= desty) {
2671 		if (cury == desty) {
2672 			/* if src and dest are on the same line, check x */
2673 			if (curx < destx)
2674 				bltmode |= 0x01;
2675 		} else
2676 			bltmode |= 0x01;
2677 	}
2678 	/* standard case: forward blitting */
2679 	nsrc = (cury * line_length) + curx;
2680 	ndest = (desty * line_length) + destx;
2681 	if (bltmode) {
2682 		/* this means start addresses are at the end,
2683 		 * counting backwards
2684 		 */
2685 		nsrc += nheight * line_length + nwidth;
2686 		ndest += nheight * line_length + nwidth;
2687 	}
2688 
2689 	cirrusfb_WaitBLT(regbase);
2690 
2691 	cirrusfb_set_blitter(regbase, nwidth, nheight,
2692 			    nsrc, ndest, bltmode, line_length);
2693 }
2694 
2695 /*******************************************************************
2696 	cirrusfb_RectFill()
2697 
2698 	perform accelerated rectangle fill
2699 ********************************************************************/
2700 
2701 static void cirrusfb_RectFill(u8 __iomem *regbase, int bits_per_pixel,
2702 		     u_short x, u_short y, u_short width, u_short height,
2703 		     u32 fg_color, u32 bg_color, u_short line_length,
2704 		     u_char blitmode)
2705 {
2706 	u_long ndest = (y * line_length) + x;
2707 	u_char op;
2708 
2709 	cirrusfb_WaitBLT(regbase);
2710 
2711 	/* This is a ColorExpand Blt, using the */
2712 	/* same color for foreground and background */
2713 	vga_wgfx(regbase, VGA_GFX_SR_VALUE, bg_color);
2714 	vga_wgfx(regbase, VGA_GFX_SR_ENABLE, fg_color);
2715 
2716 	op = 0x80;
2717 	if (bits_per_pixel >= 16) {
2718 		vga_wgfx(regbase, CL_GR10, bg_color >> 8);
2719 		vga_wgfx(regbase, CL_GR11, fg_color >> 8);
2720 		op = 0x90;
2721 	}
2722 	if (bits_per_pixel >= 24) {
2723 		vga_wgfx(regbase, CL_GR12, bg_color >> 16);
2724 		vga_wgfx(regbase, CL_GR13, fg_color >> 16);
2725 		op = 0xa0;
2726 	}
2727 	if (bits_per_pixel == 32) {
2728 		vga_wgfx(regbase, CL_GR14, bg_color >> 24);
2729 		vga_wgfx(regbase, CL_GR15, fg_color >> 24);
2730 		op = 0xb0;
2731 	}
2732 	cirrusfb_set_blitter(regbase, width - 1, height - 1,
2733 			    0, ndest, op | blitmode, line_length);
2734 }
2735 
2736 /**************************************************************************
2737  * bestclock() - determine closest possible clock lower(?) than the
2738  * desired pixel clock
2739  **************************************************************************/
2740 static void bestclock(long freq, int *nom, int *den, int *div)
2741 {
2742 	int n, d;
2743 	long h, diff;
2744 
2745 	assert(nom != NULL);
2746 	assert(den != NULL);
2747 	assert(div != NULL);
2748 
2749 	*nom = 0;
2750 	*den = 0;
2751 	*div = 0;
2752 
2753 	if (freq < 8000)
2754 		freq = 8000;
2755 
2756 	diff = freq;
2757 
2758 	for (n = 32; n < 128; n++) {
2759 		int s = 0;
2760 
2761 		d = (14318 * n) / freq;
2762 		if ((d >= 7) && (d <= 63)) {
2763 			int temp = d;
2764 
2765 			if (temp > 31) {
2766 				s = 1;
2767 				temp >>= 1;
2768 			}
2769 			h = ((14318 * n) / temp) >> s;
2770 			h = h > freq ? h - freq : freq - h;
2771 			if (h < diff) {
2772 				diff = h;
2773 				*nom = n;
2774 				*den = temp;
2775 				*div = s;
2776 			}
2777 		}
2778 		d++;
2779 		if ((d >= 7) && (d <= 63)) {
2780 			if (d > 31) {
2781 				s = 1;
2782 				d >>= 1;
2783 			}
2784 			h = ((14318 * n) / d) >> s;
2785 			h = h > freq ? h - freq : freq - h;
2786 			if (h < diff) {
2787 				diff = h;
2788 				*nom = n;
2789 				*den = d;
2790 				*div = s;
2791 			}
2792 		}
2793 	}
2794 }
2795 
2796 /* -------------------------------------------------------------------------
2797  *
2798  * debugging functions
2799  *
2800  * -------------------------------------------------------------------------
2801  */
2802 
2803 #ifdef CIRRUSFB_DEBUG
2804 
2805 /*
2806  * cirrusfb_dbg_print_regs
2807  * @regbase: If using newmmio, the newmmio base address, otherwise %NULL
2808  * @reg_class: type of registers to read: %CRT, or %SEQ
2809  *
2810  * DESCRIPTION:
2811  * Dumps the given list of VGA CRTC registers.  If @base is %NULL,
2812  * old-style I/O ports are queried for information, otherwise MMIO is
2813  * used at the given @base address to query the information.
2814  */
2815 
2816 static void cirrusfb_dbg_print_regs(struct fb_info *info,
2817 				    caddr_t regbase,
2818 				    enum cirrusfb_dbg_reg_class reg_class, ...)
2819 {
2820 	va_list list;
2821 	unsigned char val = 0;
2822 	unsigned reg;
2823 	char *name;
2824 
2825 	va_start(list, reg_class);
2826 
2827 	name = va_arg(list, char *);
2828 	while (name != NULL) {
2829 		reg = va_arg(list, int);
2830 
2831 		switch (reg_class) {
2832 		case CRT:
2833 			val = vga_rcrt(regbase, (unsigned char) reg);
2834 			break;
2835 		case SEQ:
2836 			val = vga_rseq(regbase, (unsigned char) reg);
2837 			break;
2838 		default:
2839 			/* should never occur */
2840 			assert(false);
2841 			break;
2842 		}
2843 
2844 		dev_dbg(info->device, "%8s = 0x%02X\n", name, val);
2845 
2846 		name = va_arg(list, char *);
2847 	}
2848 
2849 	va_end(list);
2850 }
2851 
2852 /*
2853  * cirrusfb_dbg_reg_dump
2854  * @base: If using newmmio, the newmmio base address, otherwise %NULL
2855  *
2856  * DESCRIPTION:
2857  * Dumps a list of interesting VGA and CIRRUSFB registers.  If @base is %NULL,
2858  * old-style I/O ports are queried for information, otherwise MMIO is
2859  * used at the given @base address to query the information.
2860  */
2861 
2862 static void cirrusfb_dbg_reg_dump(struct fb_info *info, caddr_t regbase)
2863 {
2864 	dev_dbg(info->device, "VGA CRTC register dump:\n");
2865 
2866 	cirrusfb_dbg_print_regs(info, regbase, CRT,
2867 			   "CR00", 0x00,
2868 			   "CR01", 0x01,
2869 			   "CR02", 0x02,
2870 			   "CR03", 0x03,
2871 			   "CR04", 0x04,
2872 			   "CR05", 0x05,
2873 			   "CR06", 0x06,
2874 			   "CR07", 0x07,
2875 			   "CR08", 0x08,
2876 			   "CR09", 0x09,
2877 			   "CR0A", 0x0A,
2878 			   "CR0B", 0x0B,
2879 			   "CR0C", 0x0C,
2880 			   "CR0D", 0x0D,
2881 			   "CR0E", 0x0E,
2882 			   "CR0F", 0x0F,
2883 			   "CR10", 0x10,
2884 			   "CR11", 0x11,
2885 			   "CR12", 0x12,
2886 			   "CR13", 0x13,
2887 			   "CR14", 0x14,
2888 			   "CR15", 0x15,
2889 			   "CR16", 0x16,
2890 			   "CR17", 0x17,
2891 			   "CR18", 0x18,
2892 			   "CR22", 0x22,
2893 			   "CR24", 0x24,
2894 			   "CR26", 0x26,
2895 			   "CR2D", 0x2D,
2896 			   "CR2E", 0x2E,
2897 			   "CR2F", 0x2F,
2898 			   "CR30", 0x30,
2899 			   "CR31", 0x31,
2900 			   "CR32", 0x32,
2901 			   "CR33", 0x33,
2902 			   "CR34", 0x34,
2903 			   "CR35", 0x35,
2904 			   "CR36", 0x36,
2905 			   "CR37", 0x37,
2906 			   "CR38", 0x38,
2907 			   "CR39", 0x39,
2908 			   "CR3A", 0x3A,
2909 			   "CR3B", 0x3B,
2910 			   "CR3C", 0x3C,
2911 			   "CR3D", 0x3D,
2912 			   "CR3E", 0x3E,
2913 			   "CR3F", 0x3F,
2914 			   NULL);
2915 
2916 	dev_dbg(info->device, "\n");
2917 
2918 	dev_dbg(info->device, "VGA SEQ register dump:\n");
2919 
2920 	cirrusfb_dbg_print_regs(info, regbase, SEQ,
2921 			   "SR00", 0x00,
2922 			   "SR01", 0x01,
2923 			   "SR02", 0x02,
2924 			   "SR03", 0x03,
2925 			   "SR04", 0x04,
2926 			   "SR08", 0x08,
2927 			   "SR09", 0x09,
2928 			   "SR0A", 0x0A,
2929 			   "SR0B", 0x0B,
2930 			   "SR0D", 0x0D,
2931 			   "SR10", 0x10,
2932 			   "SR11", 0x11,
2933 			   "SR12", 0x12,
2934 			   "SR13", 0x13,
2935 			   "SR14", 0x14,
2936 			   "SR15", 0x15,
2937 			   "SR16", 0x16,
2938 			   "SR17", 0x17,
2939 			   "SR18", 0x18,
2940 			   "SR19", 0x19,
2941 			   "SR1A", 0x1A,
2942 			   "SR1B", 0x1B,
2943 			   "SR1C", 0x1C,
2944 			   "SR1D", 0x1D,
2945 			   "SR1E", 0x1E,
2946 			   "SR1F", 0x1F,
2947 			   NULL);
2948 
2949 	dev_dbg(info->device, "\n");
2950 }
2951 
2952 #endif				/* CIRRUSFB_DEBUG */
2953 
2954