head	1.22;
access;
symbols
	merge-1:1.11.2.6
	autoconf:1.11.0.4
	experimental-1:1.11.0.2
	mesa-3-1-with-kw3:1.2
	mesa-3-1-prior-to-kw3:1.1;
locks; strict;
comment	@ * @;


1.22
date	99.08.03.15.23.38;	author miklos;	state Exp;
branches;
next	1.21;

1.21
date	99.08.03.14.42.03;	author keithw;	state Exp;
branches;
next	1.20;

1.20
date	99.08.01.09.12.34;	author miklos;	state Exp;
branches;
next	1.19;

1.19
date	99.07.29.16.44.54;	author miklos;	state Exp;
branches;
next	1.18;

1.18
date	99.07.25.17.02.35;	author miklos;	state Exp;
branches;
next	1.17;

1.17
date	99.07.21.17.00.18;	author miklos;	state Exp;
branches;
next	1.16;

1.16
date	99.07.20.22.40.12;	author keithw;	state Exp;
branches;
next	1.15;

1.15
date	99.07.12.12.05.26;	author keithw;	state Exp;
branches;
next	1.14;

1.14
date	99.07.06.01.10.36;	author brianp;	state Exp;
branches;
next	1.13;

1.13
date	99.07.03.15.30.11;	author tanner;	state Exp;
branches;
next	1.12;

1.12
date	99.06.18.14.23.45;	author brianp;	state Exp;
branches;
next	1.11;

1.11
date	99.05.12.01.18.14;	author keithw;	state Exp;
branches
	1.11.2.1;
next	1.10;

1.10
date	99.05.11.17.43.00;	author keithw;	state Exp;
branches;
next	1.9;

1.9
date	99.05.03.00.33.13;	author keithw;	state Exp;
branches;
next	1.8;

1.8
date	99.05.02.00.59.25;	author keithw;	state Exp;
branches;
next	1.7;

1.7
date	99.04.22.02.21.53;	author brianp;	state Exp;
branches;
next	1.6;

1.6
date	99.04.22.02.19.26;	author brianp;	state Exp;
branches;
next	1.5;

1.5
date	99.04.08.18.05.39;	author davidb;	state Exp;
branches;
next	1.4;

1.4
date	99.03.31.20.18.41;	author keithw;	state Exp;
branches;
next	1.3;

1.3
date	99.02.25.19.13.57;	author davidb;	state Exp;
branches;
next	1.2;

1.2
date	99.02.25.14.12.33;	author keithw;	state Exp;
branches;
next	1.1;

1.1
date	99.02.24.03.46.00;	author brianp;	state Exp;
branches;
next	;

1.11.2.1
date	99.05.21.21.29.28;	author keithw;	state Exp;
branches;
next	1.11.2.2;

1.11.2.2
date	99.05.24.02.04.15;	author keithw;	state Exp;
branches;
next	1.11.2.3;

1.11.2.3
date	99.05.27.2xecute. This special
		 * case marks candidates for mandatory locking.
		 */
		newattrs.ia_mode = inode->i_mode &
			~(S_ISUID | ((inode->i_mode & S_IXGRP) ? S_ISGID : 0));
		newattrs.ia_valid = ATTR_CTIME | ATTR_MODE | ATTR_FORCE;
		notify_change(inode, &newattrs);
	}

	down(&inode->i_sem);
	error = file->f_op->write(inode,file,buf,count);
	up(&inode->i_sem);
out:
	fput(file, inode);
bad_file:
	return error;
}

static int sock_readv_writev(int type, struct inode * inode, struct file * file,
	const struct iovec * iov, long count, long size)
{
	struct msghdr msg;
	struct socket *sock;

	sock = &inode->u.socket_i;
	if (!sock->ops)
		return -EOPNOTSUPP;
	msg.msg_name = NULL;
	msg.msg_namelen = 0;
	msg.msg_control = NULL;
	msg.msg_iov = (struct iovec *) iov;
	msg.msg_iovlen = count;

	/* read() does a VERIFY_WRITE */
	if (type == VERIFY_WRITE) {
		if (!sock->ops->recvmsg)
			return -EOPNOTSUPP;
		return sock->ops->recvmsg(sock, &msg, size,
			(file->f_flags & O_NONBLOCK), 0, NULL);
	}
	if (!sock->ops->sendmsg)
		return -EOPNOTSUPP;
	return sock->ops->sendmsg(sock, &msg, size,
		(file->f_flags & O_NONBLOCK), 0);
}

typedef int (*IO_fn_t)(struct inode *, struct file *, char *, int);

static int do_readv_writev(int type, struct inode * inode, struct file * file,
	const struct iovec * vector, unsigned long count)
{
	size_t tot_len;
	struct iovec iov[UIO_MAXIOV];
	int retval, i;
	IO_fn_t fn;

	/*
	 * First get the "struct iovec" from user memory and
	 * verify all the pointers
	 */
	if (!count)
		return 0;
	if (count > UIO_MAXIOV)
		return -EINVAL;
	retval = verify_area(VERIFY_READ, vector, count*sizeof(*vector));
	if (retval)
		return retval;
	memcpy_fromfs(iov, vector, count*sizeof(*vector));
	tot_len = 0;
	for (i = 0 ; i < count ; i++) {
		tot_len += iov[i].iov_len;
		retval = verify_area(type, iov[i].iov_base, iov[i].iov_len);
		if (retval)
			return retval;
	}

	retval = locks_verify_area(type == VERIFY_READ ? FLOCK_VERIFY_READ : FLOCK_VERIFY_WRITE,
				   inode, file, file->f_pos, tot_len);
	if (retval)
		return retval;

	/*
	 * Then do the actual IO.  Note that sockets need to be handled
	 * specially as they have atomicity guarantees and can handle
	 * iovec's natively
	 */
	if (inode->i_sock)
		return sock_readv_writev(type, inode, file, iov, count, tot_len);

	if (!file->f_op)
		return -EINVAL;
	/* VERIFY_WRITE actually means a read, as we write to user space */
	fn = file->f_op->read;
	if (type == VERIFY_READ)
		fn = (IO_fn_t) file->f_op->write;		
		
	if(fn==NULL)
		return -EOPNOTSUPP;
		
	vector = iov;
	while (count > 0) {
		void * base;
		int len, nr;

		base = vector->iov_base;
		len = vector->iov_len;
		vector++;
		count--;
		nr = fn(inode, file, base, len);
		if (nr < 0) {
			if (retval)
				break;
			retval = nr;
			break;
		}
		retval += nr;
		if (nr != len)
			break;
	}
	return retval;
}

asmlinkage int sys_readv(unsigned long fd, const struct iovec * vector, long count)
{
	struct file * file;
	struct inode * inode;

	if (fd >= NR_OPEN || !(file = current->files->fd[fd]) || !(inode = file->f_inode))
		return -EBADF;
	if (!(file->f_mode & 1))
		return -EBADF;
	return do_readv_writev(VERIFY_WRITE, inode, file, vector, count);
}

asmlinkage int sys_writev(unsigned long fd, const struct iovec * vector, long count)
{
	int error;
	struct file * file;
	struct inode * inode;

	if (fd >= NR_OPEN || !(file = current->files->fd[fd]) || !(inode = file->f_inode))
		return -EBADF;
	if (!(file->f_mode & 2))
		return -EBADF;
	down(&inode->i_sem);
	error = do_readv_writev(VERIFY_READ, inode, file, vector, count);
	up(&inode->i_sem);
	return error;
}
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       /*
 *  linux/fs/block_dev.c
 *
 *  Copyright (C) 1991, 1992  Linus Torvalds
 */

#include <linux/errno.h>
#include <linux/sched.h>
#include <linux/kernel.h>
#include <linux/locks.h>
#include <linux/fcntl.h>
#include <linux/mm.h>

#include <asm/segment.h>
#include <asm/system.h>

extern int *blk_size[];
extern int *blksize_size[];

#define MAX_BUF_PER_PAGE (PAGE_SIZE / 512)
#define NBUF 64

