summaryrefslogtreecommitdiffstats
path: root/src/mesa/drivers/glide
diff options
context:
space:
mode:
Diffstat (limited to 'src/mesa/drivers/glide')
-rw-r--r--src/mesa/drivers/glide/fxapi.c61
-rw-r--r--src/mesa/drivers/glide/fxdd.c92
-rw-r--r--src/mesa/drivers/glide/fxddtex.c38
-rw-r--r--src/mesa/drivers/glide/fxdrv.h124
-rw-r--r--src/mesa/drivers/glide/fxsetup.c14
-rw-r--r--src/mesa/drivers/glide/fxtris.c568
-rw-r--r--src/mesa/drivers/glide/fxvb.c403
-rw-r--r--src/mesa/drivers/glide/fxvbtmp.h143
8 files changed, 1298 insertions, 145 deletions
diff --git a/src/mesa/drivers/glide/fxapi.c b/src/mesa/drivers/glide/fxapi.c
index f3a6431aec5..6470affd9aa 100644
--- a/src/mesa/drivers/glide/fxapi.c
+++ b/src/mesa/drivers/glide/fxapi.c
@@ -581,55 +581,52 @@ void GLAPIENTRY fxMesaUpdateScreenSize(fxMesaContext fxMesa)
*/
void GLAPIENTRY fxMesaDestroyContext(fxMesaContext fxMesa)
{
- if (MESA_VERBOSE&VERBOSE_DRIVER) {
- fprintf(stderr,"fxmesa: fxMesaDestroyContext()\n");
- }
-
- if(fxMesa) {
- _mesa_destroy_visual(fxMesa->glVis);
- _mesa_destroy_context(fxMesa->glCtx);
- _mesa_destroy_framebuffer(fxMesa->glBuffer);
-
- glbTotNumCtx--;
+ if (MESA_VERBOSE&VERBOSE_DRIVER) {
+ fprintf(stderr,"fxmesa: fxMesaDestroyContext()\n");
+ }
- fxCloseHardware();
- FX_grSstWinClose(fxMesa->glideContext);
+ if(!fxMesa)
+ return;
- if(fxMesa->verbose) {
+ 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;
+ 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," 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);
+ fxMesa->stats.reqTexUpload);
fprintf(stderr," # request to TMM to upload a texture objects per swapbuffer: %.2f\n",
- fxMesa->stats.reqTexUpload/(float)fxMesa->stats.swapBuffer);
+ fxMesa->stats.reqTexUpload/(float)fxMesa->stats.swapBuffer);
fprintf(stderr," # texture objects uploaded: %u\n",
- fxMesa->stats.texUpload);
+ fxMesa->stats.texUpload);
fprintf(stderr," # texture objects uploaded per swapbuffer: %.2f\n",
- fxMesa->stats.texUpload/(float)fxMesa->stats.swapBuffer);
+ fxMesa->stats.texUpload/(float)fxMesa->stats.swapBuffer);
fprintf(stderr," # MBs uploaded to texture memory: %.2f\n",
- fxMesa->stats.memTexUpload/(float)(1<<20));
+ 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);
- }
+ (fxMesa->stats.memTexUpload/(float)fxMesa->stats.swapBuffer)/(float)(1<<20));
+ }
- if(fxMesa==fxMesaCurrentCtx)
- fxMesaCurrentCtx=NULL;
+ glbTotNumCtx--;
+
+ fxDDDestroyFxMesaContext(fxMesa);
+ _mesa_destroy_visual(fxMesa->glVis);
+ _mesa_destroy_context(fxMesa->glCtx);
+ _mesa_destroy_framebuffer(fxMesa->glBuffer);
+
+ fxCloseHardware();
+ FX_grSstWinClose(fxMesa->glideContext);
+
+ free(fxMesa);
+
+ if(fxMesa==fxMesaCurrentCtx)
+ fxMesaCurrentCtx=NULL;
}
diff --git a/src/mesa/drivers/glide/fxdd.c b/src/mesa/drivers/glide/fxdd.c
index c7229561d7c..3bbe42328a9 100644
--- a/src/mesa/drivers/glide/fxdd.c
+++ b/src/mesa/drivers/glide/fxdd.c
@@ -59,6 +59,7 @@
#include "swrast/swrast.h"
#include "swrast_setup/swrast_setup.h"
#include "tnl/tnl.h"
+#include "array_cache/acache.h"
/* These lookup table are used to extract RGB values in [0,255] from
* 16-bit pixel values.
@@ -644,9 +645,38 @@ static const GLubyte *fxDDGetString(GLcontext *ctx, GLenum name)
}
}
+#if 0
+static const struct gl_pipeline_stage * const fx_pipeline[] = {
+ &_tnl_update_material_stage,
+ &_tnl_vertex_transform_stage,
+ &_tnl_normal_transform_stage,
+ &_tnl_lighting_stage, /* OMIT: fog coordinate stage */
+ &_tnl_texgen_stage,
+ &_tnl_texture_transform_stage,
+ &_tnl_point_attenuation_stage,
+ &_fx_fast_render_stage, /* ADD: the fastpath as a render stage */
+ &_tnl_render_stage, /* KEEP: the old render stage for fallbacks */
+ 0
+};
+#else
+/* Need to turn off tnl fogging, both the stage and the clipping in
+ * _tnl_render_stage. Could insert a dummy stage that did nothing but
+ * provided storage that clipping could spin on?
+ */
+#endif
+
+
int fxDDInitFxMesaContext( fxMesaContext fxMesa )
{
+ static int firsttime = 1;
+
+ if (firsttime) {
+ fxDDSetupInit();
+ fxDDTrifuncInit();
+/* fxDDFastPathInit(); */
+ firsttime = 0;
+ }
FX_setupGrVertexLayout();
@@ -734,18 +764,14 @@ int fxDDInitFxMesaContext( fxMesaContext fxMesa )
fxMesa->glCtx->Const.MaxTextureUnits=fxMesa->emulateTwoTMUs ? 2 : 1;
fxMesa->new_state = _NEW_ALL;
- fxDDSetupInit();
- fxDDTrifuncInit();
- fxDDFastPathInit();
-
-
/* Initialize the software rasterizer and helper modules.
*/
- fxMesa->glCtx->Driver.RegisterVB = fxDDRegisterVB;
-
_swrast_CreateContext( fxMesa->glCtx );
- _swsetup_CreateContext( fxMesa->glCtx );
+ _ac_CreateContext( fxMesa->glCtx );
_tnl_CreateContext( fxMesa->glCtx );
+ _swsetup_CreateContext( fxMesa->glCtx );
+
+ fxAllocVB( fxMesa->glCtx );
fxSetupDDPointers(fxMesa->glCtx);
@@ -755,22 +781,36 @@ int fxDDInitFxMesaContext( fxMesaContext fxMesa )
_swrast_allow_pixel_fog( fxMesa->glCtx, GL_TRUE );
fxDDInitExtensions(fxMesa->glCtx);
+
+#ifdef FXVTXFMT
fxDDInitVtxfmt(fxMesa->glCtx);
+#endif
FX_grGlideGetState((GrState*)fxMesa->state);
- /* 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.
- */
- fxDDRegisterPipelineStages( fxMesa->glCtx );
-
/* Run the config file */
_mesa_context_initialize( fxMesa->glCtx );
return 1;
}
+/* Undo the above.
+ */
+void fxDDDestroyFxMesaContext( fxMesaContext fxMesa )
+{
+ _swsetup_DestroyContext( fxMesa->glCtx );
+ _tnl_DestroyContext( fxMesa->glCtx );
+ _ac_DestroyContext( fxMesa->glCtx );
+ _swrast_DestroyContext( fxMesa->glCtx );
+
+ if (fxMesa->state)
+ free(fxMesa->state);
+ if (fxMesa->fogTable)
+ free(fxMesa->fogTable);
+ fxTMClose(fxMesa);
+ fxFreeVB(fxMesa->glCtx);
+}
+
@@ -784,6 +824,9 @@ void fxDDInitExtensions( GLcontext *ctx )
gl_extensions_disable(ctx, "GL_EXT_blend_color");
gl_extensions_disable(ctx, "GL_EXT_fog_coord");
+ if (1)
+ gl_extensions_disable(ctx, "GL_EXT_point_parameters");
+
gl_extensions_add(ctx, GL_TRUE, "3DFX_set_global_palette", 0);
if (!fxMesa->haveTwoTMUs)
@@ -922,14 +965,14 @@ static void update_texture_scales( GLcontext *ctx )
}
}
-static void fxDDUpdateDDPointers(GLcontext *ctx)
+static void fxDDUpdateDDPointers(GLcontext *ctx, GLuint new_state)
{
fxMesaContext fxMesa = FX_CONTEXT(ctx);
- GLuint new_state = ctx->NewState;
_swrast_InvalidateState( ctx, new_state );
- _swsetup_InvalidateState( ctx, new_state );
+ _ac_InvalidateState( ctx, new_state );
_tnl_InvalidateState( ctx, new_state );
+ _swsetup_InvalidateState( ctx, new_state );
/* Recalculate fog table on projection matrix changes. This used to
* be triggered by the NearFar callback.
@@ -954,22 +997,22 @@ static void fxDDUpdateDDPointers(GLcontext *ctx)
fxDDChooseRenderState( ctx );
if (new_state & _FX_NEW_SETUP_FUNCTION)
- ctx->Driver.RasterSetup = fxDDChooseSetupFunction(ctx);
+ ctx->Driver.BuildProjectedVertices = fx_validate_BuildProjVerts;
if (new_state & _NEW_TEXTURE)
update_texture_scales( ctx );
}
+#ifdef FXVTXFMT
if (fxMesa->allow_vfmt) {
if (new_state & _NEW_LIGHT)
fx_update_lighting( ctx );
if (new_state & _FX_NEW_VTXFMT)
fxDDCheckVtxfmt( ctx );
- else if (fxMesa->vtxfmt_fallback_count > 1)
- fxMesa->vtxfmt_fallback_count--;
}
+#endif
}
@@ -1006,6 +1049,7 @@ void fxSetupDDPointers(GLcontext *ctx)
ctx->Driver.RenderStart=fxSetupFXUnits;
ctx->Driver.RenderFinish=_swrast_flush;
+ ctx->Driver.ResetLineStipple=_swrast_ResetLineStipple;
ctx->Driver.TexImage2D = fxDDTexImage2D;
ctx->Driver.TexSubImage2D = fxDDTexSubImage2D;
@@ -1028,14 +1072,10 @@ void fxSetupDDPointers(GLcontext *ctx)
ctx->Driver.ShadeModel=fxDDShadeModel;
ctx->Driver.Enable=fxDDEnable;
- ctx->Driver.RegisterVB=fxDDRegisterVB;
- ctx->Driver.UnregisterVB=fxDDUnregisterVB;
-
- if (!getenv("FX_NO_FAST"))
- ctx->Driver.BuildPrecalcPipeline = fxDDBuildPrecalcPipeline;
+
fxSetupDDSpanPointers(ctx);
- fxDDUpdateDDPointers(ctx);
+ fxDDUpdateDDPointers(ctx,~0);
}
diff --git a/src/mesa/drivers/glide/fxddtex.c b/src/mesa/drivers/glide/fxddtex.c
index f7beaf7e34f..7c101e823d9 100644
--- a/src/mesa/drivers/glide/fxddtex.c
+++ b/src/mesa/drivers/glide/fxddtex.c
@@ -333,11 +333,6 @@ void fxDDTexDel(GLcontext *ctx, struct gl_texture_object *tObj)
FREE(ti);
tObj->DriverData = NULL;
-
-/* Pushed into core: Set _NEW_TEXTURE whenever a bound texture is
- * deleted (changes bound texture id).
- */
-/* ctx->NewState |= _NEW_TEXTURE; */
}
@@ -824,6 +819,23 @@ static GLboolean fxIsTexSupported(GLenum target, GLint internalFormat,
/**** NEW TEXTURE IMAGE FUNCTIONS ****/
/**********************************************************************/
+
+static void PrintTexture(int w, int h, int c, const GLubyte *data)
+{
+ int i, j;
+ for (i = 0; i < h; i++) {
+ for (j = 0; j < w; j++) {
+ if (c==2)
+ printf("%02x %02x ", data[0], data[1]);
+ else if (c==3)
+ printf("%02x %02x %02x ", data[0], data[1], data[2]);
+ data += c;
+ }
+ printf("\n");
+ }
+}
+
+
GLboolean fxDDTexImage2D(GLcontext *ctx, GLenum target, GLint level,
GLenum format, GLenum type, const GLvoid *pixels,
const struct gl_pixelstore_attrib *packing,
@@ -960,6 +972,7 @@ GLboolean fxDDTexImage2D(GLcontext *ctx, GLenum target, GLint level,
return GL_FALSE;
}
+
if (ti->validated && ti->isInTM) {
/*printf("reloadmipmaplevels\n");*/
fxTMReloadMipMapLevel(fxMesa, texObj, level);
@@ -1082,21 +1095,6 @@ GLboolean fxDDTexSubImage2D(GLcontext *ctx, GLenum target, GLint level,
}
-static void PrintTexture(int w, int h, int c, const GLubyte *data)
-{
- int i, j;
- for (i = 0; i < h; i++) {
- for (j = 0; j < w; j++) {
- if (c==2)
- printf("%02x %02x ", data[0], data[1]);
- else if (c==3)
- printf("%02x %02x %02x ", data[0], data[1], data[2]);
- data += c;
- }
- printf("\n");
- }
-}
-
GLvoid *fxDDGetTexImage(GLcontext *ctx, GLenum target, GLint level,
const struct gl_texture_object *texObj,
diff --git a/src/mesa/drivers/glide/fxdrv.h b/src/mesa/drivers/glide/fxdrv.h
index 9146966c212..4e4eea96a3b 100644
--- a/src/mesa/drivers/glide/fxdrv.h
+++ b/src/mesa/drivers/glide/fxdrv.h
@@ -142,8 +142,9 @@ typedef void (*vfmt_interpolate_func)( GLfloat t,
#define SETUP_TMU0 0x1
#define SETUP_TMU1 0x2
#define SETUP_RGBA 0x4
-#define SETUP_XYZW 0x8
-#define MAX_SETUP 0x10
+#define SETUP_SNAP 0x8
+#define SETUP_XYZW 0x10
+#define MAX_SETUP 0x20
#define FX_NUM_TMU 2
@@ -291,19 +292,7 @@ typedef struct {
#define FX_NEW_COLOR_MASK 0x40
#define FX_NEW_CULL 0x80
-/* FX struct stored in VB->driver_data.
- */
-struct tfxMesaVertexBuffer {
- GLvector1ui clipped_elements;
-
- fxVertex *verts;
- fxVertex *last_vert;
- void *vert_store;
-
- GLuint size;
-};
-#define FX_DRIVER_DATA(vb) ((struct tfxMesaVertexBuffer *)((vb)->driver_data))
#define FX_CONTEXT(ctx) ((fxMesaContext)((ctx)->DriverCtx))
#define FX_TEXTURE_DATA(t) fxTMGetTexInfo((t)->_Current)
@@ -350,10 +339,13 @@ struct tfxMesaVertexBuffer {
/* Covers the state referenced in fxDDCheckVtxfmt.
*/
-#define _FX_NEW_VTXFMT (_NEW_TEXTURE | \
- _NEW_TEXTURE_MATRIX | \
- _NEW_TRANSFORM | \
- _NEW_LIGHT | \
+#define _FX_NEW_VTXFMT (_NEW_TEXTURE | \
+ _NEW_TEXTURE_MATRIX | \
+ _NEW_TRANSFORM | \
+ _NEW_LIGHT | \
+ _NEW_PROJECTION | \
+ _NEW_MODELVIEW | \
+ _TNL_NEW_NEED_EYE_COORDS | \
_FX_NEW_RENDERSTATE)
@@ -365,10 +357,10 @@ extern GLubyte FX_PixelToG[0x10000];
extern GLubyte FX_PixelToB[0x10000];
-typedef void (*fx_tri_func)( GLcontext *, const fxVertex *, const fxVertex *, const fxVertex * );
+typedef void (*fx_tri_func)( GLcontext *, const fxVertex *,
+ const fxVertex *, const fxVertex * );
typedef void (*fx_line_func)( GLcontext *, const fxVertex *, const fxVertex * );
typedef void (*fx_point_func)( GLcontext *, const fxVertex * );
-typedef void (*fxRenderEltsFunc)( struct vertex_buffer * );
struct tfxMesaContext {
GuTexPalette glbPalette;
@@ -392,18 +384,11 @@ struct tfxMesaContext {
tfxUnitsState unitsState;
tfxUnitsState restoreUnitsState; /* saved during multipass */
- GLuint tmu_source[FX_NUM_TMU];
- GLuint tex_dest[MAX_TEXTURE_UNITS];
- GLuint render_index;
- GLuint setupindex;
- GLuint setupdone;
- GLuint stw_hint_state; /* for grHints */
- GLuint is_in_hardware;
- GLuint new_state;
- GLuint using_fast_path, passes, multipass;
- /* Texture Memory Manager Data */
+ GLuint new_state;
+ /* Texture Memory Manager Data
+ */
GLuint texBindNumber;
GLint tmuSrc;
GLuint lastUnitsMode;
@@ -417,14 +402,28 @@ struct tfxMesaContext {
GrFog_t *fogTable;
GLint textureAlign;
- /* Acc. functions */
+ /* Vertex building and storage:
+ */
+ GLuint tmu_source[FX_NUM_TMU];
+ GLuint tex_dest[MAX_TEXTURE_UNITS];
+ GLuint setupindex;
+ GLuint setup_gone; /* for multipass */
+ GLuint stw_hint_state; /* for grHints */
+ fxVertex *verts;
+
+ /* Rasterization:
+ */
+ GLuint render_index;
+ GLuint passes, multipass;
+ GLuint is_in_hardware;
+
+ /* Current rasterization functions
+ */
fx_point_func draw_point;
fx_line_func draw_line;
fx_tri_func draw_tri;
- fxRenderEltsFunc RenderElementsRaw;
-
/* System to turn culling on/off for tris/lines/points.
*/
fx_point_func initial_point;
@@ -435,6 +434,8 @@ struct tfxMesaContext {
fx_line_func subsequent_line;
fx_tri_func subsequent_tri;
+ /* Keep texture scales somewhere handy:
+ */
GLfloat s0scale;
GLfloat s1scale;
GLfloat t0scale;
@@ -445,8 +446,9 @@ struct tfxMesaContext {
GLfloat inv_t0scale;
GLfloat inv_t1scale;
+ /* Glide stuff
+ */
tfxStats stats;
-
void *state;
/* Options */
@@ -476,7 +478,6 @@ struct tfxMesaContext {
GLboolean allow_vfmt;
GLvertexformat vtxfmt;
fxClipVertex current;
- fxClipVertex verts[4];
fxClipVertex *vert; /* points into verts[] */
void (*fire_on_vertex)( GLcontext * );
void (*fire_on_end)( GLcontext * );
@@ -492,29 +493,42 @@ struct tfxMesaContext {
GLuint accel_light;
GLfloat basecolor[4];
+
+
+ /* Projected vertices, fastpath data:
+ */
+ GLvector1ui clipped_elements;
+ fxVertex *last_vert;
+ GLuint size;
};
-typedef void (*tfxSetupFunc)(struct vertex_buffer *, GLuint, GLuint);
+typedef void (*tfxSetupFunc)(GLcontext *ctx, GLuint, GLuint, GLuint);
extern GrHwConfiguration glbHWConfig;
extern int glbCurrentBoard;
-extern void fxPrintSetupFlags( const char *msg, GLuint flags );
extern void fxSetupFXUnits(GLcontext *);
extern void fxSetupDDPointers(GLcontext *);
+/* fxvsetup:
+ */
extern void fxDDSetupInit(void);
-extern void fxDDCvaInit(void);
+extern void fxAllocVB( GLcontext *ctx );
+extern void fxFreeVB( GLcontext *ctx );
+extern void fxPrintSetupFlags( const char *msg, GLuint flags );
+extern void fx_BuildProjVerts( GLcontext *ctx,
+ GLuint start, GLuint count,
+ GLuint newinputs );
+extern void fx_validate_BuildProjVerts(GLcontext *ctx,
+ GLuint start, GLuint count,
+ GLuint newinputs );
+
+/* fxtrifuncs:
+ */
extern void fxDDTrifuncInit(void);
-extern void fxDDFastPathInit(void);
-
extern void fxDDChooseRenderState( GLcontext *ctx );
-extern tfxSetupFunc fxDDChooseSetupFunction(GLcontext *);
-
-extern void fxDDRenderInit(GLcontext *);
-
extern void fxUpdateDDSpanPointers(GLcontext *);
extern void fxSetupDDSpanPointers(GLcontext *);
@@ -550,18 +564,6 @@ extern void fxDDBlendFunc(GLcontext *, GLenum, GLenum);
extern void fxDDDepthMask(GLcontext *, GLboolean);
extern void fxDDDepthFunc(GLcontext *, GLenum);
-extern void fxDDRegisterVB( struct vertex_buffer *VB );
-extern void fxDDUnregisterVB( struct vertex_buffer *VB );
-extern void fxDDResizeVB( struct vertex_buffer *VB, GLuint size );
-
-extern void fxDDPartialRasterSetup( struct vertex_buffer *VB );
-
-extern void fxDDDoRasterSetup( struct vertex_buffer *VB );
-
-extern void fxDDRegisterPipelineStages( GLcontext *ctx );
-
-extern GLboolean fxDDBuildPrecalcPipeline( GLcontext *ctx );
-
extern void fxDDInitExtensions( GLcontext *ctx );
#define fxTMGetTexInfo(o) ((tfxTexInfo*)((o)->DriverData))
@@ -601,8 +603,6 @@ extern void fxDDReadDepthPixels(GLcontext *ctx, GLuint n,
const GLint x[], const GLint y[],
GLdepth depth[]);
-extern void fxDDFastPath( struct vertex_buffer *VB );
-
extern void fxDDShadeModel(GLcontext *ctx, GLenum mode);
extern void fxDDCullFace(GLcontext *ctx, GLenum mode);
@@ -611,9 +611,10 @@ extern void fxDDFrontFace(GLcontext *ctx, GLenum mode);
extern void fxPrintRenderState( const char *msg, GLuint state );
extern void fxPrintHintState( const char *msg, GLuint state );
-extern void fxDDDoRenderVB( struct vertex_buffer *VB );
-
extern int fxDDInitFxMesaContext( fxMesaContext fxMesa );
+extern void fxDDDestroyFxMesaContext( fxMesaContext fxMesa );
+
+
extern void fxSetScissorValues(GLcontext *ctx);
@@ -622,6 +623,9 @@ extern void fxTMMoveInTM_NoLock(fxMesaContext fxMesa,
GLint where);
extern void fxInitPixelTables(fxMesaContext fxMesa, GLboolean bgrOrder);
+
+/* fxvtxfmt:
+ */
extern void fxDDCheckVtxfmt( GLcontext *ctx );
extern void fx_update_lighting( GLcontext *ctx );
extern void fxDDInitVtxfmt( GLcontext *ctx );
diff --git a/src/mesa/drivers/glide/fxsetup.c b/src/mesa/drivers/glide/fxsetup.c
index f4fde1214ef..5b768848ce2 100644
--- a/src/mesa/drivers/glide/fxsetup.c
+++ b/src/mesa/drivers/glide/fxsetup.c
@@ -71,7 +71,7 @@ static void fxSetupScissor(GLcontext *ctx);
static void fxSetupCull(GLcontext *ctx);
static void fx_print_state_flags( const char *msg, GLuint flags);
/*static GLboolean fxMultipassBlend(struct vertex_buffer *, GLuint);*/
-static GLboolean fxMultipassTexture( struct vertex_buffer *, GLuint );
+static GLboolean fxMultipassTexture( GLcontext *, GLuint );
static void fxTexValidate(GLcontext *ctx, struct gl_texture_object *tObj)
{
@@ -1671,7 +1671,7 @@ static GLboolean fxMultipassBlend(struct vertex_buffer *VB, GLuint pass)
case 2:
/* Reset everything back to normal */
fxMesa->unitsState = fxMesa->restoreUnitsState;
- fxMesa->setupdone &= XXX;
+ fxMesa->setup_gone |= XXX;
fxSetupTextureSingleTMU(ctx, XXX);
fxSetupBlend(ctx);
fxSetupDepthTest(ctx);
@@ -1694,12 +1694,12 @@ static GLboolean fxMultipassBlend(struct vertex_buffer *VB, GLuint pass)
* voodoo 1. In all other cases for both voodoo 1 and 2, we fall back
* to software rendering, satisfying the spec if not the user.
*/
-static GLboolean fxMultipassTexture( struct vertex_buffer *VB, GLuint pass )
+static GLboolean fxMultipassTexture( GLcontext *ctx, GLuint pass )
{
- GLcontext *ctx = VB->ctx;
- fxVertex *v = FX_DRIVER_DATA(VB)->verts;
- fxVertex *last = FX_DRIVER_DATA(VB)->last_vert;
fxMesaContext fxMesa = FX_CONTEXT(ctx);
+ TNLcontext *tnl = TNL_CONTEXT(ctx);
+ fxVertex *v = fxMesa->verts;
+ fxVertex *last = fxMesa->verts + tnl->vb.Count;
switch (pass) {
case 1:
@@ -1742,7 +1742,7 @@ static GLboolean fxMultipassTexture( struct vertex_buffer *VB, GLuint pass )
*/
fxMesa->tmu_source[0] = 0;
fxMesa->unitsState = fxMesa->restoreUnitsState;
- fxMesa->setupdone &= ~SETUP_TMU0;
+ fxMesa->setup_gone |= SETUP_TMU0;
fxSetupTextureSingleTMU( ctx, 0 );
fxSetupBlend( ctx );
fxSetupDepthTest( ctx );
diff --git a/src/mesa/drivers/glide/fxtris.c b/src/mesa/drivers/glide/fxtris.c
new file mode 100644
index 00000000000..7d887133b61
--- /dev/null
+++ b/src/mesa/drivers/glide/fxtris.c
@@ -0,0 +1,568 @@
+
+
+#ifdef HAVE_CONFIG_H
+#include "conf.h"
+#endif
+
+#if defined(FX)
+
+#include "mmath.h"
+#include "swrast/swrast.h"
+#include "swrast_setup/swrast_setup.h"
+
+#include "tnl/t_context.h"
+
+#include "fxdrv.h"
+#include "fxglidew.h"
+
+
+
+
+
+
+
+
+static void
+fx_draw_point( GLcontext *ctx, const fxVertex *v )
+{
+ GLfloat sz = ctx->Point._Size;
+
+ if ( sz <= 1.0 )
+ {
+ grDrawPoint( &(v->v) );
+ }
+ else
+ {
+ GrVertex verts[4];
+
+ sz *= .5;
+
+ verts[0] = v->v;
+ verts[1] = v->v;
+ verts[2] = v->v;
+ verts[3] = v->v;
+
+ verts[0].x = v->v.x - sz;
+ verts[0].y = v->v.y - sz;
+
+ verts[1].x = v->v.x + sz;
+ verts[1].y = v->v.y - sz;
+
+ verts[2].x = v->v.x + sz;
+ verts[2].y = v->v.y + sz;
+
+ verts[3].x = v->v.x - sz;
+ verts[3].y = v->v.y + sz;
+
+ grDrawTriangle( &verts[0], &verts[1], &verts[3] );
+ grDrawTriangle( &verts[1], &verts[2], &verts[3] );
+ }
+}
+
+
+static void
+fx_draw_line( GLcontext *ctx, const fxVertex *v0, const fxVertex *v1 )
+{
+ float width = ctx->Line.Width;
+
+ if ( width <= 1.0 )
+ {
+ grDrawLine( &(v0->v), &(v1->v) );
+ }
+ else
+ {
+ GrVertex verts[4];
+ float dx, dy, ix, iy;
+
+ dx = v0->v.x - v1->v.x;
+ dy = v0->v.y - v1->v.y;
+
+ if (dx * dx > dy * dy) {
+ iy = width * .5;
+ ix = 0;
+ } else {
+ iy = 0;
+ ix = width * .5;
+ }
+
+
+ verts[0] = v0->v;
+ verts[0].x -= ix;
+ verts[0].y -= iy;
+
+ verts[1] = v0->v;
+ verts[1].x += ix;
+ verts[1].y += iy;
+
+ verts[2] = v1->v;
+ verts[2].x += ix;
+ verts[2].y += iy;
+
+ verts[3] = v1->v;
+ verts[3].x -= ix;
+ verts[3].y -= iy;
+
+ grDrawTriangle( &verts[0], &verts[1], &verts[3] );
+ grDrawTriangle( &verts[1], &verts[2], &verts[3] );
+ }
+}
+
+static void
+fx_draw_tri( GLcontext *ctx, const fxVertex *v0, const fxVertex *v1,
+ const fxVertex *v2 )
+{
+ grDrawTriangle( &(v0->v), &(v1->v), &(v2->v) );
+}
+
+
+
+#define FX_COLOR(vert, c) { \
+ GLubyte *col = c; \
+ vert->v.r=UBYTE_COLOR_TO_FLOAT_255_COLOR(col[0]); \
+ vert->v.g=UBYTE_COLOR_TO_FLOAT_255_COLOR(col[1]); \
+ vert->v.b=UBYTE_COLOR_TO_FLOAT_255_COLOR(col[2]); \
+ vert->v.a=UBYTE_COLOR_TO_FLOAT_255_COLOR(col[3]); \
+}
+
+#define FX_COPY_COLOR( dst, src ) { \
+ dst->v.r = src->v.r; \
+ dst->v.g = src->v.g; \
+ dst->v.b = src->v.b; \
+ dst->v.a = src->v.a; \
+}
+
+
+
+#define FX_FLAT_BIT 0x01
+#define FX_OFFSET_BIT 0x02
+#define FX_TWOSIDE_BIT 0x04
+#define FX_UNFILLED_BIT 0x10
+#define FX_FALLBACK_BIT 0x20
+#define FX_MAX_TRIFUNC 0x40
+
+static struct {
+ points_func points;
+ line_func line;
+ triangle_func triangle;
+ quad_func quad;
+} rast_tab[FX_MAX_TRIFUNC];
+
+
+#define IND (0)
+#define TAG(x) x
+#include "fxtritmp.h"
+
+#define IND (FX_FLAT_BIT)
+#define TAG(x) x##_flat
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT)
+#define TAG(x) x##_offset
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FLAT_BIT)
+#define TAG(x) x##_offset_flat
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT)
+#define TAG(x) x##_twoside
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FLAT_BIT)
+#define TAG(x) x##_twoside_flat
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT)
+#define TAG(x) x##_twoside_offset
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FLAT_BIT)
+#define TAG(x) x##_twoside_offset_flat
+#include "fxtritmp.h"
+
+#define IND (FX_FALLBACK_BIT)
+#define TAG(x) x##_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_FLAT_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_flat_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_offset_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_offset_flat_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_twoside_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_twoside_flat_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_twoside_offset_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT)
+#define TAG(x) x##_twoside_offset_flat_fallback
+#include "fxtritmp.h"
+
+#define IND (FX_UNFILLED_BIT)
+#define TAG(x) x##_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_FLAT_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_flat_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_offset_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FLAT_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_offset_flat_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FLAT_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_flat_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_offset_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FLAT_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_offset_flat_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_FLAT_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_flat_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_offset_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_OFFSET_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_offset_flat_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_flat_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_offset_fallback_unfilled
+#include "fxtritmp.h"
+
+#define IND (FX_TWOSIDE_BIT | FX_OFFSET_BIT | FX_FLAT_BIT | FX_FALLBACK_BIT | FX_UNFILLED_BIT)
+#define TAG(x) x##_twoside_offset_flat_fallback_unfilled
+#include "fxtritmp.h"
+
+
+
+
+
+
+void fxDDTrifuncInit( void )
+{
+ init();
+ init_flat();
+ init_offset();
+ init_offset_flat();
+ init_twoside();
+ init_twoside_flat();
+ init_twoside_offset();
+ init_twoside_offset_flat();
+ init_fallback();
+ init_flat_fallback();
+ init_offset_fallback();
+ init_offset_flat_fallback();
+ init_twoside_fallback();
+ init_twoside_flat_fallback();
+ init_twoside_offset_fallback();
+ init_twoside_offset_flat_fallback();
+
+ init_unfilled();
+ init_flat_unfilled();
+ init_offset_unfilled();
+ init_offset_flat_unfilled();
+ init_twoside_unfilled();
+ init_twoside_flat_unfilled();
+ init_twoside_offset_unfilled();
+ init_twoside_offset_flat_unfilled();
+ init_fallback_unfilled();
+ init_flat_fallback_unfilled();
+ init_offset_fallback_unfilled();
+ init_offset_flat_fallback_unfilled();
+ init_twoside_fallback_unfilled();
+ init_twoside_flat_fallback_unfilled();
+ init_twoside_offset_fallback_unfilled();
+ init_twoside_offset_flat_fallback_unfilled();
+}
+
+
+/* Build an SWvertex from a GrVertex. This is workable because in
+ * states where the GrVertex is insufficent (eg seperate-specular),
+ * the driver initiates a total fallback, and builds SWvertices
+ * directly -- it recognizes that it will never have use for the
+ * GrVertex.
+ *
+ * This code is hit only when a mix of accelerated and unaccelerated
+ * primitives are being drawn, and only for the unaccelerated
+ * primitives.
+ */
+static void
+fx_translate_vertex(GLcontext *ctx, const fxVertex *src, SWvertex *dst)
+{
+ fxMesaContext fxMesa = FX_CONTEXT( ctx );
+ GLuint ts0 = fxMesa->tmu_source[0];
+ GLuint ts1 = fxMesa->tmu_source[1];
+ GLfloat w = 1.0 / src->v.oow;
+
+ dst->win[0] = src->v.x;
+ dst->win[1] = src->v.y;
+ dst->win[2] = src->v.ooz;
+ dst->win[3] = src->v.oow;
+
+ dst->color[0] = (GLubyte) src->v.r;
+ dst->color[1] = (GLubyte) src->v.g;
+ dst->color[2] = (GLubyte) src->v.b;
+ dst->color[3] = (GLubyte) src->v.a;
+
+ dst->texcoord[ts0][0] = fxMesa->inv_s0scale * src->v.tmuvtx[0].sow * w;
+ dst->texcoord[ts0][1] = fxMesa->inv_t0scale * src->v.tmuvtx[0].tow * w;
+
+ if (fxMesa->stw_hint_state & GR_STWHINT_W_DIFF_TMU0)
+ dst->texcoord[ts0][3] = src->v.tmuvtx[0].oow * w;
+ else
+ dst->texcoord[ts0][3] = 1.0;
+
+ dst->texcoord[ts1][0] = fxMesa->inv_s1scale * src->v.tmuvtx[1].sow * w;
+ dst->texcoord[ts1][1] = fxMesa->inv_t1scale * src->v.tmuvtx[1].tow * w;
+
+ if (fxMesa->stw_hint_state & GR_STWHINT_W_DIFF_TMU1)
+ dst->texcoord[ts1][3] = src->v.tmuvtx[1].oow * w;
+ else
+ dst->texcoord[ts1][3] = 1.0;
+}
+
+
+static void
+fx_fallback_tri( GLcontext *ctx,
+ const fxVertex *v0, const fxVertex *v1, const fxVertex *v2 )
+{
+ SWvertex v[3];
+ fx_translate_vertex( ctx, v0, &v[0] );
+ fx_translate_vertex( ctx, v1, &v[1] );
+ fx_translate_vertex( ctx, v2, &v[2] );
+ _swrast_Triangle( ctx, &v[0], &v[1], &v[2] );
+}
+
+
+static void
+fx_fallback_line( GLcontext *ctx, const fxVertex *v0, const fxVertex *v1 )
+{
+ SWvertex v[2];
+ fx_translate_vertex( ctx, v0, &v[0] );
+ fx_translate_vertex( ctx, v1, &v[1] );
+ _swrast_Line( ctx, &v[0], &v[1] );
+}
+
+
+static void
+fx_fallback_point( GLcontext *ctx, const fxVertex *v0 )
+{
+ SWvertex v[1];
+ fx_translate_vertex( ctx, v0, &v[0] );
+ _swrast_Point( ctx, &v[0] );
+}
+
+
+/* System to turn culling off for rasterized lines and points, and
+ * back on for rasterized triangles.
+ */
+static void
+fx_cull_draw_tri( GLcontext *ctx,
+ const fxVertex *v0, const fxVertex *v1, const fxVertex *v2 )
+{
+ fxMesaContext fxMesa = FX_CONTEXT( ctx );
+
+ FX_grCullMode(fxMesa->cullMode);
+
+ fxMesa->draw_line = fxMesa->initial_line;
+ fxMesa->draw_point = fxMesa->initial_point;
+ fxMesa->draw_tri = fxMesa->subsequent_tri;
+
+ fxMesa->draw_tri( ctx, v0, v1, v2 );
+}
+
+
+static void
+fx_cull_draw_line( GLcontext *ctx, const fxVertex *v0, const fxVertex *v1 )
+{
+ fxMesaContext fxMesa = FX_CONTEXT( ctx );
+
+ FX_grCullMode( GR_CULL_DISABLE );
+
+ fxMesa->draw_point = fxMesa->initial_point;
+ fxMesa->draw_tri = fxMesa->initial_tri;
+ fxMesa->draw_line = fxMesa->subsequent_line;
+
+ fxMesa->draw_line( ctx, v0, v1 );
+}
+
+
+static void
+fx_cull_draw_point( GLcontext *ctx, const fxVertex *v0 )
+{
+ fxMesaContext fxMesa = FX_CONTEXT( ctx );
+
+ FX_grCullMode(GR_CULL_DISABLE);
+
+ fxMesa->draw_line = fxMesa->initial_line;
+ fxMesa->draw_tri = fxMesa->initial_tri;
+ fxMesa->draw_point = fxMesa->subsequent_point;
+
+ fxMesa->draw_point( ctx, v0 );
+}
+
+
+static void
+fx_null_tri( GLcontext *ctx,
+ const fxVertex *v0, const fxVertex *v1, const fxVertex *v2 )
+{
+ (void) v0;
+ (void) v1;
+ (void) v2;
+}
+
+
+
+#define POINT_FALLBACK (DD_POINT_SMOOTH )
+#define LINE_FALLBACK (DD_LINE_STIPPLE)
+#define TRI_FALLBACK (DD_TRI_SMOOTH | DD_TRI_STIPPLE )
+#define ANY_FALLBACK (POINT_FALLBACK | LINE_FALLBACK | TRI_FALLBACK)
+
+
+#define ANY_RENDER_FLAGS (DD_FLATSHADE | \
+ DD_TRI_LIGHT_TWOSIDE | \
+ DD_TRI_OFFSET | \
+ DD_TRI_UNFILLED)
+
+
+
+/* Setup the Point, Line, Triangle and Quad functions based on the
+ * current rendering state. Wherever possible, use the hardware to
+ * render the primitive. Otherwise, fallback to software rendering.
+ */
+void fxDDChooseRenderState( GLcontext *ctx )
+{
+ fxMesaContext fxMesa = FX_CONTEXT( ctx );
+ GLuint flags = ctx->_TriangleCaps;
+ GLuint index = 0;
+
+ if ( !fxMesa->is_in_hardware ) {
+ /* Build software vertices directly. No acceleration is
+ * possible. GrVertices may be insufficient for this mode.
+ */
+ ctx->Driver.PointsFunc = _swsetup_Points;
+ ctx->Driver.LineFunc = _swsetup_Line;
+ ctx->Driver.TriangleFunc = _swsetup_Triangle;
+ ctx->Driver.QuadFunc = _swsetup_Quad;
+
+ fxMesa->render_index = FX_FALLBACK_BIT;
+ return;
+ }
+
+ if ( flags & ANY_RENDER_FLAGS ) {
+ if ( flags & DD_FLATSHADE ) index |= FX_FLAT_BIT;
+ if ( flags & DD_TRI_LIGHT_TWOSIDE ) index |= FX_TWOSIDE_BIT;
+ if ( flags & DD_TRI_OFFSET ) index |= FX_OFFSET_BIT;
+ if ( flags & DD_TRI_UNFILLED ) index |= FX_UNFILLED_BIT;
+ }
+
+ if ( flags & (ANY_FALLBACK|
+ DD_LINE_WIDTH|
+ DD_POINT_SIZE|
+ DD_TRI_CULL_FRONT_BACK) ) {
+
+ /* Hook in fallbacks for specific primitives.
+ *
+ * Set up a system to turn culling on/off for wide points and
+ * lines. Alternately: figure out what tris to send so that
+ * culling isn't a problem.
+ *
+ * This replaces the ReducedPrimitiveChange mechanism.
+ */
+ index |= FX_FALLBACK_BIT;
+ fxMesa->initial_point = fx_cull_draw_point;
+ fxMesa->initial_line = fx_cull_draw_line;
+ fxMesa->initial_tri = fx_cull_draw_tri;
+
+ fxMesa->subsequent_point = fx_draw_point;
+ fxMesa->subsequent_line = fx_draw_line;
+ fxMesa->subsequent_tri = fx_draw_tri;
+
+ if ( flags & POINT_FALLBACK )
+ fxMesa->initial_point = fx_fallback_point;
+
+ if ( flags & LINE_FALLBACK )
+ fxMesa->initial_line = fx_fallback_line;
+
+ if ((flags & DD_LINE_SMOOTH) && ctx->Line.Width != 1.0)
+ fxMesa->initial_line = fx_fallback_line;
+
+ if ( flags & TRI_FALLBACK )
+ fxMesa->initial_tri = fx_fallback_tri;
+
+ if ( flags & DD_TRI_CULL_FRONT_BACK )
+ fxMesa->initial_tri = fx_null_tri;
+
+ fxMesa->draw_point = fxMesa->initial_point;
+ fxMesa->draw_line = fxMesa->initial_line;
+ fxMesa->draw_tri = fxMesa->initial_tri;
+ }
+ else if (fxMesa->render_index & FX_FALLBACK_BIT) {
+ FX_grCullMode(fxMesa->cullMode);
+ }
+
+ ctx->Driver.PointsFunc = rast_tab[index].points;
+ ctx->Driver.LineFunc = rast_tab[index].line;
+ ctx->Driver.TriangleFunc = rast_tab[index].triangle;
+ ctx->Driver.QuadFunc = rast_tab[index].quad;
+ fxMesa->render_index = index;
+}
+
+
+#else
+
+
+/*
+ * Need this to provide at least one external definition.
+ */
+
+extern int gl_fx_dummy_function_trifuncs(void);
+int gl_fx_dummy_function_trifuncs(void)
+{
+ return 0;
+}
+
+#endif /* FX */
diff --git a/src/mesa/drivers/glide/fxvb.c b/src/mesa/drivers/glide/fxvb.c
new file mode 100644
index 00000000000..22128e61f6b
--- /dev/null
+++ b/src/mesa/drivers/glide/fxvb.c
@@ -0,0 +1,403 @@
+
+/*
+ * Mesa 3-D graphics library
+ * Version: 3.3
+ *
+ * Copyright (C) 1999-2000 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"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included
+ * in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * 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.
+ *
+ * Author:
+ * Keith Whitwell <[email protected]>
+ */
+
+
+/* fxvsetup.c - 3Dfx VooDoo vertices setup functions */
+
+
+#ifdef HAVE_CONFIG_H
+#include "conf.h"
+#endif
+
+#if defined(FX)
+
+#include "fxdrv.h"
+#include "mmath.h"
+#include "swrast_setup/swrast_setup.h"
+
+#include "tnl/t_context.h"
+#include "tnl/t_pipeline.h"
+
+
+void fxPrintSetupFlags( const char *msg, GLuint flags )
+{
+ fprintf(stderr, "%s: %d %s%s%s%s%s\n",
+ msg,
+ flags,
+ (flags & SETUP_XYZW) ? " xyzw," : "",
+ (flags & SETUP_SNAP) ? " snap," : "",
+ (flags & SETUP_RGBA) ? " rgba," : "",
+ (flags & SETUP_TMU0) ? " tmu0," : "",
+ (flags & SETUP_TMU1) ? " tmu1," : "");
+}
+
+static void project_texcoords( fxVertex *v,
+ struct vertex_buffer *VB,
+ GLuint tmu_nr, GLuint tc_nr,
+ GLuint start, GLuint count )
+{
+ GrTmuVertex *tmu = &(v->v.tmuvtx[tmu_nr]);
+ GLvector4f *vec = VB->TexCoordPtr[tc_nr];
+
+ GLuint i;
+ GLuint stride = vec->stride;
+ GLfloat *data = VEC_ELT(vec, GLfloat, start);
+
+ for (i = start ; i < count ; i++, STRIDE_F(data, stride), v++) {
+ tmu->oow = v->v.oow * data[3];
+ tmu = (GrTmuVertex *)((char *)tmu + sizeof(fxVertex));
+ }
+}
+
+
+static void copy_w( fxVertex *v,
+ struct vertex_buffer *VB,
+ GLuint tmu_nr,
+ GLuint start, GLuint count )
+{
+ GrTmuVertex *tmu = &(v->v.tmuvtx[tmu_nr]);
+ GLuint i;
+
+ for (i = start ; i < count ; i++, v++) {
+ tmu->oow = v->v.oow;
+ tmu = (GrTmuVertex *)((char *)tmu + sizeof(fxVertex));
+ }
+}
+
+/* need to compute W values for fogging purposes
+ */
+static void fx_fake_fog_w( GLcontext *ctx,
+ fxVertex *verts,
+ struct vertex_buffer *VB,
+ GLuint start, GLuint end )
+{
+ const GLfloat m10 = ctx->ProjectionMatrix.m[10];
+ const GLfloat m14 = ctx->ProjectionMatrix.m[14];
+ GLfloat (*clip)[4] = VB->ClipPtr->data;
+ GLubyte *clipmask = VB->ClipMask;
+ GLuint i;
+
+ for ( i = start ; i < end ; i++) {
+ if (clipmask[i] == 0) {
+ verts[i].v.oow = - m10 / (clip[i][2] - m14); /* -1/zEye */
+ }
+ }
+}
+
+
+
+static tfxSetupFunc setupfuncs[MAX_SETUP];
+
+
+#define IND (SETUP_XYZW)
+#define INPUTS (VERT_CLIP)
+#define NAME fxsetupXYZW
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA)
+#define NAME fxsetupXYZWRGBA
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU0)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZWT0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU1)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZWT1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU1|SETUP_TMU0)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZWT0T1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZWRGBAT0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU1|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZWRGBAT1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_TMU1|SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZWRGBAT0T1
+#include "fxvbtmp.h"
+
+
+#define IND (SETUP_XYZW|SETUP_SNAP)
+#define INPUTS (VERT_CLIP)
+#define NAME fxsetupXYZW_SNAP
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA)
+#define NAME fxsetupXYZW_SNAP_RGBA
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU0)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_T0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU1)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_T1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_TMU0)
+#define INPUTS (VERT_CLIP|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_T0T1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_RGBAT0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_RGBAT1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_CLIP|VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupXYZW_SNAP_RGBAT0T1
+#include "fxvbtmp.h"
+
+
+
+#define IND (SETUP_RGBA)
+#define INPUTS (VERT_RGBA)
+#define NAME fxsetupRGBA
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU0)
+#define INPUTS (VERT_TEX_ANY)
+#define NAME fxsetupT0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU1)
+#define INPUTS (VERT_TEX_ANY)
+#define NAME fxsetupT1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU1|SETUP_TMU0)
+#define INPUTS (VERT_TEX_ANY)
+#define NAME fxsetupT0T1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupRGBAT0
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU1|SETUP_RGBA)
+#define INPUTS (VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupRGBAT1
+#include "fxvbtmp.h"
+
+#define IND (SETUP_TMU1|SETUP_TMU0|SETUP_RGBA)
+#define INPUTS (VERT_RGBA|VERT_TEX_ANY)
+#define NAME fxsetupRGBAT0T1
+#include "fxvbtmp.h"
+
+
+static void
+fxsetup_invalid( GLcontext *ctx, GLuint start, GLuint end, GLuint newinputs )
+{
+ fprintf(stderr, "fxMesa: invalid setup function\n");
+ (void) (ctx && start && end && newinputs);
+}
+
+
+void fxDDSetupInit( void )
+{
+ GLuint i;
+ for (i = 0 ; i < Elements(setupfuncs) ; i++)
+ setupfuncs[i] = fxsetup_invalid;
+
+ setupfuncs[SETUP_XYZW] = fxsetupXYZW;
+ setupfuncs[SETUP_XYZW|SETUP_RGBA] = fxsetupXYZWRGBA;
+ setupfuncs[SETUP_XYZW|SETUP_TMU0] = fxsetupXYZWT0;
+ setupfuncs[SETUP_XYZW|SETUP_TMU1] = fxsetupXYZWT1;
+ setupfuncs[SETUP_XYZW|SETUP_TMU0|SETUP_RGBA] = fxsetupXYZWRGBAT0;
+ setupfuncs[SETUP_XYZW|SETUP_TMU1|SETUP_RGBA] = fxsetupXYZWRGBAT1;
+ setupfuncs[SETUP_XYZW|SETUP_TMU1|SETUP_TMU0] = fxsetupXYZWT0T1;
+ setupfuncs[SETUP_XYZW|SETUP_TMU1|SETUP_TMU0|SETUP_RGBA] =
+ fxsetupXYZWRGBAT0T1;
+
+ setupfuncs[SETUP_XYZW|SETUP_SNAP] = fxsetupXYZW_SNAP;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_RGBA] = fxsetupXYZW_SNAP_RGBA;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU0] = fxsetupXYZW_SNAP_T0;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU1] = fxsetupXYZW_SNAP_T1;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU0|SETUP_RGBA] =
+ fxsetupXYZW_SNAP_RGBAT0;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_RGBA] =
+ fxsetupXYZW_SNAP_RGBAT1;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_TMU0] =
+ fxsetupXYZW_SNAP_T0T1;
+ setupfuncs[SETUP_XYZW|SETUP_SNAP|SETUP_TMU1|SETUP_TMU0|SETUP_RGBA] =
+ fxsetupXYZW_SNAP_RGBAT0T1;
+
+ setupfuncs[SETUP_RGBA] = fxsetupRGBA;
+ setupfuncs[SETUP_TMU0] = fxsetupT0;
+ setupfuncs[SETUP_TMU1] = fxsetupT1;
+ setupfuncs[SETUP_TMU1|SETUP_TMU0] = fxsetupT0T1;
+ setupfuncs[SETUP_TMU0|SETUP_RGBA] = fxsetupRGBAT0;
+ setupfuncs[SETUP_TMU1|SETUP_RGBA] = fxsetupRGBAT1;
+ setupfuncs[SETUP_TMU1|SETUP_TMU0|SETUP_RGBA] = fxsetupRGBAT0T1;
+}
+
+
+
+void fx_validate_BuildProjVerts(GLcontext *ctx, GLuint start, GLuint count,
+ GLuint newinputs )
+{
+ GLuint setupindex = SETUP_XYZW;
+ fxMesaContext fxMesa = (fxMesaContext)ctx->DriverCtx;
+
+ if (!fxMesa->is_in_hardware)
+ ctx->Driver.BuildProjectedVertices = _swsetup_BuildProjectedVertices;
+ else {
+ fxMesa->tmu_source[0] = 0;
+ fxMesa->tmu_source[1] = 1;
+ fxMesa->tex_dest[0] = SETUP_TMU0;
+ fxMesa->tex_dest[1] = SETUP_TMU1;
+
+ /* For flat and two-side-lit triangles, colors will always be added
+ * to vertices in the triangle functions. Vertices will *always*
+ * have rbga values, but only sometimes will they come from here.
+ */
+ if ((ctx->_TriangleCaps & (DD_FLATSHADE|DD_TRI_LIGHT_TWOSIDE)) == 0)
+ setupindex |= SETUP_RGBA;
+
+ if (ctx->Texture._ReallyEnabled & TEXTURE0_2D)
+ setupindex |= SETUP_TMU0;
+
+ if (ctx->Texture._ReallyEnabled & TEXTURE1_2D) {
+ if ((ctx->Texture._ReallyEnabled & TEXTURE0_2D) == 0) {
+ fxMesa->tmu_source[0] = 1; fxMesa->tex_dest[0] = SETUP_TMU1;
+ fxMesa->tmu_source[1] = 0; fxMesa->tex_dest[1] = SETUP_TMU0;
+ setupindex |= SETUP_TMU0;
+ } else {
+ setupindex |= SETUP_TMU1;
+ }
+ }
+
+ if (MESA_VERBOSE & (VERBOSE_DRIVER|VERBOSE_PIPELINE|VERBOSE_STATE))
+ fxPrintSetupFlags("fxmesa: vertex setup function", setupindex);
+
+ fxMesa->setupindex = setupindex;
+ ctx->Driver.BuildProjectedVertices = fx_BuildProjVerts;
+ }
+ ctx->Driver.BuildProjectedVertices( ctx, start, count, newinputs );
+}
+
+
+void fx_BuildProjVerts( GLcontext *ctx, GLuint start, GLuint count,
+ GLuint newinputs )
+{
+ fxMesaContext fxMesa = FX_CONTEXT(ctx);
+ struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
+ GLuint ind = fxMesa->setup_gone;
+
+ fxMesa->setup_gone = 0;
+
+ if (newinputs & VERT_CLIP)
+ ind = fxMesa->setupindex; /* clipmask has changed - invalidated all */
+ else {
+ if (newinputs & VERT_TEX0)
+ ind |= fxMesa->tex_dest[0];
+
+ if (newinputs & VERT_TEX1)
+ ind |= fxMesa->tex_dest[1];
+
+ if (newinputs & VERT_RGBA)
+ ind |= SETUP_RGBA;
+
+ ind &= fxMesa->setupindex;
+ }
+
+ if (0) {
+ _tnl_print_vert_flags("newinputs", newinputs);
+ fxPrintSetupFlags("setup function", ind);
+ }
+
+ if (fxMesa->new_state)
+ fxSetupFXUnits( ctx );
+
+ if (VB->importable_data)
+ VB->import_data( ctx, VB->importable_data & newinputs,
+ (VB->ClipOrMask
+ ? VEC_NOT_WRITEABLE|VEC_BAD_STRIDE
+ : VEC_BAD_STRIDE));
+
+ setupfuncs[ind]( ctx, start, count, newinputs );
+}
+
+
+void fxAllocVB( GLcontext *ctx )
+{
+ fxMesaContext fxMesa = FX_CONTEXT(ctx);
+ TNLcontext *tnl = TNL_CONTEXT(ctx);
+ fxMesa->verts = ALIGN_MALLOC( tnl->vb.Size * sizeof(fxMesa->verts[0]), 32 );
+}
+
+void fxFreeVB( GLcontext *ctx )
+{
+ fxMesaContext fxMesa = FX_CONTEXT(ctx);
+ if (fxMesa->verts)
+ ALIGN_FREE( fxMesa->verts );
+ fxMesa->verts = 0;
+}
+
+
+#else
+
+
+/*
+ * Need this to provide at least one external definition.
+ */
+
+extern int gl_fx_dummy_function_vsetup(void);
+int gl_fx_dummy_function_vsetup(void)
+{
+ return 0;
+}
+
+#endif /* FX */
diff --git a/src/mesa/drivers/glide/fxvbtmp.h b/src/mesa/drivers/glide/fxvbtmp.h
new file mode 100644
index 00000000000..5f3a293650a
--- /dev/null
+++ b/src/mesa/drivers/glide/fxvbtmp.h
@@ -0,0 +1,143 @@
+
+/*
+ * Mesa 3-D graphics library
+ * Version: 3.3
+ *
+ * Copyright (C) 1999-2000 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"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included
+ * in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * 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.
+ *
+ * Author:
+ * Keith Whitwell <[email protected]>
+ */
+
+
+static void NAME(GLcontext *ctx, GLuint start, GLuint end, GLuint newinputs)
+{
+ fxMesaContext fxMesa = (fxMesaContext)ctx->DriverCtx;
+ fxVertex *verts = fxMesa->verts;
+ struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
+ GLuint tmu0_source = fxMesa->tmu_source[0];
+ GLuint tmu1_source = fxMesa->tmu_source[1];
+ GLfloat (*tmu0_data)[4];
+ GLfloat (*tmu1_data)[4];
+ GLubyte (*color)[4];
+ GLfloat (*proj)[4] = VB->ProjectedClipPtr->data;
+ fxVertex *v = &verts[start];
+ GLfloat sscale0 = fxMesa->s0scale;
+ GLfloat tscale0 = fxMesa->t0scale;
+ GLfloat sscale1 = fxMesa->s1scale;
+ GLfloat tscale1 = fxMesa->t1scale;
+ GLubyte *clipmask = VB->ClipMask;
+ GLuint i;
+ const GLfloat * const s = ctx->Viewport._WindowMap.m;
+
+ if (IND & SETUP_TMU0)
+ tmu0_data = VB->TexCoordPtr[tmu0_source]->data;
+
+ if (IND & SETUP_TMU1)
+ tmu1_data = VB->TexCoordPtr[tmu1_source]->data;
+
+ if (IND & SETUP_RGBA)
+ color = VB->ColorPtr[0]->data;
+
+ for (i = start ; i < end ; i++, v++) {
+ if (!clipmask[i]) {
+ if (IND & SETUP_XYZW) {
+ v->v.x = s[0] * proj[i][0] + s[12];
+ v->v.y = s[5] * proj[i][1] + s[13];
+ v->v.ooz = s[10] * proj[i][2] + s[14];
+ v->v.oow = proj[i][3];
+
+ if (IND & SETUP_SNAP) {
+#if defined(USE_IEEE)
+ const float snapper = (3L<<18);
+ v->v.x += snapper;
+ v->v.x -= snapper;
+ v->v.y += snapper;
+ v->v.y -= snapper;
+#else
+ v->v.x = ((int)(v->v.x*16.0f)) * (1.0f/16.0f);
+ v->v.y = ((int)(v->v.y*16.0f)) * (1.0f/16.0f);
+#endif
+ }
+ }
+ if (IND & SETUP_RGBA) {
+ UBYTE_COLOR_TO_FLOAT_255_COLOR2(v->v.r, color[i][0]);
+ UBYTE_COLOR_TO_FLOAT_255_COLOR2(v->v.g, color[i][1]);
+ UBYTE_COLOR_TO_FLOAT_255_COLOR2(v->v.b, color[i][2]);
+ UBYTE_COLOR_TO_FLOAT_255_COLOR2(v->v.a, color[i][3]);
+ }
+ if (IND & SETUP_TMU0) {
+ v->v.tmuvtx[0].sow = sscale0*tmu0_data[i][0]*v->v.oow;
+ v->v.tmuvtx[0].tow = tscale0*tmu0_data[i][1]*v->v.oow;
+ }
+ if (IND & SETUP_TMU1) {
+ v->v.tmuvtx[1].sow = sscale1*tmu1_data[i][0]*v->v.oow;
+ v->v.tmuvtx[1].tow = tscale1*tmu1_data[i][1]*v->v.oow;
+ }
+ }
+ }
+
+ if ((IND & SETUP_XYZW) &&
+ ctx->ProjectionMatrix.m[15] != 0.0F &&
+ ctx->Fog.Enabled)
+ {
+ fx_fake_fog_w( ctx, v, VB, start, end );
+ }
+
+ /* Check for and enable projective texturing in each texture unit.
+ */
+ if (IND & (SETUP_TMU0|SETUP_TMU1)) {
+ GLuint tmu0_sz = 2;
+ GLuint tmu1_sz = 2;
+ GLuint hs = fxMesa->stw_hint_state & ~(GR_STWHINT_W_DIFF_TMU0 |
+ GR_STWHINT_W_DIFF_TMU1);
+
+ if (VB->TexCoordPtr[tmu0_source])
+ tmu0_sz = VB->TexCoordPtr[tmu0_source]->size;
+
+ if (VB->TexCoordPtr[tmu1_source])
+ tmu1_sz = VB->TexCoordPtr[tmu1_source]->size;
+
+ if (tmu0_sz == 4) {
+ project_texcoords( v, VB, 0, tmu0_source, start, end );
+ if (tmu1_sz == 4)
+ project_texcoords( v, VB, 1, tmu1_source, start, end );
+ else
+ copy_w( v, VB, 1, start, end );
+ hs |= (GR_STWHINT_W_DIFF_TMU0|GR_STWHINT_W_DIFF_TMU1);
+ }
+ else if (tmu1_sz == 4) {
+ project_texcoords( v, VB, 1, tmu1_source, start, end );
+ hs |= GR_STWHINT_W_DIFF_TMU1;
+ }
+
+ if (hs != fxMesa->stw_hint_state) {
+ fxMesa->stw_hint_state = hs;
+ FX_grHints(GR_HINT_STWHINT, hs);
+ }
+ }
+}
+
+
+
+
+#undef IND
+#undef NAME
+#undef INPUTS