/*
 *  linux/drivers/video/sgivwfb.c -- SGI DBE frame buffer device
 *
 *	Copyright (C) 1999 Silicon Graphics, Inc.
 *      Jeffrey Newquist, newquist@engr.sgi.som
 *
 *  This file is subject to the terms and conditions of the GNU General Public
 *  License. See the file COPYING in the main directory of this archive for
 *  more details.
 */

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/mm.h>
#include <linux/errno.h>
#include <linux/delay.h>
#include <linux/fb.h>
#include <linux/init.h>
#include <linux/ioport.h>
#include <linux/platform_device.h>

#include <asm/io.h>
#include <asm/mtrr.h>

#include <setup_arch.h>

#define INCLUDE_TIMING_TABLE_DATA
#define DBE_REG_BASE par->regs
#include <video/sgivw.h>

struct sgivw_par {
	struct asregs *regs;
	u32 cmap_fifo;
	u_long timing_num;
};

#define FLATPANEL_SGI_1600SW	5

/*
 *  RAM we reserve for the frame buffer. This defines the maximum screen
 *  size
 *
 *  The default can be overridden if the driver is compiled as a module
 */

static int ypan = 0;
static int ywrap = 0;

static int flatpanel_id = -1;

static struct fb_fix_screeninfo sgivwfb_fix __initdata = {
	.id		= "SGI Vis WS FB",
	.type		= FB_TYPE_PACKED_PIXELS,
        .visual		= FB_VISUAL_PSEUDOCOLOR,
	.mmio_start	= DBE_REG_PHYS,
	.mmio_len	= DBE_REG_SIZE,
        .accel		= FB_ACCEL_NONE,
	.line_length	= 640,
};

static struct fb_var_screeninfo sgivwfb_var __initdata = {
	/* 640x480, 8 bpp */
	.xres		= 640,
	.yres		= 480,
	.xres_virtual	= 640,
	.yres_virtual	= 480,
	.bits_per_pixel	= 8,
	.red		= { 0, 8, 0 },
	.green		= { 0, 8, 0 },
	.blue		= { 0, 8, 0 },
	.height		= -1,
	.width		= -1,
	.pixclock	= 20000,
	.left_margin	= 64,
	.right_margin	= 64,
	.upper_margin	= 32,
	.lower_margin	= 32,
	.hsync_len	= 64,
	.vsync_len	= 2,
	.vmode		= FB_VMODE_NONINTERLACED
};

static struct fb_var_screeninfo sgivwfb_var1600sw __initdata = {
	/* 1600x1024, 8 bpp */
	.xres		= 1600,
	.yres		= 1024,
	.xres_virtual	= 1600,
	.yres_virtual	= 1024,
	.bits_per_pixel	= 8,
	.red		= { 0, 8, 0 },
	.green		= { 0, 8, 0 },
	.blue		= { 0, 8, 0 },
	.height		= -1,
	.width		= -1,
	.pixclock	= 9353,
	.left_margin	= 20,
	.right_margin	= 30,
	.upper_margin	= 37,
	.lower_margin	= 3,
	.hsync_len	= 20,
	.vsync_len	= 3,
	.vmode		= FB_VMODE_NONINTERLACED
};

/*
 *  Interface used by the world
 */
int sgivwfb_init(void);

static int sgivwfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info);
static int sgivwfb_set_par(struct fb_info *info);
static int sgivwfb_setcolreg(u_int regno, u_int red, u_int green,
			     u_int blue, u_int transp,
			     struct fb_info *info);
static int sgivwfb_mmap(struct fb_info *info,
			struct vm_area_struct *vma);

static struct fb_ops sgivwfb_ops = {
	.owner		= THIS_MODULE,
	.fb_check_var	= sgivwfb_check_var,
	.fb_set_par	= sgivwfb_set_par,
	.fb_setcolreg	= sgivwfb_setcolreg,
	.fb_fillrect	= cfb_fillrect,
	.fb_copyarea	= cfb_copyarea,
	.fb_imageblit	= cfb_imageblit,
	.fb_mmap	= sgivwfb_mmap,
};

/*
 *  Internal routines
 */
