/*
 *
 * tdfxfb.c
 *
 * Author: Hannu Mallat <hmallat@cc.hut.fi>
 *
 * Copyright © 1999 Hannu Mallat
 * All rights reserved
 *
 * Created      : Thu Sep 23 18:17:43 1999, hmallat
 * Last modified: Tue Nov  2 21:19:47 1999, hmallat
 *
 * Lots of the information here comes from the Daryll Strauss' Banshee
 * patches to the XF86 server, and the rest comes from the 3dfx
 * Banshee specification. I'm very much indebted to Daryll for his
 * work on the X server.
 *
 * Voodoo3 support was contributed Harold Oga. Lots of additions
 * (proper acceleration, 24 bpp, hardware cursor) and bug fixes by Attila
 * Kesmarki. Thanks guys!
 *
 * Voodoo1 and Voodoo2 support aren't relevant to this driver as they
 * behave very differently from the Voodoo3/4/5. For anyone wanting to
 * use frame buffer on the Voodoo1/2, see the sstfb driver (which is
 * located at http://www.sourceforge.net/projects/sstfb).
 *
 * While I _am_ grateful to 3Dfx for releasing the specs for Banshee,
 * I do wish the next version is a bit more complete. Without the XF86
 * patches I couldn't have gotten even this far... for instance, the
 * extensions to the VGA register set go completely unmentioned in the
 * spec! Also, lots of references are made to the 'SST core', but no
 * spec is publicly available, AFAIK.
 *
 * The structure of this driver comes pretty much from the Permedia
 * driver by Ilario Nardinocchi, which in turn is based on skeletonfb.
 *
 * TODO:
 * - multihead support (basically need to support an array of fb_infos)
 * - support other architectures (PPC, Alpha); does the fact that the VGA
 *   core can be accessed only thru I/O (not memory mapped) complicate
 *   things?
 *
 * Version history:
 *
 * 0.1.4 (released 2002-05-28)	ported over to new fbdev api by James Simmons
 *
 * 0.1.3 (released 1999-11-02)	added Attila's panning support, code
 *				reorg, hwcursor address page size alignment
 *				(for mmaping both frame buffer and regs),
 *				and my changes to get rid of hardcoded
 *				VGA i/o register locations (uses PCI
 *				configuration info now)
 * 0.1.2 (released 1999-10-19)	added Attila Kesmarki's bug fixes and
 *				improvements
 * 0.1.1 (released 1999-10-07)	added Voodoo3 support by Harold Oga.
 * 0.1.0 (released 1999-10-06)	initial version
 *
 */

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/string.h>
#include <linux/mm.h>
#include <linux/slab.h>
#include <linux/fb.h>
#include <linux/init.h>
#include <linux/pci.h>
#include <asm/io.h>

#include <video/tdfx.h>

#define DPRINTK(a, b...) pr_debug("fb: %s: " a, __func__ , ## b)

#ifdef CONFIG_MTRR
#include <asm/mtrr.h>
#else
/* duplicate asm/mtrr.h defines to work on archs without mtrr */
#define MTRR_TYPE_WRCOMB     1

static inline int mtrr_add(unsigned long base, unsigned long size,
				unsigned int type, char increment)
{
    return -ENODEV;
}
static inline int mtrr_del(int reg, unsigned long base,
				unsigned long size)
{
    return -ENODEV;
}
#endif

#define BANSHEE_MAX_PIXCLOCK 270000
#define VOODOO3_MAX_PIXCLOCK 300000
#define VOODOO5_MAX_PIXCLOCK 350000

static struct fb_fix_screeninfo tdfx_fix __devinitdata = {
	.id =		"3Dfx",
	.type =		FB_TYPE_PACKED_PIXELS,
	.visual =	FB_VISUAL_PSEUDOCOLOR,
	.ypanstep =	1,
	.ywrapstep =	1,
	.accel =	FB_ACCEL_3DFX_BANSHEE
};

static struct fb_var_screeninfo tdfx_var __devinitdata = {
	/* "640x480, 8 bpp @ 60 Hz */
	.xres =		640,
	.yres =		480,
	.xres_virtual =	640,
	.yres_virtual =	1024,
	.bits_per_pixel = 8,
	.red =		{0, 8, 0},
	.blue =		{0, 8, 0},
	.green =	{0, 8, 0},
	.activate =	FB_ACTIVATE_NOW,
	.height =	-1,
	.width =	-1,
	.accel_flags =	FB_ACCELF_TEXT,
	.pixclock =	39722,
	.left_margin =	40,
	.right_margin =	24,
	.upper_margin =	32,
	.lower_margin =	11,
	.hsync_len =	96,
	.vsync_len =	2,
	.vmode =	FB_VMODE_NONINTERLACED
};

/*
 * PCI driver prototypes
 */
static int __devinit tdfxfb_probe(struct pci_dev *pdev,
				  const struct pci_device_id *id);
static void __devexit tdfxfb_remove(struct pci_dev *pdev);

static struct pci_device_id tdfxfb_id_table[] = {
	{ PCI_VENDOR_ID_3DFX, PCI_DEVICE_ID_3DFX_BANSHEE,
	  PCI_ANY_ID, PCI_ANY_ID, PCI_BASE_CLASS_DISPLAY << 16,
	  0xff0000, 0 },
	{ PCI_VENDOR_ID_3DFX, PCI_DEVICE_ID_3DFX_VOODOO3,
	  PCI_ANY_ID, PCI_ANY_ID, PCI_BASE_CLASS_DISPLAY << 16,
	  0xff0000, 0 },
	{ PCI_VENDOR_ID_3DFX, PCI_DEVICE_ID_3DFX_VOODOO5,
	  PCI_ANY_ID, PCI_ANY_ID, PCI_BASE_CLASS_DISPLAY << 16,
	  0xff0000, 0 },
	{ 0, }
};

static struct pci_driver tdfxfb_driver = {
	.name		= "tdfxfb",
	.id_table	= tdfxfb_id_table,
	.probe		= tdfxfb_probe,
	.remove		= __devexit_p(tdfxfb_remove),
};

MODULE_DEVICE_TABLE(pci, tdfxfb_id_table);

/*
 * Driver data
 */
static int nopan;
static int nowrap = 1;      /* not implemented (yet) */
static int hwcursor = 1;
static char *mode_option __devinitdata;
/* mtrr option */
static int nomtrr __devinitdata;

/* -------------------------------------------------------------------------
 *			Hardware-specific funcions
 * ------------------------------------------------------------------------- */

static inline u8 vga_inb(struct tdfx_par *par, u32 reg)
{
	return inb(par->iobase + reg - 0x300);
}

