-/* -*- mode: C; tab-width:8; -*- */
-
/*
* Mesa 3-D graphics library
- * Version: 3.3
+ * Version: 4.0
*
- * Copyright (C) 1999-2000 Brian Paul All Rights Reserved.
+ * Copyright (C) 1999-2001 Brian Paul All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- *
- * Original Mesa / 3Dfx device driver (C) 1999 David Bucciarelli, by the
- * terms stated above.
- *
- * Thank you for your contribution, David!
- *
- * Please make note of the above copyright/license statement. If you
- * contributed code or bug fixes to this code under the previous (GNU
- * Library) license and object to the new license, your code will be
- * removed at your request. Please see the Mesa docs/COPYRIGHT file
- * for more information.
- *
- * Additional Mesa/3Dfx driver developers:
- * Daryll Strauss <daryll@precisioninsight.com>
- * Keith Whitwell <keith@precisioninsight.com>
- *
- * See fxapi.h for more revision/author details.
*/
+/* Authors:
+ * David Bucciarelli
+ * Brian Paul
+ * Daryll Strauss
+ * Keith Whitwell
+ * Daniel Borca
+ * Hiroshi Morii
+ */
+
+
+/* fxapi.c - public interface to FX/Mesa functions (fxmesa.h) */
+
#ifdef HAVE_CONFIG_H
#include "conf.h"
#if defined(FX)
#include "fxdrv.h"
-static fxMesaContext fxMesaCurrentCtx=NULL;
+#include "drivers/common/driverfuncs.h"
+
+#ifndef TDFX_DEBUG
+int TDFX_DEBUG = (0
+/* | VERBOSE_VARRAY */
+/* | VERBOSE_TEXTURE */
+/* | VERBOSE_IMMEDIATE */
+/* | VERBOSE_PIPELINE */
+/* | VERBOSE_DRIVER */
+/* | VERBOSE_STATE */
+/* | VERBOSE_API */
+/* | VERBOSE_DISPLAY_LIST */
+/* | VERBOSE_LIGHTING */
+/* | VERBOSE_PRIMS */
+/* | VERBOSE_VERTS */
+ );
+#endif
+
+static fxMesaContext fxMesaCurrentCtx = NULL;
/*
* Status of 3Dfx hardware initialization
*/
-static int glbGlideInitialized=0;
-static int glb3DfxPresent=0;
-static int glbTotNumCtx=0;
+static int glbGlideInitialized = 0;
+static int glb3DfxPresent = 0;
+static int glbTotNumCtx = 0;
-GrHwConfiguration glbHWConfig;
-int glbCurrentBoard=0;
+static GrHwConfiguration glbHWConfig;
+static int glbCurrentBoard = 0;
#if defined(__WIN32__)
-static int cleangraphics(void)
+static int
+cleangraphics(void)
{
- glbTotNumCtx=1;
- fxMesaDestroyContext(fxMesaCurrentCtx);
+ glbTotNumCtx = 1;
+ fxMesaDestroyContext(fxMesaCurrentCtx);
- return 0;
+ return 0;
}
#elif defined(__linux__)
-static void cleangraphics(void)
+static void
+cleangraphics(void)
{
- glbTotNumCtx=1;
- fxMesaDestroyContext(fxMesaCurrentCtx);
+ glbTotNumCtx = 1;
+ fxMesaDestroyContext(fxMesaCurrentCtx);
}
-static void cleangraphics_handler(int s)
+static void
+cleangraphics_handler(int s)
{
- fprintf(stderr,"fxmesa: Received a not handled signal %d\n",s);
+ fprintf(stderr, "fxmesa: ERROR: received a not handled signal %d\n", s);
- cleangraphics();
+ cleangraphics();
/* abort(); */
- exit(1);
+ exit(1);
}
#endif
+/*
+ * Query 3Dfx hardware presence/kind
+ */
+static GLboolean GLAPIENTRY fxQueryHardware (void)
+{
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxQueryHardware()\n");
+ }
+
+ if (!glbGlideInitialized) {
+ grGlideInit();
+ glb3DfxPresent = FX_grSstQueryHardware(&glbHWConfig);
+
+ glbGlideInitialized = 1;
+
+#if defined(__WIN32__)
+ _onexit((_onexit_t) cleangraphics);
+#elif defined(__linux__)
+ /* Only register handler if environment variable is not defined. */
+ if (!getenv("MESA_FX_NO_SIGNALS")) {
+ atexit(cleangraphics);
+ }
+#endif
+ }
+
+ return glb3DfxPresent;
+}
+
+
/*
* Select the Voodoo board to use when creating
* a new context.
*/
-GLboolean GLAPIENTRY fxMesaSelectCurrentBoard(int n)
+GLint GLAPIENTRY fxMesaSelectCurrentBoard (int n)
{
- fxQueryHardware();
+ fxQueryHardware();
+
+ if ((n < 0) || (n >= glbHWConfig.num_sst))
+ return -1;
- if((n<0) || (n>=glbHWConfig.num_sst))
- return GL_FALSE;
+ return glbHWConfig.SSTs[glbCurrentBoard = n].type;
+}
- glbCurrentBoard=n;
- return GL_TRUE;
+fxMesaContext GLAPIENTRY fxMesaGetCurrentContext (void)
+{
+ return fxMesaCurrentCtx;
}
-fxMesaContext GLAPIENTRY fxMesaGetCurrentContext(void)
+void GLAPIENTRY fxGetScreenGeometry (GLint *w, GLint *h)
{
- return fxMesaCurrentCtx;
+ GLint width = 0;
+ GLint height = 0;
+
+ if (fxMesaCurrentCtx != NULL) {
+ width = fxMesaCurrentCtx->screen_width;
+ height = fxMesaCurrentCtx->screen_height;
+ }
+
+ if (w != NULL) {
+ *w = width;
+ }
+ if (h != NULL) {
+ *h = height;
+ }
}
* More a trick than a real extesion, use the shared global
* palette extension.
*/
-extern void GLAPIENTRY gl3DfxSetPaletteEXT(GLuint *pal); /* silence warning */
-void GLAPIENTRY gl3DfxSetPaletteEXT(GLuint *pal)
+extern void GLAPIENTRY gl3DfxSetPaletteEXT(GLuint * pal); /* silence warning */
+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);
- }
-}
+ fxMesaContext fxMesa = fxMesaCurrentCtx;
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ int i;
-static GrScreenResolution_t fxBestResolution(int width, int height, int aux)
-{
- static int resolutions[][5]={
- { 320, 200, GR_RESOLUTION_320x200, 2, 2 },
- { 320, 240, GR_RESOLUTION_320x240, 2, 2 },
- { 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
- ,{ 1280, 1024, GR_RESOLUTION_1280x1024, 8, 8 }
-#endif
-#ifdef GR_RESOLUTION_1600x1200
- ,{ 1600, 1200, GR_RESOLUTION_1600x1200, 16, 8 }
-#endif
- };
- int NUM_RESOLUTIONS = sizeof(resolutions) / (sizeof(int)*5);
- int i,fbmem;
- GrScreenResolution_t lastvalidres=resolutions[4][2];
-
- fxQueryHardware();
+ fprintf(stderr, "gl3DfxSetPaletteEXT(...)\n");
- if(glbHWConfig.SSTs[glbCurrentBoard].type==GR_SSTTYPE_VOODOO) {
- fbmem=glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig.fbRam;
+ for (i = 0; i < 256; i++) {
+ fprintf(stderr, "\t%x\n", pal[i]);
+ }
+ }
- 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;
+ if (fxMesa) {
+ fxMesa->haveGlobalPaletteTexture = 1;
- /* A work around for BZFlag */
+ grTexDownloadTable(GR_TEXTABLE_PALETTE, (GuTexPalette *) pal);
+ }
+}
- 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];
+static GrScreenResolution_t fxBestResolution (int width, int height)
+{
+ static int resolutions[][3] = {
+ { GR_RESOLUTION_320x200, 320, 200 },
+ { GR_RESOLUTION_320x240, 320, 240 },
+ { GR_RESOLUTION_400x256, 400, 256 },
+ { GR_RESOLUTION_512x384, 512, 384 },
+ { GR_RESOLUTION_640x200, 640, 200 },
+ { GR_RESOLUTION_640x350, 640, 350 },
+ { GR_RESOLUTION_640x400, 640, 400 },
+ { GR_RESOLUTION_640x480, 640, 480 },
+ { GR_RESOLUTION_800x600, 800, 600 },
+ { GR_RESOLUTION_960x720, 960, 720 },
+ { GR_RESOLUTION_856x480, 856, 480 },
+ { GR_RESOLUTION_512x256, 512, 256 },
+ { GR_RESOLUTION_1024x768, 1024, 768 },
+ { GR_RESOLUTION_1280x1024, 1280, 1024 },
+ { GR_RESOLUTION_1600x1200, 1600, 1200 },
+ { GR_RESOLUTION_400x300, 400, 300 },
+ { GR_RESOLUTION_1152x864, 1152, 864 },
+ { GR_RESOLUTION_1280x960, 1280, 960 },
+ { GR_RESOLUTION_1600x1024, 1600, 1024 },
+ { GR_RESOLUTION_1792x1344, 1792, 1344 },
+ { GR_RESOLUTION_1856x1392, 1856, 1392 },
+ { GR_RESOLUTION_1920x1440, 1920, 1440 },
+ { GR_RESOLUTION_2048x1536, 2048, 1536 },
+ { GR_RESOLUTION_2048x2048, 2048, 2048 }
+ };
+
+ int i, size;
+ int lastvalidres = GR_RESOLUTION_640x480;
+ int min = 2048 * 2048; /* max is GR_RESOLUTION_2048x2048 */
+ GrResolution resTemplate = {
+ GR_QUERY_ANY,
+ GR_QUERY_ANY,
+ 2 /*GR_QUERY_ANY */,
+ GR_QUERY_ANY
+ };
+ GrResolution *presSupported;
+
+ fxQueryHardware();
+
+ size = grQueryResolutions(&resTemplate, NULL);
+ presSupported = malloc(size);
+
+ size /= sizeof(GrResolution);
+ grQueryResolutions(&resTemplate, presSupported);
+
+ for (i = 0; i < size; i++) {
+ int r = presSupported[i].resolution;
+ if ((width <= resolutions[r][1]) && (height <= resolutions[r][2])) {
+ if (min > (resolutions[r][1] * resolutions[r][2])) {
+ min = resolutions[r][1] * resolutions[r][2];
+ lastvalidres = r;
+ }
+ }
+ }
- lastvalidres=resolutions[i][2];
- }
+ free(presSupported);
- return lastvalidres;
+ return resolutions[lastvalidres][0];
}
-fxMesaContext GLAPIENTRY fxMesaCreateBestContext(GLuint win,GLint width, GLint height,
- const GLint attribList[])
+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;
- }
- }
+ int res = fxBestResolution(width, height);
- res=fxBestResolution(width,height,aux);
+ if (res == -1) {
+ return NULL;
+ }
- return fxMesaCreateContext(win,res,refresh,attribList);
+ return fxMesaCreateContext(win, res, GR_REFRESH_60Hz, 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 GLAPIENTRY
+fxMesaCreateContext(GLuint win,
+ GrScreenResolution_t res,
+ GrScreenRefresh_t ref, const GLint attribList[])
{
- fxMesaContext fxMesa = NULL;
- int i,type;
- int aux;
- GLboolean doubleBuffer=GL_FALSE;
- GLboolean alphaBuffer=GL_FALSE;
- GLboolean verbose=GL_FALSE;
- GLint depthSize=0;
- GLint stencilSize=0;
- GLint accumSize=0;
- GLcontext *shareCtx = NULL;
- GLcontext *ctx = 0;
- /*FX_GrContext_t glideContext = 0;*/
- char *errorstr;
- GLboolean useBGR;
- char *system = NULL;
-
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaCreateContext() Start\n");
- }
-
- if(getenv("MESA_FX_INFO"))
- verbose=GL_TRUE;
-
- aux=0;
- i=0;
- while(attribList[i]!=FXMESA_NONE) {
- switch (attribList[i]) {
- case FXMESA_DOUBLEBUFFER:
- doubleBuffer=GL_TRUE;
- break;
- case FXMESA_ALPHA_SIZE:
- i++;
- alphaBuffer=attribList[i]>0;
- if(alphaBuffer)
- aux=1;
- break;
- case FXMESA_DEPTH_SIZE:
- i++;
- depthSize=attribList[i];
- if(depthSize) {
- aux=1;
- depthSize = 16;
- }
- break;
- case FXMESA_STENCIL_SIZE:
- i++;
- stencilSize=attribList[i];
- break;
- case FXMESA_ACCUM_SIZE:
- i++;
- accumSize=attribList[i];
- break;
- /* XXX ugly hack here for sharing display lists */
-#define FXMESA_SHARE_CONTEXT 990099 /* keep in sync with xmesa1.c! */
- case FXMESA_SHARE_CONTEXT:
- i++;
- {
- const void *vPtr = &attribList[i];
- GLcontext **ctx = (GLcontext **) vPtr;
- shareCtx = *ctx;
- }
- break;
- default:
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaCreateContext() End (defualt)\n");
- }
- return NULL;
- }
- i++;
- }
-
- /* A workaround for Linux GLQuake */
- if(depthSize && alphaBuffer)
- alphaBuffer=0;
-
- if ((type=fxQueryHardware()) < 0) {
- fprintf(stderr,"fx Driver: ERROR no Voodoo1/2 Graphics or Voodoo Rush !\n");
- return NULL;
- }
-
- if(type==GR_SSTTYPE_VOODOO)
- win=0;
-
- grSstSelect(glbCurrentBoard);
-
- fxMesa=(fxMesaContext)calloc(1,sizeof(struct tfxMesaContext));
- if(!fxMesa) {
- errorstr = "malloc";
- goto errorhandler;
+ fxMesaContext fxMesa = NULL;
+ GLcontext *ctx = NULL, *shareCtx = NULL;
+ struct dd_function_table functions;
+
+ int i;
+ const char *str;
+ int sliaa, numSLI, samplesPerChip;
+ struct SstCard_St *voodoo;
+ struct tdfx_glide *Glide;
+
+ GLboolean aux;
+ GLboolean doubleBuffer;
+ GLuint colDepth;
+ GLuint depthSize, alphaSize, stencilSize, accumSize;
+ GLuint redBits, greenBits, blueBits, alphaBits;
+ GrPixelFormat_t pixFmt;
+
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaCreateContext(...)\n");
+ }
+
+ /* Okay, first process the user flags */
+ aux = GL_FALSE;
+ doubleBuffer = GL_FALSE;
+ colDepth = 16;
+ depthSize = alphaSize = stencilSize = accumSize = 0;
+
+ i = 0;
+ while (attribList[i] != FXMESA_NONE) {
+ switch (attribList[i]) {
+ case FXMESA_COLORDEPTH:
+ colDepth = attribList[++i];
+ break;
+ case FXMESA_DOUBLEBUFFER:
+ doubleBuffer = GL_TRUE;
+ break;
+ case FXMESA_ALPHA_SIZE:
+ if ((alphaSize = attribList[++i])) {
+ aux = GL_TRUE;
+ }
+ break;
+ case FXMESA_DEPTH_SIZE:
+ if ((depthSize = attribList[++i])) {
+ aux = GL_TRUE;
+ }
+ break;
+ case FXMESA_STENCIL_SIZE:
+ stencilSize = attribList[++i];
+ break;
+ case FXMESA_ACCUM_SIZE:
+ accumSize = attribList[++i];
+ break;
+ /* XXX ugly hack here for sharing display lists */
+ case FXMESA_SHARE_CONTEXT:
+ shareCtx = (GLcontext *)attribList[++i];
+ break;
+ default:
+ fprintf(stderr, "fxMesaCreateContext: ERROR: wrong parameter (%d) passed\n", attribList[i]);
+ return NULL;
+ }
+ i++;
+ }
+
+ if (!fxQueryHardware()) {
+ str = "no Voodoo hardware!";
+ goto errorhandler;
+ }
+
+ grSstSelect(glbCurrentBoard);
+ /*grEnable(GR_OPENGL_MODE_EXT);*/ /* ZZZ: trick to make GL happy.
+ Glide3 will unmap memory for card when grSstWinClose is called.
+ This also forces the SLI band height to be 32 (above 1024x768) or 16
+ and disables the splash screen due to y-origin swapping.
+ Note: We only want the former. */
+ voodoo = &glbHWConfig.SSTs[glbCurrentBoard];
+
+ fxMesa = (fxMesaContext)CALLOC_STRUCT(tfxMesaContext);
+ if (!fxMesa) {
+ str = "private context";
+ goto errorhandler;
+ }
+
+ if (getenv("MESA_FX_INFO")) {
+ fxMesa->verbose = GL_TRUE;
+ }
+
+ fxMesa->type = voodoo->type;
+ fxMesa->HavePalExt = voodoo->HavePalExt && !getenv("MESA_FX_IGNORE_PALEXT");
+ fxMesa->HavePixExt = voodoo->HavePixExt && !getenv("MESA_FX_IGNORE_PIXEXT");
+ fxMesa->HaveTexFmt = voodoo->HaveTexFmt && !getenv("MESA_FX_IGNORE_TEXFMT");
+ fxMesa->HaveCmbExt = voodoo->HaveCmbExt && !getenv("MESA_FX_IGNORE_CMBEXT");
+ fxMesa->HaveMirExt = voodoo->HaveMirExt && !getenv("MESA_FX_IGNORE_MIREXT");
+ fxMesa->HaveTexUma = voodoo->HaveTexUma && !getenv("MESA_FX_IGNORE_TEXUMA");
+ fxMesa->Glide = glbHWConfig.Glide;
+ Glide = &fxMesa->Glide;
+ fxMesa->HaveTexus2 = Glide->txImgQuantize &&
+ Glide->txMipQuantize &&
+ Glide->txPalToNcc && !getenv("MESA_FX_IGNORE_TEXUS2");
+
+ /* Determine if we need vertex swapping, RGB order and SLI/AA */
+ sliaa = 0;
+ switch (fxMesa->type) {
+ case GR_SSTTYPE_VOODOO:
+ case GR_SSTTYPE_SST96:
+ case GR_SSTTYPE_Banshee:
+ fxMesa->bgrOrder = GL_TRUE;
+ fxMesa->snapVertices = GL_TRUE;
+ break;
+ case GR_SSTTYPE_Voodoo2:
+ fxMesa->bgrOrder = GL_TRUE;
+ fxMesa->snapVertices = GL_FALSE;
+ break;
+ case GR_SSTTYPE_Voodoo4:
+ case GR_SSTTYPE_Voodoo5:
+ /* number of SLI units and AA Samples per chip */
+ if ((str = Glide->grGetRegistryOrEnvironmentStringExt("SSTH3_SLI_AA_CONFIGURATION")) != NULL) {
+ sliaa = atoi(str);
+ }
+ case GR_SSTTYPE_Voodoo3:
+ default:
+ fxMesa->bgrOrder = GL_FALSE;
+ fxMesa->snapVertices = GL_FALSE;
+ break;
+ }
+ /* ZZZ TO DO: Add the old SLI/AA settings for Napalm. */
+ switch(voodoo->numChips) {
+ case 4: /* 4 chips */
+ switch(sliaa) {
+ case 8: /* 8 Sample AA */
+ numSLI = 1;
+ samplesPerChip = 2;
+ break;
+ case 7: /* 4 Sample AA */
+ numSLI = 1;
+ samplesPerChip = 1;
+ break;
+ case 6: /* 2 Sample AA */
+ numSLI = 2;
+ samplesPerChip = 1;
+ break;
+ default:
+ numSLI = 4;
+ samplesPerChip = 1;
}
-
- if(glbHWConfig.SSTs[glbCurrentBoard].type==GR_SSTTYPE_VOODOO)
- fxMesa->haveTwoTMUs=(glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig.nTexelfx > 1);
- else if(glbHWConfig.SSTs[glbCurrentBoard].type==GR_SSTTYPE_SST96)
- fxMesa->haveTwoTMUs=(glbHWConfig.SSTs[glbCurrentBoard].sstBoard.SST96Config.nTexelfx > 1);
- else
- fxMesa->haveTwoTMUs=GL_FALSE;
-
- fxMesa->haveDoubleBuffer=doubleBuffer;
- fxMesa->haveAlphaBuffer=alphaBuffer;
- fxMesa->haveGlobalPaletteTexture=GL_FALSE;
- fxMesa->haveZBuffer=depthSize ? 1 : 0;
- fxMesa->verbose=verbose;
- fxMesa->board=glbCurrentBoard;
-
-
- fxMesa->glideContext = FX_grSstWinOpen((FxU32)win,res,ref,
-#if FXMESA_USE_ARGB
- GR_COLORFORMAT_ARGB,
-#else
- GR_COLORFORMAT_ABGR,
-#endif
- GR_ORIGIN_LOWER_LEFT,
- 2,aux);
- if (!fxMesa->glideContext){
- errorstr = "grSstWinOpen";
- goto errorhandler;
+ break;
+ case 2: /* 2 chips */
+ switch(sliaa) {
+ case 4: /* 4 Sample AA */
+ numSLI = 1;
+ samplesPerChip = 2;
+ break;
+ case 3: /* 2 Sample AA */
+ numSLI = 1;
+ samplesPerChip = 1;
+ break;
+ default:
+ numSLI = 2;
+ samplesPerChip = 1;
}
-
- /*
- * Pixel tables are use during pixel read-back
- * Either initialize them for RGB or BGR order.
- */
-#if FXMESA_USE_ARGB
- useBGR = GL_FALSE; /* Force RGB pixel order */
- system = "FXMESA_USE_ARGB";
-#else
- if (glbHWConfig.SSTs[glbCurrentBoard].type == GR_SSTTYPE_VOODOO) {
- /* jk991130 - Voodoo 3s don't use BGR. Query the # of TMUs
- * as Voodoo3s have 2 TMUs on board, Banshee has only 1
- * bk000413 - another suggestion from Joseph Kain is using
- * VendorID 0x121a for all 3dfx boards
- * DeviceID VG 1/V2 2/VB 3/V3 5
- * For now we cehck for known BGR devices, and presume
- * everything else to be a V3/RGB.
- */
- GrVoodooConfig_t *voodoo;
- voodoo = &glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig;
-
- if (voodoo->nTexelfx == 1) {
- /* Voodoo1 or Banshee */
- useBGR = GL_TRUE;
- system = "Voodoo1";
- }
- else if (voodoo->nTexelfx == 2 &&
- voodoo->fbiRev == 260 &&
- voodoo->tmuConfig[0].tmuRev == 4 &&
- (voodoo->tmuConfig[0].tmuRam == 2 ||
- voodoo->tmuConfig[0].tmuRam == 4)) {
- /* Voodoo 2 */
- useBGR = GL_TRUE;
- system = "Voodoo2";
- }
- else if (voodoo->nTexelfx == 2 &&
- voodoo->fbiRev == 2 &&
- voodoo->tmuConfig[0].tmuRev == 1 &&
- voodoo->tmuConfig[0].tmuRam == 4) {
- /* Quantum3D Obsidian 50/100 */
- useBGR = GL_TRUE;
- system = "Quantum3D Obsidian";
- }
- else
- /* Brian
- * (voodoo->nTexelfx == 2 &&
- * voodoo->fbiRev == 0 &&
- * voodoo->tmuConfig[0].tmuRev == 148441048 &&
- * voodoo->tmuConfig[0].tmuRam == 3)
- * Bernd
- * (voodoo->nTexelfx == 2 &&
- * voodoo->fbiRev == 69634 &&
- * voodoo->tmuConfig[0].tmuRev == 69634 &&
- * voodoo->tmuConfig[0].tmuRam == 2 )
- */
- {
- /* Presumed Voodoo3 */
- useBGR = GL_FALSE;
- system = "Voodoo3";
- }
- if (getenv("MESA_FX_INFO")) {
- printf("Voodoo: Texelfx: %d / FBI Rev.: %d / TMU Rev.: %d / TMU RAM: %d\n",
- voodoo->nTexelfx,
- voodoo->fbiRev,
- voodoo->tmuConfig[0].tmuRev,
- voodoo->tmuConfig[0].tmuRam );
- }
- }
- else {
- useBGR = GL_FALSE; /* use RGB pixel order otherwise */
- system = "non-voodoo";
+ break;
+ default: /* 1 chip */
+ switch(sliaa) {
+ case 1: /* 2 Sample AA */
+ numSLI = 1;
+ samplesPerChip = 2;
+ break;
+ default:
+ numSLI = 1;
+ samplesPerChip = 1;
}
-#endif /*FXMESA_USE_ARGB*/
-
- if (getenv("MESA_FX_INFO"))
- printf("Voodoo pixel order: %s (%s)\n", useBGR ? "BGR" : "RGB", system);
-
- fxInitPixelTables(fxMesa, useBGR);
-
- fxMesa->width=FX_grSstScreenWidth();
- fxMesa->height=FX_grSstScreenHeight();
-
+ }
+
+ fxMesa->fsaa = samplesPerChip * voodoo->numChips / numSLI; /* 1:noFSAA, 2:2xFSAA, 4:4xFSAA, 8:8xFSAA */
+
+ switch (fxMesa->colDepth = colDepth) {
+ case 15:
+ redBits = 5;
+ greenBits = 5;
+ blueBits = 5;
+ alphaBits = depthSize ? 1 : 8;
+ switch(fxMesa->fsaa) {
+ case 8:
+ pixFmt = GR_PIXFMT_AA_8_ARGB_1555;
+ break;
+ case 4:
+ pixFmt = GR_PIXFMT_AA_4_ARGB_1555;
+ break;
+ case 2:
+ pixFmt = GR_PIXFMT_AA_2_ARGB_1555;
+ break;
+ default:
+ pixFmt = GR_PIXFMT_ARGB_1555;
+ }
+ break;
+ case 16:
+ redBits = 5;
+ greenBits = 6;
+ blueBits = 5;
+ alphaBits = depthSize ? 0 : 8;
+ switch(fxMesa->fsaa) {
+ case 8:
+ pixFmt = GR_PIXFMT_AA_8_RGB_565;
+ break;
+ case 4:
+ pixFmt = GR_PIXFMT_AA_4_RGB_565;
+ break;
+ case 2:
+ pixFmt = GR_PIXFMT_AA_2_RGB_565;
+ break;
+ default:
+ pixFmt = GR_PIXFMT_RGB_565;
+ }
+ break;
+ case 24:
+ fxMesa->colDepth = 32;
+ case 32:
+ redBits = 8;
+ greenBits = 8;
+ blueBits = 8;
+ alphaBits = 8;
+ switch(fxMesa->fsaa) {
+ case 8:
+ pixFmt = GR_PIXFMT_AA_8_ARGB_8888;
+ break;
+ case 4:
+ pixFmt = GR_PIXFMT_AA_4_ARGB_8888;
+ break;
+ case 2:
+ pixFmt = GR_PIXFMT_AA_2_ARGB_8888;
+ break;
+ default:
+ pixFmt = GR_PIXFMT_ARGB_8888;
+ }
+ break;
+ default:
+ str = "pixelFormat";
+ goto errorhandler;
+ }
+
+ /* ZZZ TODO: check if there is enough fbRam */
+
+ /* Tips:
+ * 1. we don't bother setting/checking AUX for stencil, because we'll decide
+ * later whether we have HW stencil, based on depth buffer (thus AUX is
+ * properly set)
+ * 2. when both DEPTH and ALPHA are enabled, depth should win. However, it is
+ * not clear whether 15bpp and 32bpp require AUX alpha buffer. Furthermore,
+ * alpha buffering is required only if destination alpha is used in alpha
+ * blending; alpha blending modes that do not use destination alpha can be
+ * used w/o alpha buffer.
+ * 3. `alphaBits' is what we can provide
+ * `alphaSize' is what app requests
+ * if we cannot provide enough bits for alpha buffer, we should fallback to
+ * SW alpha. However, setting `alphaBits' to `alphaSize' might confuse some
+ * of the span functions...
+ */
+
+ fxMesa->haveHwAlpha = GL_FALSE;
+ if (alphaSize && (alphaSize <= alphaBits)) {
+ alphaSize = alphaBits;
+ fxMesa->haveHwAlpha = GL_TRUE;
+ }
+
+ fxMesa->haveHwStencil = (fxMesa->HavePixExt && stencilSize && depthSize == 24);
+
+ fxMesa->haveZBuffer = depthSize > 0;
+ fxMesa->haveDoubleBuffer = doubleBuffer;
+ fxMesa->haveGlobalPaletteTexture = GL_FALSE;
+ fxMesa->board = glbCurrentBoard;
+
+ fxMesa->haveTwoTMUs = (voodoo->nTexelfx > 1);
+
+ if ((str = Glide->grGetRegistryOrEnvironmentStringExt("FX_GLIDE_NUM_TMU"))) {
+ if (atoi(str) <= 1) {
+ fxMesa->haveTwoTMUs = GL_FALSE;
+ }
+ }
+
+ if ((str = Glide->grGetRegistryOrEnvironmentStringExt("FX_GLIDE_SWAPPENDINGCOUNT"))) {
+ fxMesa->maxPendingSwapBuffers = atoi(str);
+ if (fxMesa->maxPendingSwapBuffers > 3) {
+ fxMesa->maxPendingSwapBuffers = 3;
+ } else if (fxMesa->maxPendingSwapBuffers < 0) {
+ fxMesa->maxPendingSwapBuffers = 0;
+ }
+ } else {
+ fxMesa->maxPendingSwapBuffers = 2;
+ }
+
+ if ((str = Glide->grGetRegistryOrEnvironmentStringExt("FX_GLIDE_SWAPINTERVAL"))) {
+ fxMesa->swapInterval = atoi(str);
+ } else {
+ fxMesa->swapInterval = 0;
+ }
+
+ BEGIN_BOARD_LOCK();
+ if (fxMesa->HavePixExt) {
+ fxMesa->glideContext = Glide->grSstWinOpenExt((FxU32)win, res, ref,
+ GR_COLORFORMAT_ABGR, GR_ORIGIN_LOWER_LEFT,
+ pixFmt,
+ 2, aux);
+ } else if (pixFmt == GR_PIXFMT_RGB_565) {
+ fxMesa->glideContext = grSstWinOpen((FxU32)win, res, ref,
+ GR_COLORFORMAT_ABGR, GR_ORIGIN_LOWER_LEFT,
+ 2, aux);
+ } else {
+ fxMesa->glideContext = 0;
+ }
+ END_BOARD_LOCK();
+ if (!fxMesa->glideContext) {
+ str = "grSstWinOpen";
+ goto errorhandler;
+ }
+
+ /* screen */
+ fxMesa->screen_width = FX_grSstScreenWidth();
+ fxMesa->screen_height = FX_grSstScreenHeight();
+
+ /* window inside screen */
+ fxMesa->width = fxMesa->screen_width;
+ fxMesa->height = fxMesa->screen_height;
+
+ /* scissor inside window */
fxMesa->clipMinX = 0;
fxMesa->clipMaxX = fxMesa->width;
fxMesa->clipMinY = 0;
fxMesa->clipMaxY = fxMesa->height;
- fxMesa->screen_width = fxMesa->width;
- fxMesa->screen_height = fxMesa->height;
-
- fxMesa->new_state = ~0;
-
- if(verbose)
- fprintf(stderr,"Voodoo Glide screen size: %dx%d\n",
- (int)FX_grSstScreenWidth(),(int)FX_grSstScreenHeight());
-
- fxMesa->glVis=_mesa_create_visual(GL_TRUE, /* RGB mode */
- doubleBuffer,
- GL_FALSE, /* stereo */
- 5,6,5,0, /* RGBA bits */
- 0, /* index bits */
- depthSize, /* depth_size */
- stencilSize, /* stencil_size */
- accumSize, accumSize, accumSize, accumSize,
- 1 );
+ if (fxMesa->verbose) {
+ FxI32 tmuRam, fbRam;
+
+ /* Not that it matters, but tmuRam and fbRam change after grSstWinOpen. */
+ tmuRam = voodoo->tmuConfig[GR_TMU0].tmuRam;
+ fbRam = voodoo->fbRam;
+ BEGIN_BOARD_LOCK();
+ grGet(GR_MEMORY_TMU, 4, &tmuRam);
+ grGet(GR_MEMORY_FB, 4, &fbRam);
+ END_BOARD_LOCK();
+
+ fprintf(stderr, "Voodoo Using Glide %s\n", grGetString(GR_VERSION));
+ fprintf(stderr, "Voodoo Board: %d/%d, %s, %d GPU\n",
+ fxMesa->board + 1,
+ glbHWConfig.num_sst,
+ grGetString(GR_HARDWARE),
+ voodoo->numChips);
+ fprintf(stderr, "Voodoo Memory: FB = %ld, TM = %d x %ld\n",
+ fbRam,
+ voodoo->nTexelfx,
+ tmuRam);
+ fprintf(stderr, "Voodoo Screen: %dx%d:%d %s, %svertex snapping\n",
+ fxMesa->screen_width,
+ fxMesa->screen_height,
+ colDepth,
+ fxMesa->bgrOrder ? "BGR" : "RGB",
+ fxMesa->snapVertices ? "" : "no ");
+ }
+
+ sprintf(fxMesa->rendererString, "Mesa %s v0.61 %s%s",
+ grGetString(GR_RENDERER),
+ grGetString(GR_HARDWARE),
+ ((fxMesa->type < GR_SSTTYPE_Voodoo4) && (voodoo->numChips > 1)) ? " SLI" : "");
+
+ fxMesa->glVis = _mesa_create_visual(GL_TRUE, /* RGB mode */
+ doubleBuffer,
+ GL_FALSE, /* stereo */
+ redBits, /* RGBA.R bits */
+ greenBits, /* RGBA.G bits */
+ blueBits, /* RGBA.B bits */
+ alphaSize, /* RGBA.A bits */
+ 0, /* index bits */
+ depthSize, /* depth_size */
+ stencilSize, /* stencil_size */
+ accumSize,
+ accumSize,
+ accumSize,
+ alphaSize ? accumSize : 0,
+ 1);
if (!fxMesa->glVis) {
- errorstr = "_mesa_create_visual";
+ str = "_mesa_create_visual";
goto errorhandler;
}
- ctx = fxMesa->glCtx=_mesa_create_context(fxMesa->glVis,
- shareCtx, /* share list context */
- (void *) fxMesa, GL_TRUE);
+ _mesa_init_driver_functions(&functions);
+ ctx = fxMesa->glCtx = _mesa_create_context(fxMesa->glVis, shareCtx,
+ &functions, (void *) fxMesa);
if (!ctx) {
- errorstr = "_mesa_create_context";
+ str = "_mesa_create_context";
goto errorhandler;
}
- if (!fxDDInitFxMesaContext( fxMesa )) {
- errorstr = "fxDDInitFxMesaContext failed";
+ if (!fxDDInitFxMesaContext(fxMesa)) {
+ str = "fxDDInitFxMesaContext";
goto errorhandler;
}
- fxMesa->glBuffer=_mesa_create_framebuffer(fxMesa->glVis,
- GL_FALSE, /* no software depth */
- fxMesa->glVis->StencilBits > 0,
- fxMesa->glVis->AccumRedBits > 0,
- fxMesa->glVis->AlphaBits > 0 );
+ fxMesa->glBuffer = _mesa_create_framebuffer(fxMesa->glVis,
+ GL_FALSE, /* no software depth */
+ stencilSize && !fxMesa->haveHwStencil,
+ fxMesa->glVis->accumRedBits > 0,
+ alphaSize && !fxMesa->haveHwAlpha);
if (!fxMesa->glBuffer) {
- errorstr = "_mesa_create_framebuffer";
+ str = "_mesa_create_framebuffer";
goto errorhandler;
}
-
+
glbTotNumCtx++;
/* install signal handlers */
#if defined(__linux__)
/* Only install if environment var. is not set. */
- if (fxMesa->glCtx->CatchSignals && !getenv("MESA_FX_NO_SIGNALS")) {
- 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);
+ if (!getenv("MESA_FX_NO_SIGNALS")) {
+ 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);
}
#endif
- if (MESA_VERBOSE&VERBOSE_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->fogTable)
- free(fxMesa->fogTable);
- if (fxMesa->glBuffer)
- _mesa_destroy_framebuffer(fxMesa->glBuffer);
- if (fxMesa->glVis)
- _mesa_destroy_visual(fxMesa->glVis);
- if (fxMesa->glCtx)
- _mesa_destroy_context(fxMesa->glCtx);
- free(fxMesa);
- }
-
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaCreateContext() End (%s)\n",errorstr);
- }
- return NULL;
+errorhandler:
+ if (fxMesa) {
+ if (fxMesa->glideContext) {
+ grSstWinClose(fxMesa->glideContext);
+ fxMesa->glideContext = 0;
+ }
+
+ if (fxMesa->state) {
+ FREE(fxMesa->state);
+ }
+ if (fxMesa->fogTable) {
+ FREE(fxMesa->fogTable);
+ }
+ if (fxMesa->glBuffer) {
+ _mesa_destroy_framebuffer(fxMesa->glBuffer);
+ }
+ if (fxMesa->glVis) {
+ _mesa_destroy_visual(fxMesa->glVis);
+ }
+ if (fxMesa->glCtx) {
+ _mesa_destroy_context(fxMesa->glCtx);
+ }
+ FREE(fxMesa);
+ }
+
+ fprintf(stderr, "fxMesaCreateContext: ERROR: %s\n", str);
+ return NULL;
}
/*
* Function to set the new window size in the context (mainly for the Voodoo Rush)
*/
-void GLAPIENTRY fxMesaUpdateScreenSize(fxMesaContext fxMesa)
+void GLAPIENTRY
+fxMesaUpdateScreenSize(fxMesaContext fxMesa)
{
- fxMesa->width=FX_grSstScreenWidth();
- fxMesa->height=FX_grSstScreenHeight();
+ fxMesa->width = FX_grSstScreenWidth();
+ fxMesa->height = FX_grSstScreenHeight();
}
/*
* Destroy the given FX/Mesa context.
*/
-void GLAPIENTRY fxMesaDestroyContext(fxMesaContext fxMesa)
+void GLAPIENTRY
+fxMesaDestroyContext(fxMesaContext fxMesa)
{
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaDestroyContext()\n");
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaDestroyContext(...)\n");
}
- if(!fxMesa)
+ if (!fxMesa)
return;
- if(fxMesa->verbose) {
- fprintf(stderr,"Misc Stats:\n");
- fprintf(stderr," # swap buffer: %u\n",fxMesa->stats.swapBuffer);
+ 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;
+ 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",
+ 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",
+ 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));
+ 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));
}
glbTotNumCtx--;
-
+
+ if (!glbTotNumCtx && getenv("MESA_FX_INFO")) {
+ GrSstPerfStats_t st;
+
+ FX_grSstPerfStats(&st);
+
+ fprintf(stderr, "Pixels Stats:\n");
+ fprintf(stderr, " # pixels processed (minus buffer clears): %u\n",
+ (unsigned) st.pixelsIn);
+ fprintf(stderr, " # pixels not drawn due to chroma key test failure: %u\n",
+ (unsigned) st.chromaFail);
+ fprintf(stderr, " # pixels not drawn due to depth test failure: %u\n",
+ (unsigned) st.zFuncFail);
+ fprintf(stderr,
+ " # pixels not drawn due to alpha test failure: %u\n",
+ (unsigned) st.aFuncFail);
+ fprintf(stderr, " # pixels drawn (including buffer clears and LFB writes): %u\n",
+ (unsigned) st.pixelsOut);
+ }
+
+ /* [dBorca]
+ * close the hardware first, so we can debug
+ * atexit problems (memory leaks, etc).
+ * NB: fxDDDestroyFxMesaContext must be called
+ * before _mesa_destroy_context; which must be
+ * called before fxTMClose!
+ */
+ grSstWinClose(fxMesa->glideContext);
+ fxCloseHardware();
+
fxDDDestroyFxMesaContext(fxMesa);
_mesa_destroy_visual(fxMesa->glVis);
_mesa_destroy_context(fxMesa->glCtx);
_mesa_destroy_framebuffer(fxMesa->glBuffer);
+ fxTMClose(fxMesa);
- fxCloseHardware();
- FX_grSstWinClose(fxMesa->glideContext);
-
- free(fxMesa);
+ FREE(fxMesa);
- if(fxMesa==fxMesaCurrentCtx)
- fxMesaCurrentCtx=NULL;
+ if (fxMesa == fxMesaCurrentCtx)
+ fxMesaCurrentCtx = NULL;
}
/*
* Make the specified FX/Mesa context the current one.
*/
-void GLAPIENTRY fxMesaMakeCurrent(fxMesaContext fxMesa)
+void GLAPIENTRY
+fxMesaMakeCurrent(fxMesaContext fxMesa)
{
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaMakeCurrent(...) Start\n");
- }
+ if (!fxMesa) {
+ _mesa_make_current(NULL, NULL);
+ fxMesaCurrentCtx = NULL;
- if(!fxMesa) {
- _mesa_make_current(NULL,NULL);
- fxMesaCurrentCtx=NULL;
-
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaMakeCurrent(NULL) End\n");
- }
-
- return;
- }
-
- /* if this context is already the current one, we can return early */
- if (fxMesaCurrentCtx == fxMesa
- && fxMesaCurrentCtx->glCtx == _mesa_get_current_context()) {
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaMakeCurrent(fxMesaCurrentCtx==fxMesa) End\n");
- }
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaMakeCurrent(NULL)\n");
+ }
- return;
- }
+ return;
+ }
- if(fxMesaCurrentCtx)
- grGlideGetState((GrState*)fxMesaCurrentCtx->state);
+ /* if this context is already the current one, we can return early */
+ if (fxMesaCurrentCtx == fxMesa
+ && fxMesaCurrentCtx->glCtx == _mesa_get_current_context()) {
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaMakeCurrent(NOP)\n");
+ }
- fxMesaCurrentCtx=fxMesa;
+ return;
+ }
- grSstSelect(fxMesa->board);
- grGlideSetState((GrState*)fxMesa->state);
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaMakeCurrent(...)\n");
+ }
- _mesa_make_current(fxMesa->glCtx,fxMesa->glBuffer);
+ if (fxMesaCurrentCtx)
+ grGlideGetState((GrState *) fxMesaCurrentCtx->state);
- fxSetupDDPointers(fxMesa->glCtx);
+ fxMesaCurrentCtx = fxMesa;
- /* The first time we call MakeCurrent we set the initial viewport size */
- if(fxMesa->glCtx->Viewport.Width==0)
- gl_Viewport(fxMesa->glCtx,0,0,fxMesa->width,fxMesa->height);
+ grSstSelect(fxMesa->board);
+ grGlideSetState((GrState *) fxMesa->state);
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaMakeCurrent(...) End\n");
- }
-}
+ _mesa_make_current(fxMesa->glCtx, fxMesa->glBuffer);
+ fxSetupDDPointers(fxMesa->glCtx);
-#if 0
-static void QueryCounters(void)
-{
- static GLuint prevPassed = 0;
- static GLuint prevFailed = 0;
- GLuint failed, passed;
- GrSstPerfStats_t st;
-
- FX_grSstPerfStats(&st);
- failed = st.zFuncFail - st.aFuncFail - st.chromaFail;
- passed = st.pixelsIn - failed;
- printf("failed: %d passed: %d\n", failed - prevFailed, passed - prevPassed);
-
- prevPassed = passed;
- prevFailed = failed;
+ /* The first time we call MakeCurrent we set the initial viewport size */
+ if (fxMesa->glCtx->Viewport.Width == 0)
+ _mesa_set_viewport(fxMesa->glCtx, 0, 0, fxMesa->width, fxMesa->height);
}
-#endif
/*
* Swap front/back buffers for current context if double buffered.
*/
-void GLAPIENTRY fxMesaSwapBuffers(void)
+void GLAPIENTRY
+fxMesaSwapBuffers(void)
{
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: ------------------------------- fxMesaSwapBuffers() -------------------------------\n");
- }
-
- if(fxMesaCurrentCtx) {
- _mesa_swapbuffers( fxMesaCurrentCtx->glCtx );
-
- if(fxMesaCurrentCtx->haveDoubleBuffer) {
-
- grBufferSwap(fxMesaCurrentCtx->swapInterval);
-
- /*
- * Don't allow swap buffer commands to build up!
- */
- while(FX_grGetInteger(FX_PENDING_BUFFERSWAPS)>fxMesaCurrentCtx->maxPendingSwapBuffers)
- /* The driver is able to sleep when waiting for the completation
- of multiple swapbuffer operations instead of wasting
- CPU time (NOTE: you must uncomment the following line in the
- in order to enable this option) */
- /* usleep(10000); */
- ;
-
- fxMesaCurrentCtx->stats.swapBuffer++;
- }
- }
-}
+ if (TDFX_DEBUG & VERBOSE_DRIVER) {
+ fprintf(stderr, "fxMesaSwapBuffers()\n");
+ }
+ if (fxMesaCurrentCtx) {
+ _mesa_notifySwapBuffers(fxMesaCurrentCtx->glCtx);
-/*
- * Query 3Dfx hardware presence/kind
- */
-int GLAPIENTRY fxQueryHardware(void)
-{
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxQueryHardware() Start\n");
- }
+ if (fxMesaCurrentCtx->haveDoubleBuffer) {
- if (!glbGlideInitialized) {
- grGlideInit();
- if (FX_grSstQueryHardware(&glbHWConfig)) {
- grSstSelect(glbCurrentBoard);
- glb3DfxPresent = 1;
-
- if (getenv("MESA_FX_INFO")) {
- char buf[80];
-
- FX_grGlideGetVersion(buf);
- fprintf(stderr, "Voodoo Using Glide V%s\n", buf);
- fprintf(stderr, "Voodoo Number of boards: %d\n", glbHWConfig.num_sst);
-
- if (glbHWConfig.SSTs[glbCurrentBoard].type == GR_SSTTYPE_VOODOO) {
- GrVoodooConfig_t *voodoo;
- voodoo = &glbHWConfig.SSTs[glbCurrentBoard].sstBoard.VoodooConfig;
-
- fprintf(stderr, "Voodoo Framebuffer RAM: %d\n",
- voodoo->sliDetect ? (voodoo->fbRam*2) : voodoo->fbRam);
- fprintf(stderr, "Voodoo Number of TMUs: %d\n", voodoo->nTexelfx);
- fprintf(stderr, "Voodoo fbRam: %d\n", voodoo->fbRam);
- fprintf(stderr, "Voodoo fbiRev: %d\n", voodoo->fbiRev);
-
- fprintf(stderr,"Voodoo SLI detected: %d\n", voodoo->sliDetect);
- }
- else if (glbHWConfig.SSTs[glbCurrentBoard].type == GR_SSTTYPE_SST96) {
- GrSst96Config_t *sst96;
- sst96 = &glbHWConfig.SSTs[glbCurrentBoard].sstBoard.SST96Config;
- fprintf(stderr, "Voodoo Framebuffer RAM: %d\n", sst96->fbRam);
- fprintf(stderr, "Voodoo Number of TMUs: %d\n", sst96->nTexelfx);
- }
+ grBufferSwap(fxMesaCurrentCtx->swapInterval);
- }
- }
- else {
- glb3DfxPresent = 0;
- }
-
- glbGlideInitialized = 1;
-
-#if defined(__WIN32__)
- onexit((_onexit_t)cleangraphics);
-#elif defined(__linux__)
- /* Only register handler if environment variable is not defined. */
- if (!getenv("MESA_FX_NO_SIGNALS")) {
- atexit(cleangraphics);
- }
+#if 0
+ /*
+ * Don't allow swap buffer commands to build up!
+ */
+ while (FX_grGetInteger(GR_PENDING_BUFFERSWAPS) >
+ fxMesaCurrentCtx->maxPendingSwapBuffers)
+ /* The driver is able to sleep when waiting for the completation
+ of multiple swapbuffer operations instead of wasting
+ CPU time (NOTE: you must uncomment the following line in the
+ in order to enable this option) */
+ /* usleep(10000); */
+ ;
#endif
- }
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxQueryHardware() End (voodooo)\n");
- }
-
- return glbHWConfig.SSTs[glbCurrentBoard].type;
+ fxMesaCurrentCtx->stats.swapBuffer++;
+ }
+ }
}
/*
* Shutdown Glide library
*/
-void GLAPIENTRY fxCloseHardware(void)
+void GLAPIENTRY
+fxCloseHardware(void)
{
- if (glbGlideInitialized) {
- if (getenv("MESA_FX_INFO")) {
- GrSstPerfStats_t st;
-
- FX_grSstPerfStats(&st);
- fprintf(stderr,"Pixels Stats:\n");
- fprintf(stderr," # pixels processed (minus buffer clears): %u\n",(unsigned)st.pixelsIn);
- fprintf(stderr," # pixels not drawn due to chroma key test failure: %u\n",(unsigned)st.chromaFail);
- fprintf(stderr," # pixels not drawn due to depth test failure: %u\n",(unsigned)st.zFuncFail);
- fprintf(stderr," # pixels not drawn due to alpha test failure: %u\n",(unsigned)st.aFuncFail);
- fprintf(stderr," # pixels drawn (including buffer clears and LFB writes): %u\n",(unsigned)st.pixelsOut);
- }
-
- if (glbTotNumCtx == 0) {
- grGlideShutdown();
- glbGlideInitialized = 0;
- }
- }
+ if (glbGlideInitialized) {
+ if (glbTotNumCtx == 0) {
+ grGlideShutdown();
+ glbGlideInitialized = 0;
+ }
+ }
}
* Need this to provide at least one external definition.
*/
extern int gl_fx_dummy_function_api(void);
-int gl_fx_dummy_function_api(void)
+int
+gl_fx_dummy_function_api(void)
{
- return 0;
+ return 0;
}
-#endif /* FX */
+#endif /* FX */