static unsigned long bytes_per_pixel(int bpp)
{
	switch (bpp) {
		case 8:
			return 1;
		case 16:
			return 2;
		case 32:
			return 4;
		default:
			printk(KERN_INFO "sgivwfb: unsupported bpp %d\n", bpp);
			return 0;
	}
}

static unsigned long get_line_length(int xres_virtual, int bpp)
{
	return (xres_virtual * bytes_per_pixel(bpp));
}

/*
 * Function:	dbe_TurnOffDma
 * Parameters:	(None)
 * Description:	This should turn off the monitor and dbe.  This is used
 *              when switching between the serial console and the graphics
 *              console.
 */

static void dbe_TurnOffDma(struct sgivw_par *par)
{
	unsigned int readVal;
	int i;

	// Check to see if things are already turned off:
	// 1) Check to see if dbe is not using the internal dotclock.
	// 2) Check to see if the xy counter in dbe is already off.

	DBE_GETREG(ctrlstat, readVal);
	if (GET_DBE_FIELD(CTRLSTAT, PCLKSEL, readVal) < 2)
		return;

	DBE_GETREG(vt_xy, readVal);
	if (GET_DBE_FIELD(VT_XY, VT_FREEZE, readVal) == 1)
		return;

	// Otherwise, turn off dbe

	DBE_GETREG(ovr_control, readVal);
	SET_DBE_FIELD(OVR_CONTROL, OVR_DMA_ENABLE, readVal, 0);
	DBE_SETREG(ovr_control, readVal);
	udelay(1000);
	DBE_GETREG(frm_control, readVal);
	SET_DBE_FIELD(FRM_CONTROL, FRM_DMA_ENABLE, readVal, 0);
	DBE_SETREG(frm_control, readVal);
	udelay(1000);
	DBE_GETREG(did_control, readVal);
	SET_DBE_FIELD(DID_CONTROL, DID_DMA_ENABLE, readVal, 0);
	DBE_SETREG(did_control, readVal);
	udelay(1000);

	// XXX HACK:
	//
	//    This was necessary for GBE--we had to wait through two
	//    vertical retrace periods before the pixel DMA was
	//    turned off for sure.  I've left this in for now, in
	//    case dbe needs it.

	for (i = 0; i < 10000; i++) {
		DBE_GETREG(frm_inhwctrl, readVal);
		if (GET_DBE_FIELD(FRM_INHWCTRL, FRM_DMA_ENABLE, readVal) ==
		    0)
			udelay(10);
		else {
			DBE_GETREG(ovr_inhwctrl, readVal);
			if (GET_DBE_FIELD
			    (OVR_INHWCTRL, OVR_DMA_ENABLE, readVal) == 0)
				udelay(10);
			else {
				DBE_GETREG(did_inhwctrl, readVal);
				if (GET_DBE_FIELD
				    (DID_INHWCTRL, DID_DMA_ENABLE,
				     readVal) == 0)
					udelay(10);
				else
					break;
			}
		}
	}
}

/*
 *  Set the User Defined Part of the Display. Again if par use it to get
 *  real video mode.
 */
static int sgivwfb_check_var(struct fb_var_screeninfo *var, 
			     struct fb_info *info)
{
	struct sgivw_par *par = (struct sgivw_par *)info->par;
	struct dbe_timing_info *timing;
	u_long line_length;
	u_long min_mode;
	int req_dot;
	int test_mode;

	/*
	 *  FB_VMODE_CONUPDATE and FB_VMODE_SMOOTH_XPAN are equal!
	 *  as FB_VMODE_SMOOTH_XPAN is only used internally
	 */

	if (var->vmode & FB_VMODE_CONUPDATE) {
		var->vmode |= FB_VMODE_YWRAP;
		var->xoffset = info->var.xoffset;
		var->yoffset = info->var.yoffset;
	}

	/* XXX FIXME - forcing var's */
	var->xoffset = 0;
	var->yoffset = 0;

	/* Limit bpp to 8, 16, and 32 */
	if (var->bits_per_pixel <= 8)
		var->bits_per_pixel = 8;
	else if (var->bits_per_pixel <= 16)
		var->bits_per_pixel = 16;
	else if (var->bits_per_pixel <= 32)
		var->bits_per_pixel = 32;
	else
		return -EINVAL;