static inline void vga_outb(struct tdfx_par *par, u32 reg, u8 val)
{
	outb(val, par->iobase + reg - 0x300);
}

static inline void gra_outb(struct tdfx_par *par, u32 idx, u8 val)
{
	vga_outb(par, GRA_I, idx);
	wmb();
	vga_outb(par, GRA_D, val);
	wmb();
}

static inline void seq_outb(struct tdfx_par *par, u32 idx, u8 val)
{
	vga_outb(par, SEQ_I, idx);
	wmb();
	vga_outb(par, SEQ_D, val);
	wmb();
}

static inline u8 seq_inb(struct tdfx_par *par, u32 idx)
{
	vga_outb(par, SEQ_I, idx);
	mb();
	return vga_inb(par, SEQ_D);
}

static inline void crt_outb(struct tdfx_par *par, u32 idx, u8 val)
{
	vga_outb(par, CRT_I, idx);
	wmb();
	vga_outb(par, CRT_D, val);
	wmb();
}

static inline u8 crt_inb(struct tdfx_par *par, u32 idx)
{
	vga_outb(par, CRT_I, idx);
	mb();
	return vga_inb(par, CRT_D);
}

static inline void att_outb(struct tdfx_par *par, u32 idx, u8 val)
{
	unsigned char tmp;

	tmp = vga_inb(par, IS1_R);
	vga_outb(par, ATT_IW, idx);
	vga_outb(par, ATT_IW, val);
}

static inline void vga_disable_video(struct tdfx_par *par)
{
	unsigned char s;

	s = seq_inb(par, 0x01) | 0x20;
	seq_outb(par, 0x00, 0x01);
	seq_outb(par, 0x01, s);
	seq_outb(par, 0x00, 0x03);
}

static inline void vga_enable_video(struct tdfx_par *par)
{
	unsigned char s;

	s = seq_inb(par, 0x01) & 0xdf;
	seq_outb(par, 0x00, 0x01);
	seq_outb(par, 0x01, s);
	seq_outb(par, 0x00, 0x03);
}

static inline void vga_enable_palette(struct tdfx_par *par)
{
	vga_inb(par, IS1_R);
	mb();
	vga_outb(par, ATT_IW, 0x20);
}

static inline u32 tdfx_inl(struct tdfx_par *par, unsigned int reg)
{
	return readl(par->regbase_virt + reg);
}

static inline void tdfx_outl(struct tdfx_par *par, unsigned int reg, u32 val)
{
	writel(val, par->regbase_virt + reg);
}

static inline void banshee_make_room(struct tdfx_par *par, int size)
{
	/* Note: The Voodoo3's onboard FIFO has 32 slots. This loop
	 * won't quit if you ask for more. */
	while ((tdfx_inl(par, STATUS) & 0x1f) < size - 1)
		cpu_relax();
}

static int banshee_wait_idle(struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	int i = 0;

	banshee_make_room(par, 1);
	tdfx_outl(par, COMMAND_3D, COMMAND_3D_NOP);

	do {
		if ((tdfx_inl(par, STATUS) & STATUS_BUSY) == 0)
			i++;
	} while (i < 3);

	return 0;
}

/*
 * Set the color of a palette entry in 8bpp mode
 */
static inline void do_setpalentry(struct tdfx_par *par, unsigned regno, u32 c)
{
	banshee_make_room(par, 2);
	tdfx_outl(par, DACADDR, regno);
	/* read after write makes it working */
	tdfx_inl(par, DACADDR);
	tdfx_outl(par, DACDATA, c);
}

static u32 do_calc_pll(int freq, int *freq_out)
{
	int m, n, k, best_m, best_n, best_k, best_error;
	int fref = 14318;

	best_error = freq;
	best_n = best_m = best_k = 0;

	for (k = 3; k >= 0; k--) {
		for (m = 63; m >= 0; m--) {
			/*
			 * Estimate value of n that produces target frequency
			 * with current m and k
			 */
			int n_estimated = ((freq * (m + 2) << k) / fref) - 2;

			/* Search neighborhood of estimated n */
			for (n = max(0, n_estimated);
				n <= min(255, n_estimated + 1);
				n++) {
				/*
				 * Calculate PLL freqency with current m, k and
				 * estimated n
				 */
				int f = (fref * (n + 2) / (m + 2)) >> k;
				int error = abs(f - freq);

				/*
				 * If this is the closest we've come to the
				 * target frequency then remember n, m and k
				 */
				if (error < best_error) {
					best_error = error;
					best_n = n;
					best_m = m;
					best_k = k;
				}
			}
		}
	}

	n = best_n;
	m = best_m;
	k = best_k;
	*freq_out = (fref * (n + 2) / (m + 2)) >> k;

	return (n << 8) | (m << 2) | k;
}

static void do_write_regs(struct fb_info *info, struct banshee_reg *reg)
{
	struct tdfx_par *par = info->par;
	int i;

	banshee_wait_idle(info);

	tdfx_outl(par, MISCINIT1, tdfx_inl(par, MISCINIT1) | 0x01);

	crt_outb(par, 0x11, crt_inb(par, 0x11) & 0x7f); /* CRT unprotect */

	banshee_make_room(par, 3);
	tdfx_outl(par, VGAINIT1, reg->vgainit1 & 0x001FFFFF);
	tdfx_outl(par, VIDPROCCFG, reg->vidcfg & ~0x00000001);
#if 0
	tdfx_outl(par, PLLCTRL1, reg->mempll);
	tdfx_outl(par, PLLCTRL2, reg->gfxpll);
#endif
	tdfx_outl(par, PLLCTRL0, reg->vidpll);

	vga_outb(par, MISC_W, reg->misc[0x00] | 0x01);

	for (i = 0; i < 5; i++)
		seq_outb(par, i, reg->seq[i]);

	for (i = 0; i < 25; i++)
		crt_outb(par, i, reg->crt[i]);

	for (i = 0; i < 9; i++)
		gra_outb(par, i, reg->gra[i]);

	for (i = 0; i < 21; i++)
		att_outb(par, i, reg->att[i]);

	crt_outb(par, 0x1a, reg->ext[0]);
	crt_outb(par, 0x1b, reg->ext[1]);

	vga_enable_palette(par);
	vga_enable_video(par);

	banshee_make_room(par, 9);
	tdfx_outl(par, VGAINIT0, reg->vgainit0);
	tdfx_outl(par, DACMODE, reg->dacmode);
	tdfx_outl(par, VIDDESKSTRIDE, reg->stride);
	tdfx_outl(par, HWCURPATADDR, reg->curspataddr);

	tdfx_outl(par, VIDSCREENSIZE, reg->screensize);
	tdfx_outl(par, VIDDESKSTART, reg->startaddr);
	tdfx_outl(par, VIDPROCCFG, reg->vidcfg);
	tdfx_outl(par, VGAINIT1, reg->vgainit1);
	tdfx_outl(par, MISCINIT0, reg->miscinit0);

	banshee_make_room(par, 8);
	tdfx_outl(par, SRCBASE, reg->startaddr);
	tdfx_outl(par, DSTBASE, reg->startaddr);
	tdfx_outl(par, COMMANDEXTRA_2D, 0);
	tdfx_outl(par, CLIP0MIN, 0);
	tdfx_outl(par, CLIP0MAX, 0x0fff0fff);
	tdfx_outl(par, CLIP1MIN, 0);
	tdfx_outl(par, CLIP1MAX, 0x0fff0fff);
	tdfx_outl(par, SRCXY, 0);

	banshee_wait_idle(info);
}