int block_write(struct inode * inode, struct file * filp,
	const char * buf, int count)
{
	int blocksize, blocksize_bits, i, buffercount,write_error;
	int block, blocks;
	loff_t offset;
	int chars;
	int written = 0;
	struct buffer_head * bhlist[NBUF];
	unsigned int size;
	kdev_t dev;
	struct buffer_head * bh, *bufferlist[NBUF];
	register char * p;

	write_error = buffercount = 0;
	dev = inode->i_rdev;
	if ( is_read_only( inode->i_rdev ))
		return -EPERM;
	blocksize = BLOCK_SIZE;
	if (blksize_size[MAJOR(dev)] && blksize_size[MAJOR(dev)][MINOR(dev)])
		blocksize = blksize_size[MAJOR(dev)][MINOR(dev)];

	i = blocksize;
	blocksize_bits = 0;
	while(i != 1) {
		blocksize_bits++;
		i >>= 1;
	}

	block = filp->f_pos >> blocksize_bits;
	offset = filp->f_pos & (blocksize-1);

	if (blk_size[MAJOR(dev)])
		size = ((loff_t) blk_size[MAJOR(dev)][MINOR(dev)] << BLOCK_SIZE_BITS) >> blocksize_bits;
	else
		size = INT_MAX;
	while (count>0) {
		if (block >= size)
			return written ? written : -ENOSPC;
		chars = blocksize - offset;
		if (chars > count)
			chars=count;

#if 0
		/* get the buffer head */
		{
			struct buffer_head * (*fn)(kdev_t, int, int) = getblk;
			if (chars != blocksize)
				fn = bread;
			bh = fn(dev, block, blocksize);
		}
#else
		bh = getblk(dev, block, blocksize);

		if (chars != blocksize && !buffer_uptodate(bh)) {
		  if(!filp->f_reada ||
		     !read_ahead[MAJOR(dev)]) {
		    /* We do this to force the read of a single buffer */
		    brelse(bh);
		    bh = bread(dev,block,blocksize);
		  } else {
		    /* Read-ahead before write */
		    blocks = read_ahead[MAJOR(dev)] / (blocksize >> 9) / 2;
		    if (block + blocks > size) blocks = size - block;
		    if (blocks > NBUF) blocks=NBUF;
		    bhlist[0] = bh;
		    for(i=1; i<blocks; i++){
		      bhlist[i] = getblk (dev, block+i, blocksize);
		      if(!bhlist[i]){
			while(i >= 0) brelse(bhlist[i--]);
			return written ? written : -EIO;
		      };
		    };
		    ll_rw_block(READ, blocks, bhlist);
		    for(i=1; i<blocks; i++) brelse(bhlist[i]);
		    wait_on_buffer(bh);
		      
		  };
		};
#endif
		block++;
		if (!bh)
			return written ? written : -EIO;
		p = offset + bh->b_data;
		offset = 0;
		filp->f_pos += chars;
		written += chars;
		count -= chars;
		memcpy_fromfs(p,buf,chars);
		p += chars;
		buf += chars;
		mark_buffer_uptodate(bh, 1);
		mark_buffer_dirty(bh, 0);
		if (filp->f_flags & O_SYNC)
			bufferlist[buffercount++] = bh;
		else
			brelse(bh);
		if (buffercount == NBUF){
			ll_rw_block(WRITE, buffercount, bufferlist);
			for(i=0; i<buffercount; i++){
				wait_on_buffer(bufferlist[i]);
				if (!buffer_uptodate(bufferlist[i]))
					write_error=1;
				brelse(bufferlist[i]);
			}
			buffercount=0;
		}
		if(write_error)
			break;
	}
	if ( buffercount ){
		ll_rw_block(WRITE, buffercount, bufferlist);
		for(i=0; i<buffercount; i++){
			wait_on_buffer(bufferlist[i]);
			if (!buffer_uptodate(bufferlist[i]))
				write_error=1;
			brelse(bufferlist[i]);
		}
	}		
	filp->f_reada = 1;
	if(write_error)
		return -EIO;
	return written;
}