	var->grayscale = 0;	/* No grayscale for now */

	/* determine valid resolution and timing */
	for (min_mode = 0; min_mode < DBE_VT_SIZE; min_mode++) {
		if (dbeVTimings[min_mode].width >= var->xres &&
		    dbeVTimings[min_mode].height >= var->yres)
			break;
	}

	if (min_mode == DBE_VT_SIZE)
		return -EINVAL;	/* Resolution to high */

	/* XXX FIXME - should try to pick best refresh rate */
	/* for now, pick closest dot-clock within 3MHz */
	req_dot = PICOS2KHZ(var->pixclock);
	printk(KERN_INFO "sgivwfb: requested pixclock=%d ps (%d KHz)\n",
	       var->pixclock, req_dot);
	test_mode = min_mode;
	while (dbeVTimings[min_mode].width == dbeVTimings[test_mode].width) {
		if (dbeVTimings[test_mode].cfreq + 3000 > req_dot)
			break;
		test_mode++;
	}
	if (dbeVTimings[min_mode].width != dbeVTimings[test_mode].width)
		test_mode--;
	min_mode = test_mode;
	timing = &dbeVTimings[min_mode];
	printk(KERN_INFO "sgivwfb: granted dot-clock=%d KHz\n", timing->cfreq);

	/* Adjust virtual resolution, if necessary */
	if (var->xres > var->xres_virtual || (!ywrap && !ypan))
		var->xres_virtual = var->xres;
	if (var->yres > var->yres_virtual || (!ywrap && !ypan))
		var->yres_virtual = var->yres;

	/*
	 *  Memory limit
	 */
	line_length = get_line_length(var->xres_virtual, var->bits_per_pixel);
	if (line_length * var->yres_virtual > sgivwfb_mem_size)
		return -ENOMEM;	/* Virtual resolution to high */

	info->fix.line_length = line_length;

	switch (var->bits_per_pixel) {
	case 8:
		var->red.offset = 0;
		var->red.length = 8;
		var->green.offset = 0;
		var->green.length = 8;
		var->blue.offset = 0;
		var->blue.length = 8;
		var->transp.offset = 0;
		var->transp.length = 0;
		break;
	case 16:		/* RGBA 5551 */
		var->red.offset = 11;
		var->red.length = 5;
		var->green.offset = 6;
		var->green.length = 5;
		var->blue.offset = 1;
		var->blue.length = 5;
		var->transp.offset = 0;
		var->transp.length = 0;
		break;
	case 32:		/* RGB 8888 */
		var->red.offset = 0;
		var->red.length = 8;
		var->green.offset = 8;
		var->green.length = 8;
		var->blue.offset = 16;
		var->blue.length = 8;
		var->transp.offset = 24;
		var->transp.length = 8;
		break;
	}
	var->red.msb_right = 0;
	var->green.msb_right = 0;
	var->blue.msb_right = 0;
	var->transp.msb_right = 0;

	/* set video timing information */
	var->pixclock = KHZ2PICOS(timing->cfreq);
	var->left_margin = timing->htotal - timing->hsync_end;
	var->right_margin = timing->hsync_start - timing->width;
	var->upper_margin = timing->vtotal - timing->vsync_end;
	var->lower_margin = timing->vsync_start - timing->height;
	var->hsync_len = timing->hsync_end - timing->hsync_start;
	var->vsync_len = timing->vsync_end - timing->vsync_start;

	/* Ouch. This breaks the rules but timing_num is only important if you
	* change a video mode */
	par->timing_num = min_mode;

	printk(KERN_INFO "sgivwfb: new video mode xres=%d yres=%d bpp=%d\n",
		var->xres, var->yres, var->bits_per_pixel);
	printk(KERN_INFO "         vxres=%d vyres=%d\n", var->xres_virtual,
		var->yres_virtual);
	return 0;
}

/*
 *  Setup flatpanel related registers.
 */