static unsigned long do_lfb_size(struct tdfx_par *par, unsigned short dev_id)
{
	u32 draminit0 = tdfx_inl(par, DRAMINIT0);
	u32 draminit1 = tdfx_inl(par, DRAMINIT1);
	u32 miscinit1;
	int num_chips = (draminit0 & DRAMINIT0_SGRAM_NUM) ? 8 : 4;
	int chip_size; /* in MB */
	int has_sgram = draminit1 & DRAMINIT1_MEM_SDRAM;

	if (dev_id < PCI_DEVICE_ID_3DFX_VOODOO5) {
		/* Banshee/Voodoo3 */
		chip_size = 2;
		if (has_sgram && (draminit0 & DRAMINIT0_SGRAM_TYPE))
			chip_size = 1;
	} else {
		/* Voodoo4/5 */
		has_sgram = 0;
		chip_size = draminit0 & DRAMINIT0_SGRAM_TYPE_MASK;
		chip_size = 1 << (chip_size >> DRAMINIT0_SGRAM_TYPE_SHIFT);
	}

	/* disable block writes for SDRAM */
	miscinit1 = tdfx_inl(par, MISCINIT1);
	miscinit1 |= has_sgram ? 0 : MISCINIT1_2DBLOCK_DIS;
	miscinit1 |= MISCINIT1_CLUT_INV;

	banshee_make_room(par, 1);
	tdfx_outl(par, MISCINIT1, miscinit1);
	return num_chips * chip_size * 1024l * 1024;
}

/* ------------------------------------------------------------------------- */

static int tdfxfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	u32 lpitch;

	if (var->bits_per_pixel != 8  && var->bits_per_pixel != 16 &&
	    var->bits_per_pixel != 24 && var->bits_per_pixel != 32) {
		DPRINTK("depth not supported: %u\n", var->bits_per_pixel);
		return -EINVAL;
	}

	if (var->xres != var->xres_virtual)
		var->xres_virtual = var->xres;

	if (var->yres > var->yres_virtual)
		var->yres_virtual = var->yres;

	if (var->xoffset) {
		DPRINTK("xoffset not supported\n");
		return -EINVAL;
	}
	var->yoffset = 0;

	/*
	 * Banshee doesn't support interlace, but Voodoo4/5 and probably
	 * Voodoo3 do.
	 * no direct information about device id now?
	 *  use max_pixclock for this...
	 */
	if (((var->vmode & FB_VMODE_MASK) == FB_VMODE_INTERLACED) &&
	    (par->max_pixclock < VOODOO3_MAX_PIXCLOCK)) {
		DPRINTK("interlace not supported\n");
		return -EINVAL;
	}

	var->xres = (var->xres + 15) & ~15; /* could sometimes be 8 */
	lpitch = var->xres * ((var->bits_per_pixel + 7) >> 3);

	if (var->xres < 320 || var->xres > 2048) {
		DPRINTK("width not supported: %u\n", var->xres);
		return -EINVAL;
	}

	if (var->yres < 200 || var->yres > 2048) {
		DPRINTK("height not supported: %u\n", var->yres);
		return -EINVAL;
	}

	if (lpitch * var->yres_virtual > info->fix.smem_len) {
		var->yres_virtual = info->fix.smem_len / lpitch;
		if (var->yres_virtual < var->yres) {
			DPRINTK("no memory for screen (%ux%ux%u)\n",
				var->xres, var->yres_virtual,
				var->bits_per_pixel);
			return -EINVAL;
		}
	}

	if (PICOS2KHZ(var->pixclock) > par->max_pixclock) {
		DPRINTK("pixclock too high (%ldKHz)\n",
			PICOS2KHZ(var->pixclock));
		return -EINVAL;
	}

	var->transp.offset = 0;
	var->transp.length = 0;
	switch (var->bits_per_pixel) {
	case 8:
		var->red.length = 8;
		var->red.offset = 0;
		var->green = var->red;
		var->blue = var->red;
		break;
	case 16:
		var->red.offset   = 11;
		var->red.length   = 5;
		var->green.offset = 5;
		var->green.length = 6;
		var->blue.offset  = 0;
		var->blue.length  = 5;
		break;
	case 32:
		var->transp.offset = 24;
		var->transp.length = 8;
	case 24:
		var->red.offset = 16;
		var->green.offset = 8;
		var->blue.offset = 0;
		var->red.length = var->green.length = var->blue.length = 8;
		break;
	}
	var->width = -1;
	var->height = -1;

	var->accel_flags = FB_ACCELF_TEXT;

	DPRINTK("Checking graphics mode at %dx%d depth %d\n",
		var->xres, var->yres, var->bits_per_pixel);
	return 0;
}