int block_read(struct inode * inode, struct file * filp,
	char * buf, int count)
{
	unsigned int block;
	loff_t offset;
	int blocksize;
	int blocksize_bits, i;
	unsigned int blocks, rblocks, left;
	int bhrequest, uptodate;
	struct buffer_head ** bhb, ** bhe;
	struct buffer_head * buflist[NBUF];
	struct buffer_head * bhreq[NBUF];
	unsigned int chars;
	loff_t size;
	kdev_t dev;
	int read;

	dev = inode->i_rdev;
	blocksize = BLOCK_SIZE;
	if (blksize_size[MAJOR(dev)] && blksize_size[MAJOR(dev)][MINOR(dev)])
		blocksize = blksize_size[MAJOR(dev)][MINOR(dev)];
	i = blocksize;
	blocksize_bits = 0;
	while (i != 1) {
		blocksize_bits++;
		i >>= 1;
	}

	off        pixel-span optimization
 *         - fixed a problem related to fxDDSetNearFar() and ctx->ProjectionMatrixType
 *           (thanks to Ben "Ctrl-Alt-Delete" and the Raul Alonso's ssystem)
 *         - fixed a small bug in the Rune's pixel-span optimization
 *         - fixed a problem with GL_CCW (thanks to Curt Olson for and example
 *           of the problem)
 *         - grVertex setup code is now ready for the internal thread support
 *         - fixed a no used optimization with clipped vertices in
 *           grVertex setup code
 *         - fixed a problem in the GL_LIGHT_MODEL_TWO_SIDE support (thanks
 *           to Patrick H. Madden for a complete example of the bug)
 *
 *         Rune Hasvold (runeh@@ifi.uio.no)
 *         - highly optimized the driver functions for writing pixel
 *           span (2-3 times faster !)
 *
 *         Axel W. Volley (volley@@acm.org) Krauss-Maffei Wehrtechnik
 *         - written the fxDDReadDepthSpanFloat() and fxDDReadDepthSpanInt()
 *           functions
 *
 * V0.25 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - fixed a problem with Voodoo boards with only one TMU
 *         - fixed a bug in the fxMesaCreateContext()
 *         - now the GL_FRONT_AND_BACK works fine also with
 *           the alpha buffer and/or antialiasing
 *         - written the support for GL_FRONT_AND_BACK drawing but
 *           it doesn't works with the alpha buffer and/or antialiasing
 *         - fixed some bug in the Mesa core for glCopyTexSubImage
 *           and glCopyTexImage functions (thanks to Mike Connell
 *           for an example of the problem)
 *         - make some small optimizations in the Mesa core in order
 *           to save same driver call and state change for not very
 *           well written applications
 *         - introduced the NEW_DRVSTATE and make other optimizations
 *           for minimizing state changes
 *         - made a lot of optimizations in order to minimize state
 *           changes
 *         - it isn't more possible to create a context with the
 *           depth buffer and the stancil buffer (it isn't yet supported)
 *         - now the partial support for the Multitexture extension
 *           works with Quake2 for windows
 *         - vertex snap is not longer used for the Voodoo2 (FX_V2
 *           must be defined)
 *         - done a lot of cleanup in the fxsetup.c file
 *         - now the partial support for the Multitexture extension
 *           works with GLQuake for windows
 *
 *         Dieter Nuetzel (nuetzel@@kogs.informatik.uni-hamburg.de) University of Hamburg
 *         - fixed a problem in the asm code for Linux of the fxvsetup.c file
 *           highlighted by the binutils-2.8.1.0.29. 'fildw' asm instruction
 *           changed in 'fild'
 *
 *         Kevin Hester (kevinh@@glassworks.net)
 *         - written the wglUseFontBitmaps() function in the WGL emulator
 *
 * V0.24 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - now the drive always uses per fragment fog
 *         - written a small optimization in the points drawing function
 *         - written the support for trilinear filtering with 2 TMUs
 *         - written the first partial support for the Multitexture extension.
 *           This task is quite hard because the color combine units work after
 *           the two texture combine units and not before as required by the 
 *           Multitexture extension
 *         - written a workaround in fxBestResolution() in order to solve a
 *           problem with bzflag (it asks for 1x1 window !)
 *         - changed the fxBestResolution() behavior. It now returns the larger
 *           screen resolution supported by the hardware (instead of 640x480)
 *           when it is unable to find an appropriate resolution that is large
 *           enough for the requested size 
 *         - the driver is now able to use also the texture memory attached to
 *           second TMU
 *         - the texture memory manager is now able to work with two TMUs and
 *           store texture maps in the memory attached to TMU0, TMU1 or to split
 *           the mimpmap levels across TMUs in order to support trilinear filtering
 *         - I have bought a Voodoo2 board !
 *         - the amount of frambuffer ram is now doubled when an SLI configuration
 *           is detected
 *         - solved a problem related to the fxDDTexParam() and fxTexInvalidate()
 *           functions (thanks to Rune Hasvold for highlighting the problem)
 *         - done some cleanup in the fxvsetup.c file, written
 *           the FXVSETUP_FUNC macro
 *         - done a lot of cleanup in data types and field names
 *
 *         Rune Hasvold (runeh@@ifi.uio.no)
 *         - written the support for a right management of the auxiliary buffer.
 *           You can now use an 800x600 screen without the depth and alpha
 *           buffer
 *         - written the support for a new pixel format (without the depth
 *           and alpha buffer) in the WGL emulator
 *         - fixed a bug in the window version of the GLUT (it was ever asking
 *           for depth buffer)
 *
 * V0.23 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - included in the Mesa-3.0beta2 release
 *         - written the support for the OpenGL 1.2 GL_TEXTURE_BASE_LEVEL
 *           and GL_TEXTURE_MAX_LEVEL
 *         - rewritten several functions for a more clean support of texture
 *           mapping and in order to solve some bug
 *         - the accumulation buffer works (it is  bit slow beacuase it requires
 *           to read/write from/to the Voodoo frame buffer but it works)
 *         - fixed a bug in the fxDDReadRGBASpan driver function (the R and
 *           B channels were read in the wrong order). Thanks to Jason Heym
 *           for highlighting the problem
 *         - written the support for multiple contexts on multiple boards.
 *           you can now use the Mesa/Voodoo with multiple Voodoo Graphics
 *           boards (for example with multiple screens or an HMD)
 *         - the fxBestResolution() now check all available resolutions
 *           and it is able to check the amount of framebuffer memory
 *           before return a resolution
 *         - modified the GLX/X11 driver in order to support all the
 *           resolution available
 *         - changed all function names. They should be now a bit more
 *           readable
 *         - written the Glide grVertex setup code for two TMU or
 *           for Multitexture support with emulationa dn one TMU
 *         - written the support for the new Mesa driver
 *           function GetParametri
 *         - small optimization/clean up in the texbind() function
 *         - fixed a FPU precision problem for glOrtho and texture
 *           mapping (thanks to Antti Juhani Huovilainen for an example
 *           of the problem)
 *         - written some small SGI OpenGL emulation code for the wgl,
 *           the OpenGL Optimizer and Cosmo3D work fine under windows !
 *         - moved the point/line/triangle/quad support in the fxmesa7.c
 *         - fixed a bug in the clear_color_depth() (thanks to Henk Kok
 *           for an example of the problem)
 *         - written a small workaround for Linux GLQuake, it asks
 *           for the alpha buffer and the depth buffer at the some time
 *           (but it never uses the alpha buffer)
 *         - checked the antialiasing points, lines and polygons support.
 *           It works fine
 *         - written the support for standard OpenGL antialiasing using
 *           blending. Lines support works fine (tested with BZflag)
 *           while I have still to check the polygons and points support
 *         - written the support for the alpha buffer. The driver is now
 *           able to use the Voodoo auxiliary buffer as an alpha buffer
 *           instead of a depth buffer. Also all the OpenGL blending
 *           modes are now supported. But you can't request a context
 *           with an alpha buffer AND a depth buffer at the some time
 *           (this is an hardware limitation)
 *         - written the support for switching between the fullscreen
 *           rendering and the in-window-rendering hack on the fly
 *
 *         Rune Hasvold (runeh@@ifi.uio.no)
 *         - fixed a bug in the texparam() function
 *
 *         Brian Paul (brianp@@elastic.avid.com) Avid Technology
 *         - sources accomodated for the new Mesa 3.0beta1
 *
 * V0.22 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - included with some v0.23 bug fix in the final release
 *           of the Mesa-2.6
 *         - written the support for the MESA_WGL_FX env. var. but
 *           not tested because I have only Voodoo Graphics boards
 *         - fixed a bug in the backface culling code
 *           (thanks to David Farrell for an example of the problem)
 *         - fixed the "Quake2 elevator" bug
 *         - GL_POLYGONS with 3/4 vertices are now drawn as
 *           GL_TRIANLGES/GL_QUADS (a small optimization for GLQuake)
 *         - fixed a bug in fxmesa6.h for GL_LINE_LOOP
 *         - fixed a NearFarStack bug in the Mesa when applications
 *           directly call glLoadMatrix to load a projection matrix 
 *         - done some cleanup in the fxmesa2.c file
 *         - the driver no longer translates the texture maps
 *           when the Mesa internal format and the Voodoo
 *           format are the some (usefull for 1 byte texture maps
 *           where the driver can directly use the Mesa texture
 *           map). Also the amount of used memory is halfed
 *         - fixed a bug for GL_DECAL and GL_RGBA
 *         - fixed a bug in the clear_color_depth()
 *         - tested the v0.22 with the Mesa-2.6beta2. Impressive
 *           performances improvement thanks to the new Josh's
 *           asm code (+10fps in the isosurf demo, +5fps in GLQuake
 *           TIMEREFRESH)
 *         - written a optimized version of the RenderVB Mesa driver
 *           function. The Voodoo driver is now able to upload polygons
 *           in the most common cases at a very good speed. Good
 *           performance improvement for large set of small polygons
 *         - optimized the asm code for setting up the color information
 *           in the Glide grVertex structure
 *         - fixed a bug in the fxmesa2.c asm code (the ClipMask[]
 *           wasn't working)
 *
 *         Josh Vanderhoof (joshv@@planet.net)
 *         - removed the flush() function because it isn't required
 *         - limited the maximum number of swapbuffers in the Voodoo
 *           commands FIFO (controlled by the env. var. MESA_FX_SWAP_PENDING)
 *
 *         Holger Kleemiss (holger.kleemiss@@metronet.de) STN Atlas Elektronik GmbH
 *         - applied some patch for the Voodoo Rush
 *
 * V0.21 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - the driver is now able to take advantage of the ClipMask[],
 *           ClipOrMask and ClipAndMask information also under Windows
 *         - introduced a new function in the Mesa driver interface
 *           ClearColorAndDepth(). Now the glClear() function is
 *           2 times faster (!) when you have to clear the color buffer
 *           and the depth buffer at some time
 *         - written the first version of the fxRenderVB() driver
 *           function
 *         - optimized the glTexImage() path
 *         - removed the fxMesaTextureUsePalette() support
 *         - fixed a bug in the points support (thanks to David Farrell
 *           for an example of the problem)
 *         - written the optimized path for glSubTexImage(),
 *           introduced a new function in the Mesa driver interface
 *           TexSubImage(...)
 *         - fixed a bug for glColorMask and glDepthMask
 *         - the wbuffer is not more used. The Voodoo driver uses
 *           a standard 16bit zbuffer in all cases. It is more consistent
 *           and now GLQuake and GLQuake2test work also with a GL_ZTRICK 0
 *         - the driver is now able to take advantage of the ClipMask[],
 *           ClipOrMask and ClipAndMask information (under Linux);
 *         - rewritten the setup_fx_units() function, now the texture
 *           mapping support is compliant to the OpenGL specs (GL_BLEND
 *           support is still missing). The LinuxGLQuake console correctly
 *           fade in/out and transparent water of GLQuake2test works fine
 *         - written the support for the env. var. FX_GLIDE_SWAPINTERVAL
 *         - found a bug in the Mesa core. There is a roundup problem for
 *           color values out of the [0.0,1.0] range
 *
 *         Wonko <matt@@khm.de>
 *         - fixed a Voodoo Rush related problem in the fxwgl.c
 *
 *         Daryll Strauss <daryll@@harlot.rb.ca.us>
 *         - written the scissor test support
 *
 * V0.20 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - written the closetmmanger() function in order to free all the memory
 *           allocated by the Texture Memory Manager (it will be useful
 *           when the support for multiple contexts/boards will be ready)
 *         - now the Voodoo driver runs without printing any information,
 *           define the env. var. MESA_FX_INFO if you want to read some
 *           information about the hardware and some statistic
 *         - written a small workaround for the "GLQuake multiplayer white box bug"
 *           in the setup_fx_units() funxtions. I'm already rewriting
 *           this function because it is the source of nearly all the current
 *           Voodoo driver problems
 *         - fixed the GLQuake texture misalignment problem (the texture
 *           coordinates must be scaled between 0.0 and 256.0 and not
 *           between 0.0 and 255.0)
 *         - written the support for the GL_EXT_shared_texture_palette
 *         - some small change for supporting the automatic building of the
 *           OpenGL32.dll under the Windows platform
 *         - the redefinition of a mipmap level is now a LOT faster. This path
 *           is used by GLQuake for dynamic lighting with some call to glTexSubImage2D()
 *         - the texture memory is now managed a set of 2MB blocks so
 *           texture maps can't be allocated on a 2MB boundary. The new Pure3D
 *           needs this kind of support (and probably any other Voodoo Graphics
 *           board with more than 2MB of texture memory)
 *
 *         Brian Paul (brianp@@elastic.avid.com) Avid Technology
 *         - added write_monocolor_span(), fixed bug in write_color_span()
 *         - added test for stenciling in choosepoint/line/triangle functions
 *
 *         Joe Waters (falc@@attila.aegistech.com) Aegis
 *         - written the support for the env. var. SST_SCREENREFRESH
 *
 * V0.19 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - written the 3Dfx Global Palette extension for GLQuake
 *         - written the support for the GL_EXT_paletted_texture (it works only with GL_RGBA
 *           palettes and the alpha value is ignored ... this is a limitation of the
 *           the current Glide version and Voodoo hardware)
 *         - fixed the amount of memory allocated for 8bit textures
 *         - merged the under construction v0.19 driver with the Mesa 2.5
 *         - finally written the support for deleting textures
 *         - introduced a new powerful texture memory manager: the texture memory
 *           is used as a cache of the set of all defined texture maps. You can
 *           now define several MB of texture maps also with a 2MB of texture memory
 *           (the texture memory manager will do automatically all the swap out/swap in
 *           work). The new texture memory manager has also
 *           solved a lot of other bugs/no specs compliance/problems
 *           related to the texture memory usage. The texture
 *           manager code is inside the new fxmesa3.c file
 *         - broken the fxmesa.c file in two files (fxmesa1.c and fxmesa2.c)
 *           and done some code cleanup
 *         - now is possible to redefine texture mipmap levels already defined
 *         - fixed a problem with the amount of texture memory allocated for textures
 *           with not all mipmap levels defined
 *         - fixed a small problem with single buffer rendering
 *
 *         Brian Paul (brianp@@elastic.avid.com) Avid Technology
 *         - read/write_color_span() now use front/back buffer correctly
 *         - create GLvisual with 5,6,5 bits per pixel, not 8,8,8
 *         - removed a few ^M characters from fxmesa2.c file
 *
 * V0.18 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - the Mesa-2.4beta3 is finally using the driver quads support (the
 *           previous Mesa versions have never taken any advantage from the quads support !)
 *         - tested with the Glide 2.4 for Win
 *         - ported all asm code to Linux
 *         - ported the v0.18 to Linux (without asm code)
 *         - back to Linux !!!
 *         - optimized the SETUP macro (no more vertex snap for points and lines)
 *         - optimized the SETUP macro (added one argument)
 *         - the Mesa/Voodoo is now 20/30% for points, lines and small triangles !
 *         - performance improvement setting VBSIZE to 72 
 *         - the GrVertex texture code is now written in asm
 *         - the GrVertex zbuffer code is now written in asm
 *         - the GrVertex wbuffer code is now written in asm
 *         - the GrVertex gouraud code is now written in asm
 *         - the GrVertex snap code is now written in asm
 *         - changed the 8bit compressed texture maps in 8bit palette texture maps
 *           support (it has the some advantage of compressed texture maps without the
 *           problem of a fixed NCC table for all mipmap levels)
 *         - written the support for 8bit compressed texture maps (but texture maps with
 *           more than one mipmap level aren't working fine)
 *         - finnaly everthing is working fine in MesaQuake !
 *         - fixed a bug in the computation of texture mapping coordinates (I have found
 *           the bug thanks to MesaQuake !)
 *         - written the GL_REPLACE support (mainly for MesaQuake)
 *         - written the support for textures with not all mipmap levels defined
 *         - rewritten all the Texture memory stuff
 *         - written the MesaQuake support (define MESAQUAKE)
 *         - working with a ZBuffer if glOrtho or not int the default glDepthRange,
 *           otherwise working with the WBuffer
 *         written the glDepthRange support
 *
 *         Diego Picciani (d.picciani@@novacomp.it) Nova Computer s.r.l.
 *         - written the fxCloseHardware() and the fxQuaryHardware() (mainly
 *           for the VoodooWGL emulator)
 *
 *         Brian Paul (brianp@@elastic.avid.com) Avid Technology
 *         - implemented read/write_color_span() so glRead/DrawPixels() works
 *         - now needs Glide 2.3 or later.  Removed GLIDE_FULL_SCREEN and call to grSstOpen()
 *
 * V0.17 - David Bucciarelli (tech.hmw@@plus.it) Humanware s.r.l.
 *         - optimized the bitmap support (66% faster)
 *         - tested with the Mesa 2.3beta2
 *
 *         Diego Picciani (d.picciani@@novacomp.it) Nova Computer s.r.l.
 *         - solved a problem with nls)
{
	struct nls_table ** tmp = &tables;

	if (!nls)
		return -EINVAL;
	if (nls->next)
		return -EBUSY;
	while (*tmp) {
		if (nls == *tmp) {
			return -EBUSY;
		}
		tmp = &(*tmp)->next;
	}
	nls->next = tables;
	tables = nls;
	return 0;	
}

int unregister_nls(struct nls_table * nls)
{
	struct nls_table ** tmp = &tables;

	while (*tmp) {
		if (nls == *tmp) {
			*tmp = nls->next;
			return 0;
		}
		tmp = &(*tmp)->next;
	}
	return -EINVAL;
}

struct nls_table *find_nls(char *charset)
{
	struct nls_table *nls = tables;
	while (nls) {
		if (! strcmp(nls->charset, charset))
			return nls;
		nls = nls->next;
	}
	return NULL;
}

struct nls_table *load_nls(char *charset)
{
	struct nls_table *nls;
#ifdef CONFIG_KERNELD
	char buf[40];
	int ret;
#endif

	nls = find_nls(charset);
	if (nls) {
		nls->inc_use_count();
		return nls;
	}

#ifndef CONFIG_KERNELD
	return NULL;
#else
	if (strlen(charset) > sizeof(buf) - sizeof("nls_")) {
		printk("Unable to load NLS charset %s: name too long\n", charset);
		return NULL;
	}
		
	sprintf(buf, "nls_%s", charset);
	ret = strlen(buf);

	/* Hack to get around genksyms problem */
	if (buf[ret-2] == '-')
		buf[ret-2] = '_';
	if (buf[ret-3] == '-')
		buf[ret-3] = '_';

	ret = request_module(buf);
	if (ret != 0) {
		printk("Unable to load NLS charset %s(%s)\n", charset, buf);
		return NULL;
	}
	nls = find_nls(charset);
	if (nls) {
		nls->inc_use_count();
	}
	return nls;
#endif
}

void unload_nls(struct nls_table *nls)
{
	nls->dec_use_count();
}

struct nls_unicode charset2uni[256] = {
	/* 0x00*/
	{0x00, 0x00}, {0x01, 0x00}, {0x02, 0x00}, {0x03, 0x00},
	{0x04, 0x00}, {0x05, 0x00}, {0x06, 0x00}, {0x07, 0x00},
	{0x08, 0x00}, {0x09, 0x00}, {0x0a, 0x00}, {0x0b, 0x00},
	{0x0c, 0x00}, {0x0d, 0x00}, {0x0e, 0x00}, {0x0f, 0x00},
	/* 0x10*/
	{0x10, 0x00}, {0x11, 0x00}, {0x12, 0x00}, {0x13, 0x00},
	{0x14, 0x00}, {0x15, 0x00}, {0x16, 0x00}, {0x17, 0x00},
	{0x18, 0x00}, {0x19, 0x00}, {0x1a, 0x00}, {0x1b, 0x00},
	{0x1c, 0x00}, {0x1d, 0x00}, {0x1e, 0x00}, {0x1f, 0x00},
	/* 0x20*/
	{0x20, 0x00}, {0x21, 0x00}, {0x22, 0x00}, {0x23, 0x00},
	{0x24, 0x00}, {0x25, 0x00}, {0x26, 0x00}, {0x27, 0x00},
	{0x28, 0x00}, {0x29, 0x00}, {0x2a, 0x00}, {0x2b, 0x00},
	{0x2c, 0x00}, {0x2d, 0x00}, {0x2e, 0x00}, {0x2f, 0x00},
	/* 0x30*/
	{0x30, 0x00}, {0x31, 0x00}, {0x32, 0x00}, {0x33, 0x00},
	{0x34, 0x00}, {0x35, 0x00}, {0x36, 0x00}, {0x37, 0x00},
	{0x38, 0x00}, {0x39, 0x00}, {0x3a, 0x00}, {0x3b, 0x00},
	{0x3c, 0x00}, {0x3d, 0x00}, {0x3e, 0x00}, {0x3f, 0x00},
	/* 0x40*/
	{0x40, 0x00}, {0x41, 0x00}, {0x42, 0x00}, {0x43, 0x00},
	{0x44, 0x00}, {0x45, 0x00}, {0x46, 0x00}, {0x47, 0x00},
	{0x48, 0x00}, {0x49, 0x00}, {0x4a, 0x00}, {0x4b, 0x00},
	{0x4c, 0x00}, {0x4d, 0x00}, {0x4e, 0x00}, {0x4f, 0x00},
	/* 0x50*/
	{0x50, 0x00}, {0x51, 0x00}, {0x52, 0x00}, {0x53, 0x00},
	{0x54, 0x00}, {0x55, 0x00}, {0x56, 0x00}, {0x57, 0x00},
	{0x58, 0x00}, {0x59, 0x00}, {0x5a, 0x00}, {0x5b, 0x00},
	{0x5c, 0x00}, {0x5d, 0x00}, {0x5e, 0x00}, {0x5f, 0x00},
	/* 0x60*/
	{0x60, 0x00}, {0x61, 0x00}, {0x62, 0x00}, {0x63, 0x00},
	{0x64, 0x00}, {0x65, 0x00}, {0x66, 0x00}, {0x67, 0x00},
	{0x68, 0x00}, {0x69, 0x00}, {0x6a, 0x00}, {0x6b, 0x00},
	{0x6c, 0x00}, {0x6d, 0x00}, {0x6e, 0x00}, {0x6f, 0x00},
	/* 0x70*/
	{0x70, 0x00}, {0x71, 0x00}, {0x72, 0x00}, {0x73, 0x00},
	{0x74, 0x00}, {0x75, 0x00}, {0x76, 0x00}, {0x77, 0x00},
	{0x78, 0x00}, {0x79, 0x00}, {0x7a, 0x00}, {0x7b, 0x00},
	{0x7c, 0x00}, {0x7d, 0x00}, {0x7e, 0x00}, {0x7f, 0x00},
	/* 0x80*/
	{0x80, 0x00}, {0x81, 0x00}, {0x82, 0x00}, {0x83, 0x00},
	{0x84, 0x00}, {0x85, 0x00}, {0x86, 0x00}, {0x87, 0x00},
	{0x88, 0x00}, {0x89, 0x00}, {0x8a, 0x00}, {0x8b, 0x00},
	{0x8c, 0x00}, {0x8d, 0x00}, {0x8e, 0x00}, {0x8f, 0x00},
	/* 0x90*/
	{0x90, 0x00}, {0x91, 0x00}, {0x92, 0x00}, {0x93, 0x00},
	{0x94, 0x00}, {0x95, 0x00}, {0x96, 0x00}, {0x97, 0x00},
	{0x98, 0x00}, {0x99, 0x00}, {0x9a, 0x00}, {0x9b, 0x00},
	{0x9c, 0x00}, {0x9d, 0x00}, {0x9e, 0x00}, {0x9f, 0x00},
	/* 0xa0*/
	{0xa0, 0x00}, {0xa1, 0x00}, {0xa2, 0x00}, {0xa3, 0x00},
	{0xa4, 0x00}, {0xa5, 0x00}, {0xa6, 0x00}, {0xa7, 0x00},
	{0xa8, 0x00}, {0xa9, 0x00}, {0xaa, 0x00}, {0xab, 0x00},
	{0xac, 0x00}, {0xad, 0x00}, {0xae, 0x00}, {0xaf, 0x00},
	/* 0xb0*/
	{0xb0, 0x00}, {0xb1, 0x00}, {0xb2, 0x00}, {0xb3, 0x00},
	{0xb4, 0x00}, {0xb5, 0x00}, {0xb6, 0x00}, {0xb7, 0x00},
	{0xb8, 0x00}, {0xb9, 0x00}, {0xba, 0x00}, {0xbb, 0x00},
	{0xbc, 0x00}, {0xbd, 0x00}, {0xbe, 0x00}, {0xbf, 0x00},
	/* 0xc0*/
	{0xc0, 0x00}, {0xc1, 0x00}, {0xc2, 0x00}, {0xc3, 0x00},
	{0xc4, 0x00}, {0xc5, 0x00}, {0xc6, 0x00}, {0xc7, 0x00},
	{0xc8, 0x00}, {0xc9, 0x00}, {0xca, 0x00}, {0xcb, 0x00},
	{0xcc, 0x00}, {0xcd, 0x00}, {0xce, 0x00}, {0xcf, 0x00},
	/* 0xd0*/
	{0xd0, 0x00}, {0xd1, 0x00}, {0xd2, 0x00}, {0xd3, 0x00},
	{0xd4, 0x00}, {0xd5, 0x00}, {0xd6, 0x00}, {0xd7, 0x00},
	{0xd8, 0x00}, {0xd9, 0x00}, {0xda, 0x00}, {0xdb, 0x00},
	{0xdc, 0x00}, {0xdd, 0x00}, {0xde, 0x00}, {0xdf, 0x00},
	/* 0xe0*/
	{0xe0, 0x00}, {0xe1, 0x00}, {0xe2, 0x00}, {0xe3, 0x00},
	{0xe4, 0x00}, {0xe5, 0x00}, {0xe6, 0x00}, {0xe7, 0x00},
	{0xe8, 0x00}, {0xe9, 0x00}, {0xea, 0x00}, {0xeb, 0x00},
	{0xec, 0x00}, {0xed, 0x00}, {0xee, 0x00}, {0xef, 0x00},
	/* 0bCurrentBoard=0;


#if defined(__WIN32__)
static int cleangraphics(void)
{
  glbTotNumCtx=1;
  fxMesaDestroyContext(fxMesaCurrentCtx);

  return 0;
}
#elif defined(__linux__)
static void cleangraphics(void)
{
  glbTotNumCtx=1;
  fxMesaDestroyContext(fxMesaCurrentCtx);
}

static void cleangraphics_handler(int s)
{
  fprintf(stderr,"fxmesa: Received a not handled signal %d\n",s);

  cleangraphics();
/*    abort(); */
  exit(1);
}
#endif


/*
 * Select the Voodoo board to use when creating
 * a new context.
 */
GLboolean GLAPIENTRY fxMesaSelectCurrentBoard(int n)
{
  fxQueryHardware();

  if((n<0) || (n>=glbHWConfig.num_sst))
    return GL_FALSE;

  glbCurrentBoard=n;

  return GL_TRUE;
}


fxMesaContext GLAPIENTRY fxMesaGetCurrentContext(void)
{
  return fxMesaCurrentCtx;
}


void GLAPIENTRY fxMesaSetNearFar(GLfloat n, GLfloat f)
{
  if(fxMesaCurrentCtx)
    fxDDSetNearFar(fxMesaCurrentCtx->glCtx,n,f);
}


/*
 * The extension GL_FXMESA_global_texture_lod_bias
 */
void GLAPIENTRY glGlobalTextureLODBiasFXMESA(GLfloat biasVal)
{
  grTexLodBiasValue(GR_TMU0,biasVal);

  if(fxMesaCurrentCtx->haveTwoTMUs)
    grTexLodBiasValue(GR_TMU1,biasVal);
}


/*
 * The 3Dfx Global Palette extension for GLQuake.
 * More a trick than a real extesion, use the shared global
 * palette extension. 
 */
void GLAPIENTRY gl3DfxSetPaletteEXT(GLuint *pal)
{
  fxMesaContext fxMesa =fxMesaCurrentCtx;
  
  if (MESA_VERBOSE&VERBOSE_DRIVER) {
    int i;

    fprintf(stderr,"fxmesa: gl3DfxSetPaletteEXT()\n");

    for(i=0;i<256;i++)
      fprintf(stderr,"%x\n",pal[i]);
  }
  
  if(fxMesa) {
    fxMesa->haveGlobalPaletteTexture=1;
    
    FX_grTexDownloadTable(GR_TMU0,GR_TEXTABLE_PALETTE,(GuTexPalette *)pal);
    if (fxMesa->haveTwoTMUs)
    	 FX_grTexDownloadTable(GR_TMU1,GR_TEXTABLE_PALETTE,(GuTexPalette *)pal);
  }
}


static GrScreenResolution_t fxBestResolution(int width, int height, int aux)
{
  static int resolutions[][5]={ 
    { 512, 384, GR_RESOLUTION_512x384, 2, 2 },
    { 640, 400, GR_RESOLUTION_640x400, 2, 2 },
    { 640, 480, GR_RESOLUTION_640x480, 2, 2 },
    { 800, 600, GR_RESOLUTION_800x600, 4, 2 },
    { 960, 720, GR_RESOLUTION_960x720, 6, 4 }
#ifdef GR_RESOLUTION_1024x768
    ,{ 1024, 768, GR_RESOLUTION_1024x768, 8, 4 }
#endif
#ifdef GR_RESOLUTION_1280x1024
    ,{ 1024, 768, GR_RESOLUTION_1280x1024, 8, 8 }
#endif
#ifdef GR_RESOLUTION_1600x1200
    ,{ 1024, 768, GR_RESOLUTION_1600x1200, 16, 8 }
#endif
  };
  int NUM_RESOLUTIONS = sizeof(resolutions) / (sizeof(int)*5);
  int i,fbmem;
  GrScreenResolution_t lastvalidres=resolutions[1][2];

  fxQueryHardware();

  if(glbHWConfig.SSTs[glbCurrentBoard].type==GR_SSTTYPE_VOODOO) {
    fbmem=glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig.fbRam;

    if(glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig.sliDetect)
      fbmem*=2;
  } else if(glbHWConfig.SSTs[glbCurrentBoard].type==GR_SSTTYPE_SST96)
    fbmem=glbHWConfig.SSTs[glbCurrentBoard].sstBoard.SST96Config.fbRam;
  else
    fbmem=2;

  /* A work around for BZFlag */

  if((width==1) && (height==1)) {
    width=640;
    height=480;
  }

  for(i=0;i<NUM_RESOLUTIONS;i++)
    if(resolutions[i][4-aux]<=fbmem) {
      if((width<=resolutions[i][0]) && (height<=resolutions[i][1]))
        return resolutions[i][2];

      lastvalidres=resolutions[i][2];
    }

  return lastvalidres;
}


fxMesaContext GLAPIENTRY fxMesaCreateBestContext(GLuint win,GLint width, GLint height,
					       const GLint attribList[])
{
  GrScreenRefresh_t refresh;
  int i;
  int res,aux;
  refresh=GR_REFRESH_75Hz;

  if(getenv("SST_SCREENREFRESH")) {
    if(!strcmp(getenv("SST_SCREENREFRESH"),"60"))
      refresh=GR_REFRESH_60Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"70"))
      refresh=GR_REFRESH_70Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"72"))
      refresh=GR_REFRESH_72Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"75"))
      refresh=GR_REFRESH_75Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"80"))
      refresh=GR_REFRESH_80Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"85"))
      refresh=GR_REFRESH_85Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"90"))
      refresh=GR_REFRESH_90Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"100"))
      refresh=GR_REFRESH_100Hz;
    if(!strcmp(getenv("SST_SCREENREFRESH"),"120"))
      refresh=GR_REFRESH_120Hz;
  }

  aux=0;
  for(i=0;attribList[i]!=FXMESA_NONE;i++)
    if((attribList[i]==FXMESA_ALPHA_SIZE) ||
       (attribList[i]==FXMESA_DEPTH_SIZE)) {
      if(attribList[++i]>0) {
        aux=1;
        break;
      }
    }

  res=fxBestResolution(width,height,aux);

  return fxMesaCreateContext(win,res,refresh,attribList);
}