static void sgivwfb_setup_flatpanel(struct sgivw_par *par, struct dbe_timing_info *currentTiming)
{
	int fp_wid, fp_hgt, fp_vbs, fp_vbe;
	u32 outputVal = 0;

	SET_DBE_FIELD(VT_FLAGS, HDRV_INVERT, outputVal, 
		(currentTiming->flags & FB_SYNC_HOR_HIGH_ACT) ? 0 : 1);
	SET_DBE_FIELD(VT_FLAGS, VDRV_INVERT, outputVal, 
		(currentTiming->flags & FB_SYNC_VERT_HIGH_ACT) ? 0 : 1);
	DBE_SETREG(vt_flags, outputVal);

	/* Turn on the flat panel */
	switch (flatpanel_id) {
		case FLATPANEL_SGI_1600SW:
			fp_wid = 1600;
			fp_hgt = 1024;
			fp_vbs = 0;
			fp_vbe = 1600;
			currentTiming->pll_m = 4;
			currentTiming->pll_n = 1;
			currentTiming->pll_p = 0;
			break;
		default:
      			fp_wid = fp_hgt = fp_vbs = fp_vbe = 0xfff;
  	}

	outputVal = 0;
	SET_DBE_FIELD(FP_DE, FP_DE_ON, outputVal, fp_vbs);
	SET_DBE_FIELD(FP_DE, FP_DE_OFF, outputVal, fp_vbe);
	DBE_SETREG(fp_de, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(FP_HDRV, FP_HDRV_OFF, outputVal, fp_wid);
	DBE_SETREG(fp_hdrv, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(FP_VDRV, FP_VDRV_ON, outputVal, 1);
	SET_DBE_FIELD(FP_VDRV, FP_VDRV_OFF, outputVal, fp_hgt + 1);
	DBE_SETREG(fp_vdrv, outputVal);
}

/*
 *  Set the hardware according to 'par'.
 */
static int sgivwfb_set_par(struct fb_info *info)
{
	struct sgivw_par *par = info->par;
	int i, j, htmp, temp;
	u32 readVal, outputVal;
	int wholeTilesX, maxPixelsPerTileX;
	int frmWrite1, frmWrite2, frmWrite3b;
	struct dbe_timing_info *currentTiming; /* Current Video Timing */
	int xpmax, ypmax;	// Monitor resolution
	int bytesPerPixel;	// Bytes per pixel

	currentTiming = &dbeVTimings[par->timing_num];
	bytesPerPixel = bytes_per_pixel(info->var.bits_per_pixel);
	xpmax = currentTiming->width;
	ypmax = currentTiming->height;

	/* dbe_InitGraphicsBase(); */
	/* Turn on dotclock PLL */
	DBE_SETREG(ctrlstat, 0x20000000);

	dbe_TurnOffDma(par);

	/* dbe_CalculateScreenParams(); */
	maxPixelsPerTileX = 512 / bytesPerPixel;
	wholeTilesX = xpmax / maxPixelsPerTileX;
	if (wholeTilesX * maxPixelsPerTileX < xpmax)
		wholeTilesX++;

	printk(KERN_DEBUG "sgivwfb: pixPerTile=%d wholeTilesX=%d\n",
	       maxPixelsPerTileX, wholeTilesX);

	/* dbe_InitGammaMap(); */
	udelay(10);

	for (i = 0; i < 256; i++) {
		DBE_ISETREG(gmap, i, (i << 24) | (i << 16) | (i << 8));
	}

	/* dbe_TurnOn(); */
	DBE_GETREG(vt_xy, readVal);
	if (GET_DBE_FIELD(VT_XY, VT_FREEZE, readVal) == 1) {
		DBE_SETREG(vt_xy, 0x00000000);
		udelay(1);
	} else
		dbe_TurnOffDma(par);

	/* dbe_Initdbe(); */
	for (i = 0; i < 256; i++) {
		for (j = 0; j < 100; j++) {
			DBE_GETREG(cm_fifo, readVal);
			if (readVal != 0x00000000)
				break;
			else
				udelay(10);
		}

		// DBE_ISETREG(cmap, i, 0x00000000);
		DBE_ISETREG(cmap, i, (i << 8) | (i << 16) | (i << 24));
	}

	/* dbe_InitFramebuffer(); */
	frmWrite1 = 0;
	SET_DBE_FIELD(FRM_SIZE_TILE, FRM_WIDTH_TILE, frmWrite1,
		      wholeTilesX);
	SET_DBE_FIELD(FRM_SIZE_TILE, FRM_RHS, frmWrite1, 0);

	switch (bytesPerPixel) {
	case 1:
		SET_DBE_FIELD(FRM_SIZE_TILE, FRM_DEPTH, frmWrite1,
			      DBE_FRM_DEPTH_8);
		break;
	case 2:
		SET_DBE_FIELD(FRM_SIZE_TILE, FRM_DEPTH, frmWrite1,
			      DBE_FRM_DEPTH_16);
		break;
	case 4:
		SET_DBE_FIELD(FRM_SIZE_TILE, FRM_DEPTH, frmWrite1,
			      DBE_FRM_DEPTH_32);
		break;
	}

	frmWrite2 = 0;
	SET_DBE_FIELD(FRM_SIZE_PIXEL, FB_HEIGHT_PIX, frmWrite2, ypmax);

	// Tell dbe about the framebuffer location and type
	// XXX What format is the FRM_TILE_PTR??  64K aligned address?
	frmWrite3b = 0;
	SET_DBE_FIELD(FRM_CONTROL, FRM_TILE_PTR, frmWrite3b,
		      sgivwfb_mem_phys >> 9);
	SET_DBE_FIELD(FRM_CONTROL, FRM_DMA_ENABLE, frmWrite3b, 1);
	SET_DBE_FIELD(FRM_CONTROL, FRM_LINEAR, frmWrite3b, 1);

	/* Initialize DIDs */

	outputVal = 0;
	switch (bytesPerPixel) {
	case 1:
		SET_DBE_FIELD(WID, TYP, outputVal, DBE_CMODE_I8);
		break;
	case 2:
		SET_DBE_FIELD(WID, TYP, outputVal, DBE_CMODE_RGBA5);
		break;
	case 4:
		SET_DBE_FIELD(WID, TYP, outputVal, DBE_CMODE_RGB8);
		break;
	}
	SET_DBE_FIELD(WID, BUF, outputVal, DBE_BMODE_BOTH);

	for (i = 0; i < 32; i++) {
		DBE_ISETREG(mode_regs, i, outputVal);
	}

	/* dbe_InitTiming(); */
	DBE_SETREG(vt_intr01, 0xffffffff);
	DBE_SETREG(vt_intr23, 0xffffffff);

	DBE_GETREG(dotclock, readVal);
	DBE_SETREG(dotclock, readVal & 0xffff);

	DBE_SETREG(vt_xymax, 0x00000000);
	outputVal = 0;
	SET_DBE_FIELD(VT_VSYNC, VT_VSYNC_ON, outputVal,
		      currentTiming->vsync_start);
	SET_DBE_FIELD(VT_VSYNC, VT_VSYNC_OFF, outputVal,
		      currentTiming->vsync_end);
	DBE_SETREG(vt_vsync, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(VT_HSYNC, VT_HSYNC_ON, outputVal,
		      currentTiming->hsync_start);
	SET_DBE_FIELD(VT_HSYNC, VT_HSYNC_OFF, outputVal,
		      currentTiming->hsync_end);
	DBE_SETREG(vt_hsync, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(VT_VBLANK, VT_VBLANK_ON, outputVal,
		      currentTiming->vblank_start);
	SET_DBE_FIELD(VT_VBLANK, VT_VBLANK_OFF, outputVal,
		      currentTiming->vblank_end);
	DBE_SETREG(vt_vblank, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(VT_HBLANK, VT_HBLANK_ON, outputVal,
		      currentTiming->hblank_start);
	SET_DBE_FIELD(VT_HBLANK, VT_HBLANK_OFF, outputVal,
		      currentTiming->hblank_end - 3);
	DBE_SETREG(vt_hblank, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(VT_VCMAP, VT_VCMAP_ON, outputVal,
		      currentTiming->vblank_start);
	SET_DBE_FIELD(VT_VCMAP, VT_VCMAP_OFF, outputVal,
		      currentTiming->vblank_end);
	DBE_SETREG(vt_vcmap, outputVal);
	outputVal = 0;
	SET_DBE_FIELD(VT_HCMAP, VT_HCMAP_ON, outputVal,
		      currentTiming->hblank_start);
	SET_DBE_FIELD(VT_HCMAP, VT_HCMAP_OFF, outputVal,
		      currentTiming->hblank_end - 3);
	DBE_SETREG(vt_hcmap, outputVal);

	if (flatpanel_id != -1)
		sgivwfb_setup_flatpanel(par, currentTiming);

	outputVal = 0;
	temp = currentTiming->vblank_start - currentTiming->vblank_end - 1;
	if (temp > 0)
		temp = -temp;

	SET_DBE_FIELD(DID_START_XY, DID_STARTY, outputVal, (u32) temp);
	if (currentTiming->hblank_end >= 20)
		SET_DBE_FIELD(DID_START_XY, DID_STARTX, outputVal,
			      currentTiming->hblank_end - 20);
	else
		SET_DBE_FIELD(DID_START_XY, DID_STARTX, outputVal,
			      currentTiming->htotal - (20 -
						       currentTiming->
						       hblank_end));
	DBE_SETREG(did_start_xy, outputVal);

	outputVal = 0;
	SET_DBE_FIELD(CRS_START_XY, CRS_STARTY, outputVal,
		      (u32) (temp + 1));
	if (currentTiming->hblank_end >= DBE_CRS_MAGIC)
		SET_DBE_FIELD(CRS_START_XY, CRS_STARTX, outputVal,
			      currentTiming->hblank_end - DBE_CRS_MAGIC);
	else
		SET_DBE_FIELD(CRS_START_XY, CRS_STARTX, outputVal,
			      currentTiming->htotal - (DBE_CRS_MAGIC -
						       currentTiming->
						       hblank_end));
	DBE_SETREG(crs_start_xy, outputVal);

	outputVal = 0;
	SET_DBE_FIELD(VC_START_XY, VC_STARTY, outputVal, (u32) temp);
	SET_DBE_FIELD(VC_START_XY, VC_STARTX, outputVal,
		      currentTiming->hblank_end - 4);
	DBE_SETREG(vc_start_xy, outputVal);

	DBE_SETREG(frm_size_tile, frmWrite1);
	DBE_SETREG(frm_size_pixel, frmWrite2);

	outputVal = 0;
	SET_DBE_FIELD(DOTCLK, M, outputVal, currentTiming->pll_m - 1);
	SET_DBE_FIELD(DOTCLK, N, outputVal, currentTiming->pll_n - 1);
	SET_DBE_FIELD(DOTCLK, P, outputVal, currentTiming->pll_p);
	SET_DBE_FIELD(DOTCLK, RUN, outputVal, 1);
	DBE_SETREG(dotclock, outputVal);

	udelay(11 * 1000);

	DBE_SETREG(vt_vpixen, 0xffffff);
	DBE_SETREG(vt_hpixen, 0xffffff);

	outputVal = 0;
	SET_DBE_FIELD(VT_XYMAX, VT_MAXX, outputVal, currentTiming->htotal);
	SET_DBE_FIELD(VT_XYMAX, VT_MAXY, outputVal, currentTiming->vtotal);
	DBE_SETREG(vt_xymax, outputVal);

	outputVal = frmWrite1;
	SET_DBE_FIELD(FRM_SIZE_TILE, FRM_FIFO_RESET, outputVal, 1);
	DBE_SETREG(frm_size_tile, outputVal);
	DBE_SETREG(frm_size_tile, frmWrite1);

	outputVal = 0;
	SET_DBE_FIELD(OVR_WIDTH_TILE, OVR_FIFO_RESET, outputVal, 1);
	DBE_SETREG(ovr_width_tile, outputVal);
	DBE_SETREG(ovr_width_tile, 0);

	DBE_SETREG(frm_control, frmWrite3b);
	DBE_SETREG(did_control, 0);

	// Wait for dbe to take frame settings
	for (i = 0; i < 100000; i++) {
		DBE_GETREG(frm_inhwctrl, readVal);
		if (GET_DBE_FIELD(FRM_INHWCTRL, FRM_DMA_ENABLE, readVal) !=
		    0)
			break;
		else
			udelay(1);
	}

	if (i == 100000)
		printk(KERN_INFO
		       "sgivwfb: timeout waiting for frame DMA enable.\n");

	outputVal = 0;
	htmp = currentTiming->hblank_end - 19;
	if (htmp < 0)
		htmp += currentTiming->htotal;	/* allow blank to wrap around */
	SET_DBE_FIELD(VT_HPIXEN, VT_HPIXEN_ON, outputVal, htmp);
	SET_DBE_FIELD(VT_HPIXEN, VT_HPIXEN_OFF, outputVal,
		      ((htmp + currentTiming->width -
			2) % currentTiming->htotal));
	DBE_SETREG(vt_hpixen, outputVal);

	outputVal = 0;
	SET_DBE_FIELD(VT_VPIXEN, VT_VPIXEN_OFF, outputVal,
		      currentTiming->vblank_start);
	SET_DBE_FIELD(VT_VPIXEN, VT_VPIXEN_ON, outputVal,
		      currentTiming->vblank_end);
	DBE_SETREG(vt_vpixen, outputVal);

	// Turn off mouse cursor
	par->regs->crs_ctl = 0;

	// XXX What's this section for??
	DBE_GETREG(ctrlstat, readVal);
	readVal &= 0x02000000;

	if (readVal != 0) {
		DBE_SETREG(ctrlstat, 0x30000000);
	}
	return 0;
}

/*
 *  Set a single color register. The values supplied are already
 *  rounded down to the hardware's capabilities (according to the
 *  entries in the var structure). Return != 0 for invalid regno.
 */

static int sgivwfb_setcolreg(u_int regno, u_int red, u_int green,
			     u_int blue, u_int transp,
			     struct fb_info *info)
{
	struct sgivw_par *par = (struct sgivw_par *) info->par;

	if (regno > 255)
		return 1;
	red >>= 8;
	green >>= 8;
	blue >>= 8;

	/* wait for the color map FIFO to have a free entry */
	while (par->cmap_fifo == 0)
		par->cmap_fifo = par->regs->cm_fifo;

	par->regs->cmap[regno] = (red << 24) | (green << 16) | (blue << 8);
	par->cmap_fifo--;	/* assume FIFO is filling up */
	return 0;
}

static int sgivwfb_mmap(struct fb_info *info,
			struct vm_area_struct *vma)
{
	unsigned long size = vma->vm_end - vma->vm_start;
	unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;

	if (vma->vm_pgoff > (~0UL >> PAGE_SHIFT))
		return -EINVAL;
	if (offset + size > sgivwfb_mem_size)
		return -EINVAL;
	offset += sgivwfb_mem_phys;
	pgprot_val(vma->vm_page_prot) =
	    pgprot_val(vma->vm_page_prot) | _PAGE_PCD;
	vma->vm_flags |= VM_IO;
	if (remap_pfn_range(vma, vma->vm_start, offset >> PAGE_SHIFT,
						size, vma->vm_page_prot))
		return -EAGAIN;
	printk(KERN_DEBUG "sgivwfb: mmap framebuffer P(%lx)->V(%lx)\n",
	       offset, vma->vm_start);
	return 0;
}

int __init sgivwfb_setup(char *options)
{
	char *this_opt;

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

	while ((this_opt = strsep(&options, ",")) != NULL) {
		if (!strncmp(this_opt, "monitor:", 8)) {
			if (!strncmp(this_opt + 8, "crt", 3))
				flatpanel_id = -1;
			else if (!strncmp(this_opt + 8, "1600sw", 6))
				flatpanel_id = FLATPANEL_SGI_1600SW;
		}
	}
	return 0;
}

/*
 *  Initialisation
 */
static int __init sgivwfb_probe(struct platform_device *dev)
{
	struct sgivw_par *par;
	struct fb_info *info;
	char *monitor;

	info = framebuffer_alloc(sizeof(struct sgivw_par) + sizeof(u32) * 256, &dev->dev);
	if (!info)
		return -ENOMEM;
	par = info->par;

	if (!request_mem_region(DBE_REG_PHYS, DBE_REG_SIZE, "sgivwfb")) {
		printk(KERN_ERR "sgivwfb: couldn't reserve mmio region\n");
		framebuffer_release(info);
		return -EBUSY;
	}

	par->regs = (struct asregs *) ioremap_nocache(DBE_REG_PHYS, DBE_REG_SIZE);
	if (!par->regs) {
		printk(KERN_ERR "sgivwfb: couldn't ioremap registers\n");
		goto fail_ioremap_regs;
	}

	mtrr_add(sgivwfb_mem_phys, sgivwfb_mem_size, MTRR_TYPE_WRCOMB, 1);

	sgivwfb_fix.smem_start = sgivwfb_mem_phys;
	sgivwfb_fix.smem_len = sgivwfb_mem_size;
	sgivwfb_fix.ywrapstep = ywrap;
	sgivwfb_fix.ypanstep = ypan;

	info->fix = sgivwfb_fix;

	switch (flatpanel_id) {
		case FLATPANEL_SGI_1600SW:
			info->var = sgivwfb_var1600sw;
			monitor = "SGI 1600SW flatpanel";
			break;
		default:
			info->var = sgivwfb_var;
			monitor = "CRT";
	}

	printk(KERN_INFO "sgivwfb: %s monitor selected\n", monitor);

	info->fbops = &sgivwfb_ops;
	info->pseudo_palette = (void *) (par + 1);
	info->flags = FBINFO_DEFAULT;

	info->screen_base = ioremap_nocache((unsigned long) sgivwfb_mem_phys, sgivwfb_mem_size);
	if (!info->screen_base) {
		printk(KERN_ERR "sgivwfb: couldn't ioremap screen_base\n");
		goto fail_ioremap_fbmem;
	}

	if (fb_alloc_cmap(&info->cmap, 256, 0) < 0)
		goto fail_color_map;

	if (register_framebuffer(info) < 0) {
		printk(KERN_ERR "sgivwfb: couldn't register framebuffer\n");
		goto fail_register_framebuffer;
	}

	platform_set_drvdata(dev, info);

	printk(KERN_INFO "fb%d: SGI DBE frame buffer device, using %ldK of video memory at %#lx\n",      
		info->node, sgivwfb_mem_size >> 10, sgivwfb_mem_phys);
	return 0;

fail_register_framebuffer:
	fb_dealloc_cmap(&info->cmap);
fail_color_map:
	iounmap((char *) info->screen_base);
fail_ioremap_fbmem:
	iounmap(par->regs);
fail_ioremap_regs:
	release_mem_region(DBE_REG_PHYS, DBE_REG_SIZE);
	framebuffer_release(info);
	return -ENXIO;
}

static int sgivwfb_remove(struct platform_device *dev)
{
	struct fb_info *info = platform_get_drvdata(dev);

	if (info) {
		struct sgivw_par *par = info->par;

		unregister_framebuffer(info);
		dbe_TurnOffDma(par);
		iounmap(par->regs);
		iounmap(info->screen_base);
		release_mem_region(DBE_REG_PHYS, DBE_REG_SIZE);
	}
	return 0;
}

static struct platform_driver sgivwfb_driver = {
	.probe	= sgivwfb_probe,
	.remove	= sgivwfb_remove,
	.driver	= {
		.name	= "sgivwfb",
	},
};

static struct platform_device *sgivwfb_device;

int __init sgivwfb_init(void)
{
	int ret;

#ifndef MODULE
	char *option = NULL;

	if (fb_get_options("sgivwfb", &option))
		return -ENODEV;
	sgivwfb_setup(option);
#endif
	ret = platform_driver_register(&sgivwfb_driver);
	if (!ret) {
		sgivwfb_device = platform_device_alloc("sgivwfb", 0);
		if (sgivwfb_device) {
			ret = platform_device_add(sgivwfb_device);
		} else
			ret = -ENOMEM;
		if (ret) {
			platform_driver_unregister(&sgivwfb_driver);
			platform_device_put(sgivwfb_device);
		}
	}
	return ret;
}

module_init(sgivwfb_init);

#ifdef MODULE
MODULE_LICENSE("GPL");

static void __exit sgivwfb_exit(void)
{
	platform_device_unregister(sgivwfb_device);
	platform_driver_unregister(&sgivwfb_driver);
}

module_exit(sgivwfb_exit);

#endif				/* MODULE */