static int tdfxfb_set_par(struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	u32 hdispend = info->var.xres;
	u32 hsyncsta = hdispend + info->var.right_margin;
	u32 hsyncend = hsyncsta + info->var.hsync_len;
	u32 htotal   = hsyncend + info->var.left_margin;
	u32 hd, hs, he, ht, hbs, hbe;
	u32 vd, vs, ve, vt, vbs, vbe;
	struct banshee_reg reg;
	int fout, freq;
	u32 wd;
	u32 cpp = (info->var.bits_per_pixel + 7) >> 3;

	memset(&reg, 0, sizeof(reg));

	reg.vidcfg = VIDCFG_VIDPROC_ENABLE | VIDCFG_DESK_ENABLE |
		     VIDCFG_CURS_X11 |
		     ((cpp - 1) << VIDCFG_PIXFMT_SHIFT) |
		     (cpp != 1 ? VIDCFG_CLUT_BYPASS : 0);

	/* PLL settings */
	freq = PICOS2KHZ(info->var.pixclock);

	reg.vidcfg &= ~VIDCFG_2X;

	if (freq > par->max_pixclock / 2) {
		freq = freq > par->max_pixclock ? par->max_pixclock : freq;
		reg.dacmode |= DACMODE_2X;
		reg.vidcfg  |= VIDCFG_2X;
		hdispend >>= 1;
		hsyncsta >>= 1;
		hsyncend >>= 1;
		htotal   >>= 1;
	}

	wd = (hdispend >> 3) - 1;
	hd  = wd;
	hs  = (hsyncsta >> 3) - 1;
	he  = (hsyncend >> 3) - 1;
	ht  = (htotal >> 3) - 1;
	hbs = hd;
	hbe = ht;

	if ((info->var.vmode & FB_VMODE_MASK) == FB_VMODE_DOUBLE) {
		vd = (info->var.yres << 1) - 1;
		vs  = vd + (info->var.lower_margin << 1);
		ve  = vs + (info->var.vsync_len << 1);
		vt = ve + (info->var.upper_margin << 1) - 1;
		reg.screensize = info->var.xres | (info->var.yres << 13);
		reg.vidcfg |= VIDCFG_HALF_MODE;
		reg.crt[0x09] = 0x80;
	} else {
		vd = info->var.yres - 1;
		vs  = vd + info->var.lower_margin;
		ve  = vs + info->var.vsync_len;
		vt = ve + info->var.upper_margin - 1;
		reg.screensize = info->var.xres | (info->var.yres << 12);
		reg.vidcfg &= ~VIDCFG_HALF_MODE;
	}
	vbs = vd;
	vbe = vt;

	/* this is all pretty standard VGA register stuffing */
	reg.misc[0x00] = 0x0f |
			(info->var.xres < 400 ? 0xa0 :
			 info->var.xres < 480 ? 0x60 :
			 info->var.xres < 768 ? 0xe0 : 0x20);

	reg.gra[0x05] = 0x40;
	reg.gra[0x06] = 0x05;
	reg.gra[0x07] = 0x0f;
	reg.gra[0x08] = 0xff;

	reg.att[0x00] = 0x00;
	reg.att[0x01] = 0x01;
	reg.att[0x02] = 0x02;
	reg.att[0x03] = 0x03;
	reg.att[0x04] = 0x04;
	reg.att[0x05] = 0x05;
	reg.att[0x06] = 0x06;
	reg.att[0x07] = 0x07;
	reg.att[0x08] = 0x08;
	reg.att[0x09] = 0x09;
	reg.att[0x0a] = 0x0a;
	reg.att[0x0b] = 0x0b;
	reg.att[0x0c] = 0x0c;
	reg.att[0x0d] = 0x0d;
	reg.att[0x0e] = 0x0e;
	reg.att[0x0f] = 0x0f;
	reg.att[0x10] = 0x41;
	reg.att[0x12] = 0x0f;

	reg.seq[0x00] = 0x03;
	reg.seq[0x01] = 0x01; /* fixme: clkdiv2? */
	reg.seq[0x02] = 0x0f;
	reg.seq[0x03] = 0x00;
	reg.seq[0x04] = 0x0e;

	reg.crt[0x00] = ht - 4;
	reg.crt[0x01] = hd;
	reg.crt[0x02] = hbs;
	reg.crt[0x03] = 0x80 | (hbe & 0x1f);
	reg.crt[0x04] = hs;
	reg.crt[0x05] = ((hbe & 0x20) << 2) | (he & 0x1f);
	reg.crt[0x06] = vt;
	reg.crt[0x07] = ((vs & 0x200) >> 2) |
			((vd & 0x200) >> 3) |
			((vt & 0x200) >> 4) | 0x10 |
			((vbs & 0x100) >> 5) |
			((vs & 0x100) >> 6) |
			((vd & 0x100) >> 7) |
			((vt & 0x100) >> 8);
	reg.crt[0x09] |= 0x40 | ((vbs & 0x200) >> 4);
	reg.crt[0x10] = vs;
	reg.crt[0x11] = (ve & 0x0f) | 0x20;
	reg.crt[0x12] = vd;
	reg.crt[0x13] = wd;
	reg.crt[0x15] = vbs;
	reg.crt[0x16] = vbe + 1;
	reg.crt[0x17] = 0xc3;
	reg.crt[0x18] = 0xff;

	/* Banshee's nonvga stuff */
	reg.ext[0x00] = (((ht & 0x100) >> 8) |
			((hd & 0x100) >> 6) |
			((hbs & 0x100) >> 4) |
			((hbe & 0x40) >> 1) |
			((hs & 0x100) >> 2) |
			((he & 0x20) << 2));
	reg.ext[0x01] = (((vt & 0x400) >> 10) |
			((vd & 0x400) >> 8) |
			((vbs & 0x400) >> 6) |
			((vbe & 0x400) >> 4));

	reg.vgainit0 =	VGAINIT0_8BIT_DAC     |
			VGAINIT0_EXT_ENABLE   |
			VGAINIT0_WAKEUP_3C3   |
			VGAINIT0_ALT_READBACK |
			VGAINIT0_EXTSHIFTOUT;
	reg.vgainit1 = tdfx_inl(par, VGAINIT1) & 0x1fffff;

	if (hwcursor)
		reg.curspataddr = info->fix.smem_len;

	reg.cursloc   = 0;

	reg.cursc0    = 0;
	reg.cursc1    = 0xffffff;

	reg.stride    = info->var.xres * cpp;
	reg.startaddr = info->var.yoffset * reg.stride
			+ info->var.xoffset * cpp;

	reg.vidpll = do_calc_pll(freq, &fout);
#if 0
	reg.mempll = do_calc_pll(..., &fout);
	reg.gfxpll = do_calc_pll(..., &fout);
#endif

	if ((info->var.vmode & FB_VMODE_MASK) == FB_VMODE_INTERLACED)
		reg.vidcfg |= VIDCFG_INTERLACE;
	reg.miscinit0 = tdfx_inl(par, MISCINIT0);

#if defined(__BIG_ENDIAN)
	switch (info->var.bits_per_pixel) {
	case 8:
	case 24:
		reg.miscinit0 &= ~(1 << 30);
		reg.miscinit0 &= ~(1 << 31);
		break;
	case 16:
		reg.miscinit0 |= (1 << 30);
		reg.miscinit0 |= (1 << 31);
		break;
	case 32:
		reg.miscinit0 |= (1 << 30);
		reg.miscinit0 &= ~(1 << 31);
		break;
	}
#endif
	do_write_regs(info, &reg);

	/* Now change fb_fix_screeninfo according to changes in par */
	info->fix.line_length = reg.stride;
	info->fix.visual = (info->var.bits_per_pixel == 8)
				? FB_VISUAL_PSEUDOCOLOR
				: FB_VISUAL_TRUECOLOR;
	DPRINTK("Graphics mode is now set at %dx%d depth %d\n",
		info->var.xres, info->var.yres, info->var.bits_per_pixel);
	return 0;
}