#if 0
void fxsignals()
{
   signal(SIGINT,SIG_IGN);
   signal(SIGHUP,SIG_IGN);
   signal(SIGPIPE,SIG_IGN);
   signal(SIGFPE,SIG_IGN);
   signal(SIGBUS,SIG_IGN);
   signal(SIGILL,SIG_IGN);
   signal(SIGSEGV,SIG_IGN);
   signal(SIGTERM,SIG_IGN);
}
#endif

/*
 * Create a new FX/Mesa context and return a handle to it.
 */
fxMesaContext GLAPIENTRY fxMesaCreateContext(GLuint win,GrScreenResolution_t res,
					   GrScreenRefresh_t ref,
					   const GLint attribList[])
{
  fxMesaContext /* 0x60-0x67 */
	0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, /* 0x68-0x6f */
	0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, /* 0x70-0x77 */
	0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0xff, 0xad, 0x9b, 0x9c, 0x00, 0x00, 0x00, 0x00, /* 0xa0-0xa7 */
	0x00, 0x00, 0xa6, 0xae, 0xaa, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0xf8, 0xf1, 0xfd, 0x00, 0x00, 0xe6, 0x00, 0xfa, /* 0xb0-0xb7 */
	0x00, 0x00, 0xa7, 0xaf, 0xac, 0xab, 0x00, 0xa8, /* 0xb8-0xbf */
	0x91, 0x86, 0x8f, 0x8e, 0x00, 0x00, 0x00, 0x80, /* 0xc0-0xc7 */
	0x92, 0x90, 0x89, 0x00, 0x98, 0x8b, 0x00, 0x00, /* 0xc8-0xcf */
	0x00, 0xa5, 0xa9, 0x9f, 0x8c, 0x99, 0x00, 0x00, /* 0xd0-0xd7 */
	0x00, 0x9d, 0x96, 0x00, 0x9a, 0x00, 0x00, 0xe1, /* 0xd8-0xdf */
	0x85, 0xa0, 0x83, 0x84, 0x00, 0x00, 0x00, 0x87, /* 0xe0-0xe7 */
	0x8a, 0x82, 0x88, 0x00, 0x8d, 0xa1, 0x00, 0x00, /* 0xe8-0xef */
	0x00, 0xa4, 0x95, 0xa2, 0x93, 0x94, 0x00, 0xf6, /* 0xf0-0xf7 */
	0x00, 0x97, 0xa3, 0x00, 0x81, 0x00, 0x00, 0x00, /* 0xf8-0xff */
};

static unsigned char page03[256] = {
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x00-0x07 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x08-0x0f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x10-0x17 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x18-0x1f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x27 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x28-0x2f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x30-0x37 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x38-0x3f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x40-0x47 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x48-0x4f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x50-0x57 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x58-0x5f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x60-0x67 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x68-0x6f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x70-0x77 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0xe2, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0xe9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0x00, 0x00, 0x00, 0xe4, 0x00, 0x00, 0xe8, 0x00, /* 0xa0-0xa7 */
	0x00, 0xea, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0x00, 0xe0, 0x00, 0x00, 0xeb, 0xee, 0x00, 0x00, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb8-0xbf */
	0xe3, 0x00, 0x00, 0xe5, 0xe7, 0x00, 0xed, 0x00, /* 0xc0-0xc7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc8-0xcf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xd0-0xd7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xd8-0xdf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe0-0xe7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe8-0xef */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf0-0xf7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf8-0xff */
};

static unsigned char page20[256] = {
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x00-0x07 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x08-0x0f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x10-0x17 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x18-0x1f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x27 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x28-0x2f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x30-0x37 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x38-0x3f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x40-0x47 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x48-0x4f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x50-0x57 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x58-0x5f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x60-0x67 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x68-0x6f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x70-0x77 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfc, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9e, /* 0xa0-0xa7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb8-0xbf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc0-0xc7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc8-0xcf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xd0-0xd7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xd8-0xdf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe0-0xe7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe8-0xef */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf0-0xf7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf8-0xff */
};