/* A handy macro shamelessly pinched from matroxfb */
#define CNVT_TOHW(val, width) ((((val) << (width)) + 0x7FFF - (val)) >> 16)

static int tdfxfb_setcolreg(unsigned regno, unsigned red, unsigned green,
			    unsigned blue, unsigned transp,
			    struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	u32 rgbcol;

	if (regno >= info->cmap.len || regno > 255)
		return 1;

	/* grayscale works only partially under directcolor */
	if (info->var.grayscale) {
		/* grayscale = 0.30*R + 0.59*G + 0.11*B */
		blue = (red * 77 + green * 151 + blue * 28) >> 8;
		green = blue;
		red = blue;
	}

	switch (info->fix.visual) {
	case FB_VISUAL_PSEUDOCOLOR:
		rgbcol = (((u32)red   & 0xff00) << 8) |
			 (((u32)green & 0xff00) << 0) |
			 (((u32)blue  & 0xff00) >> 8);
		do_setpalentry(par, regno, rgbcol);
		break;
	/* Truecolor has no hardware color palettes. */
	case FB_VISUAL_TRUECOLOR:
		if (regno < 16) {
			rgbcol = (CNVT_TOHW(red, info->var.red.length) <<
				  info->var.red.offset) |
				(CNVT_TOHW(green, info->var.green.length) <<
				 info->var.green.offset) |
				(CNVT_TOHW(blue, info->var.blue.length) <<
				 info->var.blue.offset) |
				(CNVT_TOHW(transp, info->var.transp.length) <<
				 info->var.transp.offset);
			par->palette[regno] = rgbcol;
		}

		break;
	default:
		DPRINTK("bad depth %u\n", info->var.bits_per_pixel);
		break;
	}

	return 0;
}

/* 0 unblank, 1 blank, 2 no vsync, 3 no hsync, 4 off */
static int tdfxfb_blank(int blank, struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	int vgablank = 1;
	u32 dacmode = tdfx_inl(par, DACMODE);

	dacmode &= ~(BIT(1) | BIT(3));

	switch (blank) {
	case FB_BLANK_UNBLANK: /* Screen: On; HSync: On, VSync: On */
		vgablank = 0;
		break;
	case FB_BLANK_NORMAL: /* Screen: Off; HSync: On, VSync: On */
		break;
	case FB_BLANK_VSYNC_SUSPEND: /* Screen: Off; HSync: On, VSync: Off */
		dacmode |= BIT(3);
		break;
	case FB_BLANK_HSYNC_SUSPEND: /* Screen: Off; HSync: Off, VSync: On */
		dacmode |= BIT(1);
		break;
	case FB_BLANK_POWERDOWN: /* Screen: Off; HSync: Off, VSync: Off */
		dacmode |= BIT(1) | BIT(3);
		break;
	}

	banshee_make_room(par, 1);
	tdfx_outl(par, DACMODE, dacmode);
	if (vgablank)
		vga_disable_video(par);
	else
		vga_enable_video(par);
	return 0;
}

/*
 * Set the starting position of the visible screen to var->yoffset
 */
static int tdfxfb_pan_display(struct fb_var_screeninfo *var,
			      struct fb_info *info)
{
	struct tdfx_par *par = info->par;
	u32 addr = var->yoffset * info->fix.line_length;

	if (nopan || var->xoffset || (var->yoffset > var->yres_virtual))
		return -EINVAL;
	if ((var->yoffset + var->yres > var->yres_virtual && nowrap))
		return -EINVAL;

	banshee_make_room(par, 1);
	tdfx_outl(par, VIDDESKSTART, addr);

	info->var.xoffset = var->xoffset;
	info->var.yoffset = var->yoffset;
	return 0;
}

#ifdef CONFIG_FB_3DFX_ACCEL
/*
 * FillRect 2D command (solidfill or invert (via ROP_XOR))
 */
static void tdfxfb_fillrect(struct fb_info *info,
			    const struct fb_fillrect *rect)
{
	struct tdfx_par *par = info->par;
	u32 bpp = info->var.bits_per_pixel;
	u32 stride = info->fix.line_length;
	u32 fmt = stride | ((bpp + ((bpp == 8) ? 0 : 8)) << 13);
	int tdfx_rop;
	u32 dx = rect->dx;
	u32 dy = rect->dy;
	u32 dstbase = 0;

	if (rect->rop == ROP_COPY)
		tdfx_rop = TDFX_ROP_COPY;
	else
		tdfx_rop = TDFX_ROP_XOR;

	/* asume always rect->height < 4096 */
	if (dy + rect->height > 4095) {
		dstbase = stride * dy;
		dy = 0;
	}
	/* asume always rect->width < 4096 */
	if (dx + rect->width > 4095) {
		dstbase += dx * bpp >> 3;
		dx = 0;
	}
	banshee_make_room(par, 6);
	tdfx_outl(par, DSTFORMAT, fmt);
	if (info->fix.visual == FB_VISUAL_PSEUDOCOLOR) {
		tdfx_outl(par, COLORFORE, rect->color);
	} else { /* FB_VISUAL_TRUECOLOR */
		tdfx_outl(par, COLORFORE, par->palette[rect->color]);
	}
	tdfx_outl(par, COMMAND_2D, COMMAND_2D_FILLRECT | (tdfx_rop << 24));
	tdfx_outl(par, DSTBASE, dstbase);
	tdfx_outl(par, DSTSIZE, rect->width | (rect->height << 16));
	tdfx_outl(par, LAUNCH_2D, dx | (dy << 16));
}

/*
 * Screen-to-Screen BitBlt 2D command (for the bmove fb op.)
 */