static unsigned char page22[256] = {
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x00-0x07 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x08-0x0f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x10-0x17 */
	0x00, 0xf9, 0xfb, 0x00, 0x00, 0x00, 0xec, 0x00, /* 0x18-0x1f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x27 */
	0x00, 0xef, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x28-0x2f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x30-0x37 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x38-0x3f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x40-0x47 */
	0xf7, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x48-0x4f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x50-0x57 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x58-0x5f */
	0x00, 0xf0, 0x00, 0x00, 0xf3, 0xf2, 0x00, 0x00, /* 0x60-0x67 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x68-0x6f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x70-0x77 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa0-0xa7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb8-0xbf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc0-0xc7 */
	0x00!C "C #C $C %C &C 'C (C                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 OSE_DRIVER) {
    fprintf(stderr,"fxmesa: fxMesaCreateContext() End\n");
  }

  return fxMesa;

errorhandler:
   if (fxMesa) {
      if (fxMesa->glideContext)
      	FX_grSstWinClose(fxMesa->glideContext);
      fxMesa->glideContext = 0;
      
      if (fxMesa->state)  
     	free(fxMesa->state);
      if (fxMesa && fxMesa->fogTable)
     	free(fxMesa->fogTable);
      if (fxMesa->glBuffer)
      	gl_destroy_framebuffer(fxMesa->glBuffer);
      if (fxMesa->glVis)
      	gl_destroy_visual(fxMesa->glVis);
      if (fxMesa->glCtx)
      	gl_destroy_context(fxMesa->glCtx);
      free(fxMesa);
   }



     

  if (MESA_VERBOSE&VERBOSE_DRIVER) {
      fprintf(stderr,"fxmesa: fxMesaCreateContext() End (%s)\n",errorstr);
  }
  return NULL;
}


/*
 * Function to set the new window size in the context (mainly for the Voodoo Rush)
 */
void GLAPIENTRY fxMesaUpdateScreenSize(fxMesaContext fxMesa)
{
  fxMesa->width=FX_grSstScreenWidth();
  fxMesa->height=FX_grSstScreenHeight();
}


/*
 * Destroy the given FX/Mesa context.
 */
void GLAPIENTRY fxMesaDestroyContext(fxMesaContext fxMesa)
{
  if (MESA_VERBOSE&VERBOSE_DRIVER) {
    fprintf(stderr,"fxmesa: fxMesaDestroyContext()\n");
  }

  if(fxMesa) {
    gl_destroy_visual(fxMesa->glVis);
    gl_destroy_context(fxMesa->glCtx);
    gl_destroy_framebuffer(fxMesa->glBuffer);

    glbTotNumCtx--;

    fxCloseHardware();
    FX_grSstWinClose(fxMesa->glideContext);

    if(fxMesa->verbose) {
      fprintf(stderr,"Misc Stats:\n");
      fprintf(stderr,"  # swap buffer: %u\n",fxMesa->stats.swapBuffer);

      if(!fxMesa->stats.swapBuffer)
        fxMesa->stats.swapBuffer=1;

      fprintf(stderr,"Textures Stats:\n");
      fprintf(stderr,"  Free texture memory on TMU0: %d:\n",fxMesa->freeTexMem[FX_TMU0]);
      if(fxMesa->haveTwoTMUs)
        fprintf(stderr,"  Free texture memory on TMU1: %d:\n",fxMesa->freeTexMem[FX_TMU1]);
      fprintf(stderr,"  # request to TMM to upload a texture objects: %u\n",
              fxMesa->stats.reqTexUpload);
      fprintf(stderr,"  # request to TMM to upload a texture objects per swapbuffer: %.2f\n",
              fxMesa->stats.reqTexUpload/(float)fxMesa->stats.swapBuffer);
      fprintf(stderr,"  # texture objects uploaded: %u\n",
              fxMesa->stats.texUpload);
      fprintf(stderr,"  # texture objects uploaded per swapbuffer: %.2f\n",
              fxMesa->stats.texUpload/(float)fxMesa->stats.swapBuffer);
      fprintf(stderr,"  # MBs uploaded to texture memory: %.2f\n",
              fxMesa->stats.memTexUpload/(float)(1<<20));
      fprintf(stderr,"  # MBs uploaded to texture memory per swapbuffer: %.2f\n",
              (fxMesa->stats.memTexUpload/(float)fxMesa->stats.swapBuffer)/(float)(1<<20));
    }
    if (fxMesa->state)  
       free(fxMesa->state);
    if (fxMesa->fogTable)
       free(fxMesa->fogTable);
    fxTMClose(fxMesa);
    
    free(fxMesa);
  }

  if(fxMesa==fxMesaCurrentCtx)
    fxMesaCurrentCtx=NULL;
}


/*
 * Make the specified FX/Mesa context the current one.
 */