static void tdfxfb_copyarea(struct fb_info *info,
			    const struct fb_copyarea *area)
{
	struct tdfx_par *par = info->par;
	u32 sx = area->sx, sy = area->sy, dx = area->dx, dy = area->dy;
	u32 bpp = info->var.bits_per_pixel;
	u32 stride = info->fix.line_length;
	u32 blitcmd = COMMAND_2D_S2S_BITBLT | (TDFX_ROP_COPY << 24);
	u32 fmt = stride | ((bpp + ((bpp == 8) ? 0 : 8)) << 13);
	u32 dstbase = 0;
	u32 srcbase = 0;

	/* asume always area->height < 4096 */
	if (sy + area->height > 4095) {
		srcbase = stride * sy;
		sy = 0;
	}
	/* asume always area->width < 4096 */
	if (sx + area->width > 4095) {
		srcbase += sx * bpp >> 3;
		sx = 0;
	}
	/* asume always area->height < 4096 */
	if (dy + area->height > 4095) {
		dstbase = stride * dy;
		dy = 0;
	}
	/* asume always area->width < 4096 */
	if (dx + area->width > 4095) {
		dstbase += dx * bpp >> 3;
		dx = 0;
	}

	if (area->sx <= area->dx) {
		/* -X */
		blitcmd |= BIT(14);
		sx += area->width - 1;
		dx += area->width - 1;
	}
	if (area->sy <= area->dy) {
		/* -Y */
		blitcmd |= BIT(15);
		sy += area->height - 1;
		dy += area->height - 1;
	}

	banshee_make_room(par, 8);

	tdfx_outl(par, SRCFORMAT, fmt);
	tdfx_outl(par, DSTFORMAT, fmt);
	tdfx_outl(par, COMMAND_2D, blitcmd);
	tdfx_outl(par, DSTSIZE, area->width | (area->height << 16));
	tdfx_outl(par, DSTXY, dx | (dy << 16));
	tdfx_outl(par, SRCBASE, srcbase);
	tdfx_outl(par, DSTBASE, dstbase);
	tdfx_outl(par, LAUNCH_2D, sx | (sy << 16));
}

static void tdfxfb_imageblit(struct fb_info *info, const struct fb_image *image)
{
	struct tdfx_par *par = info->par;
	int size = image->height * ((image->width * image->depth + 7) >> 3);
	int fifo_free;
	int i, stride = info->fix.line_length;
	u32 bpp = info->var.bits_per_pixel;
	u32 dstfmt = stride | ((bpp + ((bpp == 8) ? 0 : 8)) << 13);
	u8 *chardata = (u8 *) image->data;
	u32 srcfmt;
	u32 dx = image->dx;
	u32 dy = image->dy;
	u32 dstbase = 0;

	if (image->depth != 1) {
#ifdef BROKEN_CODE
		banshee_make_room(par, 6 + ((size + 3) >> 2));
		srcfmt = stride | ((bpp + ((bpp == 8) ? 0 : 8)) << 13) |
			0x400000;
#else
		cfb_imageblit(info, image);
#endif
		return;
	}
	banshee_make_room(par, 9);
	switch (info->fix.visual) {
	case FB_VISUAL_PSEUDOCOLOR:
		tdfx_outl(par, COLORFORE, image->fg_color);
		tdfx_outl(par, COLORBACK, image->bg_color);
		break;
	case FB_VISUAL_TRUECOLOR:
	default:
		tdfx_outl(par, COLORFORE,
			  par->palette[image->fg_color]);
		tdfx_outl(par, COLORBACK,
			  par->palette[image->bg_color]);
	}
#ifdef __BIG_ENDIAN
	srcfmt = 0x400000 | BIT(20);
#else
	srcfmt = 0x400000;
#endif
	/* asume always image->height < 4096 */
	if (dy + image->height > 4095) {
		dstbase = stride * dy;
		dy = 0;
	}
	/* asume always image->width < 4096 */
	if (dx + image->width > 4095) {
		dstbase += dx * bpp >> 3;
		dx = 0;
	}

	tdfx_outl(par, DSTBASE, dstbase);
	tdfx_outl(par, SRCXY, 0);
	tdfx_outl(par, DSTXY, dx | (dy << 16));
	tdfx_outl(par, COMMAND_2D,
		  COMMAND_2D_H2S_BITBLT | (TDFX_ROP_COPY << 24));
	tdfx_outl(par, SRCFORMAT, srcfmt);
	tdfx_outl(par, DSTFORMAT, dstfmt);
	tdfx_outl(par, DSTSIZE, image->width | (image->height << 16));

	/* A count of how many free FIFO entries we've requested.
	 * When this goes negative, we need to request more. */
	fifo_free = 0;

	/* Send four bytes at a time of data */
	for (i = (size >> 2); i > 0; i--) {
		if (--fifo_free < 0) {
			fifo_free = 31;
			banshee_make_room(par, fifo_free);
		}
		tdfx_outl(par, LAUNCH_2D, *(u32 *)chardata);
		chardata += 4;
	}

	/* Send the leftovers now */
	banshee_make_room(par, 3);
	switch (size % 4) {
	case 0:
		break;
	case 1:
		tdfx_outl(par, LAUNCH_2D, *chardata);
		break;
	case 2:
		tdfx_outl(par, LAUNCH_2D, *(u16 *)chardata);
		break;
	case 3:
		tdfx_outl(par, LAUNCH_2D,
			*(u16 *)chardata | (chardata[3] << 24));
		break;
	}
}
#endif /* CONFIG_FB_3DFX_ACCEL */

static int tdfxfb_cursor(struct fb_info *info, struct fb_cursor *cursor)
{
	struct tdfx_par *par = info->par;
	u32 vidcfg;

	if (!hwcursor)
		return -EINVAL;	/* just to force soft_cursor() call */

	/* Too large of a cursor or wrong bpp :-( */
	if (cursor->image.width > 64 ||
	    cursor->image.height > 64 ||
	    cursor->image.depth > 1)
		return -EINVAL;

	vidcfg = tdfx_inl(par, VIDPROCCFG);
	if (cursor->enable)
		tdfx_outl(par, VIDPROCCFG, vidcfg | VIDCFG_HWCURSOR_ENABLE);
	else
		tdfx_outl(par, VIDPROCCFG, vidcfg & ~VIDCFG_HWCURSOR_ENABLE);

	/*
	 * If the cursor is not be changed this means either we want the
	 * current cursor state (if enable is set) or we want to query what
	 * we can do with the cursor (if enable is not set)
	 */
	if (!cursor->set)
		return 0;

	/* fix cursor color - XFree86 forgets to restore it properly */
	if (cursor->set & FB_CUR_SETCMAP) {
		struct fb_cmap cmap = info->cmap;
		u32 bg_idx = cursor->image.bg_color;
		u32 fg_idx = cursor->image.fg_color;
		unsigned long bg_color, fg_color;

		fg_color = (((u32)cmap.red[fg_idx]   & 0xff00) << 8) |
			   (((u32)cmap.green[fg_idx] & 0xff00) << 0) |
			   (((u32)cmap.blue[fg_idx]  & 0xff00) >> 8);
		bg_color = (((u32)cmap.red[bg_idx]   & 0xff00) << 8) |
			   (((u32)cmap.green[bg_idx] & 0xff00) << 0) |
			   (((u32)cmap.blue[bg_idx]  & 0xff00) >> 8);
		banshee_make_room(par, 2);
		tdfx_outl(par, HWCURC0, bg_color);
		tdfx_outl(par, HWCURC1, fg_color);
	}

	if (cursor->set & FB_CUR_SETPOS) {
		int x = cursor->image.dx;
		int y = cursor->image.dy - info->var.yoffset;

		x += 63;
		y += 63;
		banshee_make_room(par, 1);
		tdfx_outl(par, HWCURLOC, (y << 16) + x);
	}
	if (cursor->set & (FB_CUR_SETIMAGE | FB_CUR_SETSHAPE)) {
		/*
		 * Voodoo 3 and above cards use 2 monochrome cursor patterns.
		 *    The reason is so the card can fetch 8 words at a time
		 * and are stored on chip for use for the next 8 scanlines.
		 * This reduces the number of times for access to draw the
		 * cursor for each screen refresh.
		 *    Each pattern is a bitmap of 64 bit wide and 64 bit high
		 * (total of 8192 bits or 1024 bytes). The two patterns are
		 * stored in such a way that pattern 0 always resides in the
		 * lower half (least significant 64 bits) of a 128 bit word
		 * and pattern 1 the upper half. If you examine the data of
		 * the cursor image the graphics card uses then from the
		 * begining you see line one of pattern 0, line one of
		 * pattern 1, line two of pattern 0, line two of pattern 1,
		 * etc etc. The linear stride for the cursor is always 16 bytes
		 * (128 bits) which is the maximum cursor width times two for
		 * the two monochrome patterns.
		 */
		u8 __iomem *cursorbase = info->screen_base + info->fix.smem_len;
		u8 *bitmap = (u8 *)cursor->image.data;
		u8 *mask = (u8 *)cursor->mask;
		int i;

		fb_memset(cursorbase, 0, 1024);

		for (i = 0; i < cursor->image.height; i++) {
			int h = 0;
			int j = (cursor->image.width + 7) >> 3;

			for (; j > 0; j--) {
				u8 data = *mask ^ *bitmap;
				if (cursor->rop == ROP_COPY)
					data = *mask & *bitmap;
				/* Pattern 0. Copy the cursor mask to it */
				fb_writeb(*mask, cursorbase + h);
				mask++;
				/* Pattern 1. Copy the cursor bitmap to it */
				fb_writeb(data, cursorbase + h + 8);
				bitmap++;
				h++;
			}
			cursorbase += 16;
		}
	}
	return 0;
}

static struct fb_ops tdfxfb_ops = {
	.owner		= THIS_MODULE,
	.fb_check_var	= tdfxfb_check_var,
	.fb_set_par	= tdfxfb_set_par,
	.fb_setcolreg	= tdfxfb_setcolreg,
	.fb_blank	= tdfxfb_blank,
	.fb_pan_display	= tdfxfb_pan_display,
	.fb_sync	= banshee_wait_idle,
	.fb_cursor	= tdfxfb_cursor,
#ifdef CONFIG_FB_3DFX_ACCEL
	.fb_fillrect	= tdfxfb_fillrect,
	.fb_copyarea	= tdfxfb_copyarea,
	.fb_imageblit	= tdfxfb_imageblit,
#else
	.fb_fillrect	= cfb_fillrect,
	.fb_copyarea	= cfb_copyarea,
	.fb_imageblit	= cfb_imageblit,
#endif
};

/**
 *      tdfxfb_probe - Device Initializiation
 *
 *      @pdev:  PCI Device to initialize
 *      @id:    PCI Device ID
 *
 *      Initializes and allocates resources for PCI device @pdev.
 *
 */