void GLAPIENTRY fxMesaMakeCurrent(fxMesaContext fxMesa)
{
  if (/*
 * linux/fs/nls_cp861.c
 *
 * Charset cp861 translation tables.
 * Generated automatically from the Unicode and charset
 * tables from the Unicode Organization (www.unicode.org).
 * The Unicode to charset table has only exact mappings.
 */

#ifndef _NLS_CP
#define _NLS_CP

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/string.h>
#include <linux/nls.h>

static struct nls_unicode charset2uni[256] = {
	/* 0x00*/
	{0x00, 0x00}, {0x01, 0x00}, {0x02, 0x00}, {0x03, 0x00},
	{0x04, 0x00}, {0x05, 0x00}, {0x06, 0x00}, {0x07, 0x00},
	{0x08, 0x00}, {0x09, 0x00}, {0x0a, 0x00}, {0x0b, 0x00},
	{0x0c, 0x00}, {0x0d, 0x00}, {0x0e, 0x00}, {0x0f, 0x00},
	/* 0x10*/
	{0x10, 0x00}, {0x11, 0x00}, {0x12, 0x00}, {0x13, 0x00},
	{0x14, 0x00}, {0x15, 0x00}, {0x16, 0x00}, {0x17, 0x00},
	{0x18, 0x00}, {0x19, 0x00}, {0x1a, 0x00}, {0x1b, 0x00},
	{0x1c, 0x00}, {0x1d, 0x00}, {0x1e, 0x00}, {0x1f, 0x00},
	/* 0x20*/
	{0x20, 0x00}, {0x21, 0x00}, {0x22, 0x00}, {0x23, 0x00},
	{0x24, 0x00}, {0x25, 0x00}, {0x26, 0x00}, {0x27, 0x00},
	{0x28, 0x00}, {0x29, 0x00}, {0x2a, 0x00}, {0x2b, 0x00},
	{0x2c, 0x00}, {0x2d, 0x00}, {0x2e, 0x00}, {0x2f, 0x00},
	/* 0x30*/
	{0x30, 0x00}, {0x31, 0x00}, {0x32, 0x00}, {0x33, 0x00},
	{0x34, 0x00}, {0x35, 0x00}, {0x36, 0x00}, {0x37, 0x00},
	{0x38, 0x00}, {0x39, 0x00}, {0x3a, 0x00}, {0x3b, 0x00},
	{0x3c, 0x00}, {0x3d, 0x00}, {0x3e, 0x00}, {0x3f, 0x00},
	/* 0x40*/
	{0x40, 0x00}, {0x41, 0x00}, {0x42, 0x00}, {0x43, 0x00},
	{0x44, 0x00}, {0x45, 0x00}, {0x46, 0x00}, {0x47, 0x00},
	{0x48, 0x00}, {0x49, 0x00}, {0x4a, 0x00}, {0x4b, 0x00},
	{0x4c, 0x00}, {0x4d, 0x00}, {0x4e, 0x00}, {0x4f, 0x00},
	/* 0x50*/
	{0x50, 0x00}, {0x51, 0x00}, {0x52, 0x00}, {0x53, 0x00},
	{0x54, 0x00}, {0x55, 0x00}, {0x56, 0x00}, {0x57, 0x00},
	{0x58, 0x00}, {0x59, 0x00}, {0x5a, 0x00}, {0x5b, 0x00},
	{0x5c, 0x00}, {0x5d, 0x00}, {0x5e, 0x00}, {0x5f, 0x00},
	/* 0x60*/
	{0x60, 0x00}, {0x61, 0x00}, {0x62, 0x00}, {0x63, 0x00},
	{0x64, 0x00}, {0x65, 0x00}, {0x66, 0x00}, {0x67, 0x00},
	{0x68, 0x00}, {0x69, 0x00}, {0x6a, 0x00}, {0x6b, 0x00},
	{0x6c, 0x00}, {0x6d, 0x00}, {0x6e, 0x00}, {0x6f, 0x00},
	/* 0x70*/
	{0x70, 0x00}, {0x71, 0x00}, {0x72, 0x00}, {0x73, 0x00},
	{0x74, 0x00}, {0x75, 0x00}, {0x76, 0x00}, {0x77, 0x00},
	{0x78, 0x00}, {0x79, 0x00}, {0x7a, 0x00}, {0x7b, 0x00},
	{0x7c, 0x00}, {0x7d, 0x00}, {0x7e, 0x00}, {0x7f, 0x00},
	/* 0x80*/
	{0xc7, 0x00}, {0xfc, 0x00}, {0xe9, 0x00}, {0xe2, 0x00},
	{0xe4, 0x00}, {0xe0, 0x00}, {0xe5, 0x00}, {0xe7, 0x00},
	{0xea, 0x00}, {0xeb, 0x00}, {0xe8, 0x00}, {0xd0, 0x00},
	{0xf0, 0x00}, {0xde, 0x00}, {0xc4, 0x00}, {0xc5, 0x00},
	/* 0x90*/
	{0xc9, 0x00}, {0xe6, 0x00}, {0xc6, 0x00}, {0xf4, 0x00},
	{0xf6, 0x00}, {0xfe, 0x00}, {0xfb, 0x00}, {0xdd, 0x00},
	{0xfd, 0x00}, {0xd6, 0x00}, {0xdc, 0x00}, {0xf8, 0x00},
	{0xa3, 0x00}, {0xd8, 0x00}, {0xa7, 0x20}, {0x92, 0x01},
	/* 0xa0*/
	{0xe1, 0x00}, {0xed, 0x00}, {0xf3, 0x00}, {0xfa, 0x00},
	{0xc1, 0x00}, {0xcd, 0x00}, {0xd3, 0x00}, {0xda, 0x00},
	{0xbf, 0x00}, {0x10, 0x23}, {0xac, 0x00}, {0xbd, 0x00},
	{0xbc, 0x00}, {0xa1, 0x00}, {0xab, 0x00}, {0xbb, 0x00},
	/* 0xb0*/
	{0x91, 0x25}, {0x92, 0x25}, {0x93, 0x25}, {0x02, 0x25},
	{0x24, 0x25}, {0x61, 0x25}, {0x62, 0x25}, {0x56, 0x25},
	{0x55, 0x25}, {0x63, 0x25}, {0x51, 0x25}, {0x57, 0x25},
	{0x5d, 0x25}, {0x5c, 0x25}, {0x5b, 0x25}, {0x10, 0x25},
	/* 0xc0*/
	{0x14, 0x25}, {0x34, 0x25}, {0x2c, 0x25}, {0x1c, 0x25},
	{0x00, 0x25}, {0x3c, 0x25}, {0x5e, 0x25}, {0x5f, 0x25},
	{0x5a, 0x25}, {0x54, 0x25}, {0x69, 0x25}, {0x66, 0x25},
	{0x60, 0x25}, {0x50, 0x25}, {0x6c, 0x25}, {0x67, 0x25},
	/* 0xd0*/
	{0x68, 0x25}, {0x64, 0x25}, {0x65, 0x25}, {0x59, 0x25},
	{0x58, 0x25}, {0x52, 0x25}, {0x53, 0x25}, {0x6b, 0x25},
	{0x6a, 0x25}, {0x18, 0x25}, {0x0c, 0x25}, {0x88, 0x25},
	{0x84, 0x25}, {0x8c, 0x25}, {0x90, 0x25}, {0x80, 0x25},
	/* 0xe0*/
	{0xb1, 0x03}, {0xdf, 0x00}, {0x93, 0x03}, {0xc0, 0x03},
	{0xa3, 0x03}, {0xc3, 0x03}, {0xb5, 0x00}, {0xc4, 0x03},
	{0xa6, 0x03}, {0x98, 0x03}, {0xa9, 0x03}, {0xb4, 0x03},
	{0x1e, 0x22}, {0xc6, 0x03}, {0xb5, 0x03}, {0x29, 0x22},
	/* 0xf0*/
	{0x61, 0x22}, {0xb1, 0x00}, {0x65, 0x22}, {0x64, 0x22},
	{0x20, 0x23}, {0x21, 0x23}, {0xf7, 0x00}, {0x48, 0x22},
	{0xb0, 0x00}, {0x19, 0x22}, {0xb7, 0x00}, {0x1a, 0x22},
	{0x7f, 0x20}, {0xb2, 0x00}, {0xa0, 0x25}, {0xa0, 0x00},
};

static unsigned char page00[256] = {
	0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, /* 0x00-0x07 */
	0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, /* 0x08-0x0f */
	0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, /* 0x10-0x17 */
	0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, /* 0x18-0x1f */
	0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, /* 0x20-0x27 */
	0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, /* 0x28-0x2f */
	0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, /* 0x30-0x37 */
	0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, /* 0x38-0x3f */
	0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, /* 0x40-0x47 */
	0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, /* 0x48-0x4f */
	0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, /* 0x50-0x57 */
	0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, /* 0x58-0x5f */
	0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, /* 0x60-0x67 */
	0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, /* 0x68-0x6f */
	0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, /* 0x70-0x77 */
	0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0xff, 0xad, 0x00, 0x9c, 0x00, 0x00, 0x00, 0x00, /* 0xa0-0xa7 */
	0x00, 0x00, 0x00, 0xae, 0xaa, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0xf8, 0xf1, 0xfd, 0x00, 0x00, 0xe6, 0x00, 0xfa, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0xaf, 0xac, 0xab, 0x00, 0xa8, /* 0xb8-0xbf */
	0x00, 0xa4, 0x00, 0x00, 0x8e, 0x8f, 0x92, 0x80, /* 0xc0-0xc7 */
	0x00, 0x90, 0x00, 0x00, 0x00, 0xa5, 0x00, 0x00, /* 0xc8-0xcf */
	0x8b, 0x00, 0x00, 0xa6, 0x00, 0x00, 0x99, 0x00, /* 0xd0-0xd7 */
	0x9d, 0x00, 0xa7, 0x00, 0x9a, 0x97, 0x8d, 0xe1, /* 0xd8-0xdf */
	0x85, 0xa0, 0x83, 0x00, 0x84, 0x86, 0x91, 0x87, /* 0xe0-0xe7 */
	0x8a, 0x82, 0x88, 0x89, 0x00, 0xa1, 0x00, 0x00, /* 0xe8-0xef */
	0x8c, 0x00, 0x00, 0xa2, 0x93, 0x00, 0x94, 0xf6, /* 0xf0-0xf7 */
	0x9b, 0x00, 0xa3, 0x96, 0x81, 0x98, 0x95, 0x00, /* 0xf8-0xff */
};

static unsigned char page01[256] = {
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x00-0x07 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x08-0x0f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x10-0x17 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x18-0x1f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x27 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x28-0x2f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x30-0x37 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x38-0x3f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x40-0x47 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x48-0x4f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x50-0x57 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x58-0x5f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x60-0x67 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x68-0x6f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x70-0x77 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x9f, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa0-0xa7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb8-0xbf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc0-0xc7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xc8-0xcf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xd0-0xd7 */
	0x00, 0x00, 0x00, 0x00        (void *) fxMesa, GL_TRUE);
d1029 1
a1029 1
  fxMesa->glCtx->Const.MaxTextureUnits=fxMesa->haveTwoTMUs ? 2 : 1;
d1035 1
d1037 1
d1041 1
a1041 1
  fxDDInitExtensions(fxMesa->glCtx);
d1051 9
d1061 1
d1217 3
@


1.13
log
@
merged the autoconf build system from experimental-1 branch
@
text
@d1150 5
a1154 3
  if(fxMesaCurrentCtx==fxMesa) {
    if (MESA_VERBOSE&VERBOSE_DRIVER) {
      fprintf(stderr,"fxmesa: fxMesaMakeCurrent(fxMesaCurrentCtx==fxMesa) End\n");
a1158 1

@


1.12
log
@no real change - cvs commit test
@
text
@d591 4
@


1.11
log
@use MESA_VERBOSE for debugging, and q3test/trilinear bug fix
@
text
@d590 1
@


1.11.2.1
log
@Quake3 inspired optimizations
@
text
@a831 1
  GLcontext *ctx = 0;
d1006 3
a1008 3
  ctx = fxMesa->glCtx=gl_create_context(fxMesa->glVis,
					shareCtx,  /* share list context */
					(void *) fxMesa, GL_TRUE);
a1019 1
  fxDDClipInit();
d1024 1
a1024 1
  fxDDInitExtensions(fxMesa->glCtx);  
a1033 9
  
  /* XXX Fix me too: need to have the 'struct dd' prepared prior to
   * creating the context... The below is broken if you try to insert
   * new stages.  
   */
  if (ctx->NrPipelineStages)
     ctx->NrPipelineStages = fxDDRegisterPipelineStages( ctx->PipelineStage,
							 ctx->PipelineStage,
							 ctx->NrPipelineStages);
a1034 1
  
@


1.11.2.2
log
@new, experimental fast path for quake 3 precalc pipeline
@
text
@a1022 1
  fxDDFastPathInit();
@


1.11.2.3
log
@Faux multitexturing for voodoo-1
@
text
@a936 13
  if (getenv("FX_EMULATE_SINGLE_TMU")) {
     fprintf(stderr, "\n\nEmulating single tmu\n\n");
     fxMesa->haveTwoTMUs = GL_FALSE;
  }

  fxMesa->emulateTwoTMUs = fxMesa->haveTwoTMUs;
  
  if (getenv("FX_EMULATE_MULTITEX")) {
     fprintf(stderr, "\n\nEmulating multitexture\n\n");
     fxMesa->emulateTwoTMUs = GL_TRUE;
  }


d966 1
d971 1
d978 1
d1015 1
a1015 1
  fxMesa->glCtx->Const.MaxTextureUnits=fxMesa->emulateTwoTMUs ? 2 : 1;
@


1.11.2.4
log
@added #if defined(FX)-#endif to make compilation without glide possible
@
text
@d591 1
@


1.11.2.5
log
@some trial assembly, made newer code active by default
@
text
@d943 1
a943 1
  if (!getenv("FX_DONT_FAKE_MULTITEX")) {
@


1.11.2.6
log
@cleaned up fxpipeline
@
text
@a1210 3
       extern int fx_frame;
       fx_frame += fxMesaCurrentCtx->using_fast_path;

@


1.10
log
@miscellaneous bug fixes
@
text
@a606 5
#ifndef DEBUG_FXMESA
int DEBUG_FXMESA = 0;
#endif


d683 1
a683 1
  if (DEBUG_FXMESA) {
d833 1
a833 1
  if (DEBUG_FXMESA) {
d878 1
a878 1
      if (DEBUG_FXMESA) {
d901 1
a901 1
      if (DEBUG_FXMESA) {
d917 1
a917 1
    if (DEBUG_FXMESA) {
d1054 1
a1054 1
  if (DEBUG_FXMESA) {
d1077 1
a1077 1
  if (DEBUG_FXMESA) {
d1130 1
a1130 1
  if (DEBUG_FXMESA) {
d1138 1
a1138 1
    if (DEBUG_FXMESA) {
d1146 1
a1146 1
    if (DEBUG_FXMESA) {
d1170 1
a1170 1
  if (DEBUG_FXMESA) {
d1181 1
a1181 1
  if (DEBUG_FXMESA) {
d1213 1
a1213 1
  if (DEBUG_FXMESA) {
d1260 1
a1260 1
    if (DEBUG_FXMESA) {
d1266 1
a1266 1
  if (DEBUG_FXMESA) {
@


1.9
log
@miklos' macintosh changes
@
text
@d1025 1
a1027 1
  fxDDTrifuncInit(fxMesa->glCtx);
@


1.8
log
@FX polygon offset and debugging changes
@
text
@d806 1
d818 1
@


1.7
log
@clean-up of fx-catch-signals option
@
text
@d607 5
d633 2
a634 1
  exit(-1);
d688 2
a689 2
#if defined(DEBUG_FXMESA)
  int i;
d691 1
a691 5
  fprintf(stderr,"fxmesa: gl3DfxSetPaletteEXT()\n");

  for(i=0;i<256;i++)
    fprintf(stderr,"%x\n",pal[i]);
#endif
d693 4
d806 11
d836 3
a838 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxMesaCreateContext() Start\n");
#endif
d881 3
a883 3
#if defined(DEBUG_FXMESA)
      fprintf(stderr,"fxmesa: fxMesaCreateContext() End (defualt)\n");
#endif
d904 3
a906 3
#if defined(DEBUG_FXMESA)
      fprintf(stderr,"fxmesa: fxMesaCreateContext() End (grSstWinOpen)\n");
#endif
d920 3
a922 3
#if defined(DEBUG_FXMESA)
    fprintf(stderr,"fxmesa: fxMesaCreateContext() End (malloc)\n");
#endif
d1025 1
a1025 1

d1057 3
a1059 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxMesaCreateContext() End\n");
#endif
d1080 3
a1082 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxMesaDestroyContext()\n");
#endif
d1133 3
a1135 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxMesaMakeCurrent(...) Start\n");
#endif
d1141 3
a1143 3
#if defined(DEBUG_FXMESA)
    fprintf(stderr,"fxmesa: fxMesaMakeCurrent(NULL) End\n");
#endif
d1149 3
a1151 3
#if defined(DEBUG_FXMESA)
    fprintf(stderr,"fxmesa: fxMesaMakeCurrent(fxMesaCurrentCtx==fxMesa) End\n");
#endif
d1173 3
a1175 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxMesaMakeCurrent(...) End\n");
#endif
d1184 3
a1186 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: ------------------------------- fxMesaSwapBuffers() -------------------------------\n");
#endif
d1216 3
a1218 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxQueryHardware() Start\n");
#endif
d1263 3
a1265 3
#if defined(DEBUG_FXMESA)
    fprintf(stderr,"fxmesa: fxQueryHardware() End (-1)\n");
#endif
d1269 3
a1271 3
#if defined(DEBUG_FXMESA)
  fprintf(stderr,"fxmesa: fxQueryHardware() End (voodooo)\n");
#endif
@


1.6
log
@added fx-catch-signals config option
@
text
@d1027 1
d1038 1
a1241 18

#if 0
    if (fxMesaCurrentCtx && fxMesaCurrentCtx->glCtx
        && fxMesaCurrentCtx->glCtx->CatchSignals) {
       signal(SIGINT,cleangraphics_handler);
       signal(SIGHUP,cleangraphics_handler);
       signal(SIGPIPE,cleangraphics_handler);
       signal(SIGFPE,cleangraphics_handler);
       signal(SIGBUS,cleangraphics_handler);
       signal(SIGILL,cleangraphics_handler);
       signal(SIGSEGV,cleangraphics_handler);
       signal(SIGTERM,cleangraphics_handler);
       printf("catching signals\n");
    }
    else
       printf("NOT catching signals\n");
#endif

@


1.5
log
@Introduced a new MESA_GLX_FX related behavior
@
text
@d607 26
a636 1

d1016 1
a1016 1
  /* Fix me: callback not registered when main VB is created.
d1026 12
a1191 25
#if defined(__WIN32__)
static int cleangraphics(void)
{
  glbTotNumCtx=1;
  fxMesaDestroyContext(fxMesaCurrentCtx);

  return 0;
}
#elif defined(__linux__)
static void cleangraphics(void)
{
  glbTotNumCtx=1;
  fxMesaDestroyContext(fxMesaCurrentCtx);
}

static void cleangraphics_handler(int s)
{
  fprintf(stderr,"fxmesa: Received a not handled signal %d\n",s);

  cleangraphics();
  exit(-1);
}
#endif


d1241 17
a1257 8
    signal(SIGINT,cleangraphics_handler);
    signal(SIGHUP,cleangraphics_handler);
    signal(SIGPIPE,cleangraphics_handler);
    signal(SIGFPE,cleangraphics_handler);
    signal(SIGBUS,cleangraphics_handler);
    signal(SIGILL,cleangraphics_handler);
    signal(SIGSEGV,cleangraphics_handler);
    signal(SIGTERM,cleangraphics_handler);
@


1.4
log
@Compiled vertex arrays
@
text
@d36 2
a37 1
 * V0.30 - David Bucciarelli (humanware@@plus.it) Humanware s.r.l.
d61 1
d697 1
a697 1
  GrScreenResolution_t lastvalidres;
d852 1
a852 1
    fprintf(stderr,"Mesa fx Voodoo Device Driver v0.30\nWritten by David Bucciarelli (tech.hmw@@plus.it)\n");
@


1.3
log
@Updated to the Mesa Voodoo driver v0.30
@
text
@d719 1
a719 1
	return resolutions[i][2];
d762 2
a763 2
	aux=1;
	break;
d773 1
d810 1
a810 1
	aux=1;
d816 1
a816 1
	aux=1;
d826 1
a826 1
    /* XXX ugly hack here for sharing display lists */
d831 3
a833 3
         const void *vPtr = &attribList[i];
         GLcontext **ctx = (GLcontext **) vPtr;
         shareCtx = *ctx;
d868 1
a868 1
	      (int)grSstScreenWidth(),(int)grSstScreenHeight());
d950 1
a950 2
  if(depthSize) {
    grDepthMask(FXTRUE);
a951 1
  }
d956 8
a963 8
				 alphaBuffer,
				 doubleBuffer,
				 GL_FALSE,    /* stereo */
				 depthSize,   /* depth_size */
				 stencilSize, /* stencil_size */
				 accumSize,   /* accum_size */
				 0,           /* index bits */
				 5,6,5,0);    /* RGBA bits */
d967 1
a967 1
				  (void *) fxMesa, GL_TRUE);
d977 3
d983 1
d989 5
d996 2
a997 4

  /* KW: Culling now done in software.
   */
  grCullMode(GR_CULL_DISABLE);
d1040 1
a1040 1
	fxMesa->stats.swapBuffer=1;
d1045 1
a1045 1
	fprintf(stderr,"  Free texture memory on TMU1: %d:\n",fxMesa->freeTexMem[FX_TMU1]);
d1047 1
a1047 1
	      fxMesa->stats.reqTexUpload);
d1049 1
a1049 1
	      fxMesa->stats.reqTexUpload/(float)fxMesa->stats.swapBuffer);
d1051 1
a10, 0x00, 0x00, 0x00, 0x00, /* 0xd8-0xdf */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe0-0xe7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xe8-0xef */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf0-0xf7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xf8-0xff */
};

static unsigned char page03[256] = {
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x00-0x07 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x08-0x0f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x10-0x17 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x18-0x1f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x20-0x27 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x28-0x2f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x30-0x37 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x38-0x3f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x40-0x47 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x48-0x4f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x50-0x57 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x58-0x5f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x60-0x67 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x68-0x6f */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x70-0x77 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x78-0x7f */

	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x80-0x87 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x88-0x8f */
	0x00, 0x00, 0x00, 0xe2, 0x00, 0x00, 0x00, 0x00, /* 0x90-0x97 */
	0xe9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0x98-0x9f */
	0x00, 0x00, 0x00, 0xe4, 0x00, 0x00, 0xe8, 0x00, /* 0xa0-0xa7 */
	0x00, 0xea, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xa8-0xaf */
	0x00, 0xe0, 0x00, 0x00, 0xeb, 0xee, 0x00, 0x00, /* 0xb0-0xb7 */
	0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* 0xb8-0xbf */
	0xe3, 0x00, 0x00, 0xe5, 0xe7, 0x00, 0xed, 0x00, /* 0xc0-0xc7 */
	0x00, 0x00, 0x00, 0x00,