static int __devinit tdfxfb_probe(struct pci_dev *pdev,
				  const struct pci_device_id *id)
{
	struct tdfx_par *default_par;
	struct fb_info *info;
	int err, lpitch;

	err = pci_enable_device(pdev);
	if (err) {
		printk(KERN_ERR "tdfxfb: Can't enable pdev: %d\n", err);
		return err;
	}

	info = framebuffer_alloc(sizeof(struct tdfx_par), &pdev->dev);

	if (!info)
		return -ENOMEM;

	default_par = info->par;

	/* Configure the default fb_fix_screeninfo first */
	switch (pdev->device) {
	case PCI_DEVICE_ID_3DFX_BANSHEE:
		strcat(tdfx_fix.id, " Banshee");
		default_par->max_pixclock = BANSHEE_MAX_PIXCLOCK;
		break;
	case PCI_DEVICE_ID_3DFX_VOODOO3:
		strcat(tdfx_fix.id, " Voodoo3");
		default_par->max_pixclock = VOODOO3_MAX_PIXCLOCK;
		break;
	case PCI_DEVICE_ID_3DFX_VOODOO5:
		strcat(tdfx_fix.id, " Voodoo5");
		default_par->max_pixclock = VOODOO5_MAX_PIXCLOCK;
		break;
	}

	tdfx_fix.mmio_start = pci_resource_start(pdev, 0);
	tdfx_fix.mmio_len = pci_resource_len(pdev, 0);
	if (!request_mem_region(tdfx_fix.mmio_start, tdfx_fix.mmio_len,
				"tdfx regbase")) {
		printk(KERN_ERR "tdfxfb: Can't reserve regbase\n");
		goto out_err;
	}

	default_par->regbase_virt =
		ioremap_nocache(tdfx_fix.mmio_start, tdfx_fix.mmio_len);
	if (!default_par->regbase_virt) {
		printk(KERN_ERR "fb: Can't remap %s register area.\n",
				tdfx_fix.id);
		goto out_err_regbase;
	}

	tdfx_fix.smem_start = pci_resource_start(pdev, 1);
	tdfx_fix.smem_len = do_lfb_size(default_par, pdev->device);
	if (!tdfx_fix.smem_len) {
		printk(KERN_ERR "fb: Can't count %s memory.\n", tdfx_fix.id);
		goto out_err_regbase;
	}

	if (!request_mem_region(tdfx_fix.smem_start,
				pci_resource_len(pdev, 1), "tdfx smem")) {
		printk(KERN_ERR "tdfxfb: Can't reserve smem\n");
		goto out_err_regbase;
	}

	info->screen_base = ioremap_nocache(tdfx_fix.smem_start,
					    tdfx_fix.smem_len);
	if (!info->screen_base) {
		printk(KERN_ERR "fb: Can't remap %s framebuffer.\n",
				tdfx_fix.id);
		goto out_err_screenbase;
	}

	default_par->iobase = pci_resource_start(pdev, 2);

	if (!request_region(pci_resource_start(pdev, 2),
			    pci_resource_len(pdev, 2), "tdfx iobase")) {
		printk(KERN_ERR "tdfxfb: Can't reserve iobase\n");
		goto out_err_screenbase;
	}

	printk(KERN_INFO "fb: %s memory = %dK\n", tdfx_fix.id,
			tdfx_fix.smem_len >> 10);

	default_par->mtrr_handle = -1;
	if (!nomtrr)
		default_par->mtrr_handle =
			mtrr_add(tdfx_fix.smem_start, tdfx_fix.smem_len,
				 MTRR_TYPE_WRCOMB, 1);

	tdfx_fix.ypanstep	= nopan ? 0 : 1;
	tdfx_fix.ywrapstep	= nowrap ? 0 : 1;

	info->fbops		= &tdfxfb_ops;
	info->fix		= tdfx_fix;
	info->pseudo_palette	= default_par->palette;
	info->flags		= FBINFO_DEFAULT | FBINFO_HWACCEL_YPAN;
#ifdef CONFIG_FB_3DFX_ACCEL
	info->flags		|= FBINFO_HWACCEL_FILLRECT |
				   FBINFO_HWACCEL_COPYAREA |
				   FBINFO_HWACCEL_IMAGEBLIT |
				   FBINFO_READS_FAST;
#endif
	/* reserve 8192 bits for cursor */
	/* the 2.4 driver says PAGE_MASK boundary is not enough for Voodoo4 */
	if (hwcursor)
		info->fix.smem_len = (info->fix.smem_len - 1024) &
					(PAGE_MASK << 1);

	if (!mode_option)
		mode_option = "640x480@60";

	err = fb_find_mode(&info->var, info, mode_option, NULL, 0, NULL, 8);
	if (!err || err == 4)
		info->var = tdfx_var;

	/* maximize virtual vertical length */
	lpitch = info->var.xres_virtual * ((info->var.bits_per_pixel + 7) >> 3);
	info->var.yres_virtual = info->fix.smem_len / lpitch;
	if (info->var.yres_virtual < info->var.yres)
		goto out_err_iobase;

	if (fb_alloc_cmap(&info->cmap, 256, 0) < 0) {
		printk(KERN_ERR "tdfxfb: Can't allocate color map\n");
		goto out_err_iobase;
	}

	if (register_framebuffer(info) < 0) {
		printk(KERN_ERR "tdfxfb: can't register framebuffer\n");
		fb_dealloc_cmap(&info->cmap);
		goto out_err_iobase;
	}
	/*
	 * Our driver data
	 */
	pci_set_drvdata(pdev, info);
	return 0;

out_err_iobase:
	if (default_par->mtrr_handle >= 0)
		mtrr_del(default_par->mtrr_handle, info->fix.smem_start,
			 info->fix.smem_len);
	release_mem_region(pci_resource_start(pdev, 2),
			   pci_resource_len(pdev, 2));
out_err_screenbase:
	if (info->screen_base)
		iounmap(info->screen_base);
	release_mem_region(tdfx_fix.smem_start, pci_resource_len(pdev, 1));
out_err_regbase:
	/*
	 * Cleanup after anything that was remapped/allocated.
	 */
	if (default_par->regbase_virt)
		iounmap(default_par->regbase_virt);
	release_mem_region(tdfx_fix.mmio_start, tdfx_fix.mmio_len);
out_err:
	framebuffer_release(info);
	return -ENXIO;
}

#ifndef MODULE
static void __init tdfxfb_setup(char *options)
{
	char *this_opt;

	if (!options || !*options)
		return;

	while ((this_opt = strsep(&options, ",")) != NULL) {
		if (!*this_opt)
			continue;
		if (!strcmp(this_opt, "nopan")) {
			nopan = 1;
		} else if (!strcmp(this_opt, "nowrap")) {
			nowrap = 1;
		} else if (!strncmp(this_opt, "hwcursor=", 9)) {
			hwcursor = simple_strtoul(this_opt + 9, NULL, 0);
#ifdef CONFIG_MTRR
		} else if (!strncmp(this_opt, "nomtrr", 6)) {
			nomtrr = 1;
#endif
		} else {
			mode_option = this_opt;
		}
	}
}
#endif

/**
 *      tdfxfb_remove - Device removal
 *
 *      @pdev:  PCI Device to cleanup
 *
 *      Releases all resources allocated during the course of the driver's
 *      lifetime for the PCI device @pdev.
 *
 */
static void __devexit tdfxfb_remove(struct pci_dev *pdev)
{
	struct fb_info *info = pci_get_drvdata(pdev);
	struct tdfx_par *par = info->par;

	unregister_framebuffer(info);
	if (par->mtrr_handle >= 0)
		mtrr_del(par->mtrr_handle, info->fix.smem_start,
			 info->fix.smem_len);
	iounmap(par->regbase_virt);
	iounmap(info->screen_base);

	/* Clean up after reserved regions */
	release_region(pci_resource_start(pdev, 2),
		       pci_resource_len(pdev, 2));
	release_mem_region(pci_resource_start(pdev, 1),
			   pci_resource_len(pdev, 1));
	release_mem_region(pci_resource_start(pdev, 0),
			   pci_resource_len(pdev, 0));
	pci_set_drvdata(pdev, NULL);
	framebuffer_release(info);
}

static int __init tdfxfb_init(void)
{
#ifndef MODULE
	char *option = NULL;

	if (fb_get_options("tdfxfb", &option))
		return -ENODEV;

	tdfxfb_setup(option);
#endif
	return pci_register_driver(&tdfxfb_driver);
}

static void __exit tdfxfb_exit(void)
{
	pci_unregister_driver(&tdfxfb_driver);
}

MODULE_AUTHOR("Hannu Mallat <hmallat@cc.hut.fi>");
MODULE_DESCRIPTION("3Dfx framebuffer device driver");
MODULE_LICENSE("GPL");

module_param(hwcursor, int, 0644);
MODULE_PARM_DESC(hwcursor, "Enable hardware cursor "
			"(1=enable, 0=disable, default=1)");
#ifdef CONFIG_MTRR
module_param(nomtrr, bool, 0);
MODULE_PARM_DESC(nomtrr, "Disable MTRR support (default: enabled)");
#endif

module_init(tdfxfb_init);
module_exit(tdfxfb_exit);
