diff options
Diffstat (limited to 'src/mesa/swrast')
-rw-r--r-- | src/mesa/swrast/s_arbshader.c | 208 | ||||
-rw-r--r-- | src/mesa/swrast/s_context.h | 7 | ||||
-rw-r--r-- | src/mesa/swrast/s_span.c | 70 | ||||
-rw-r--r-- | src/mesa/swrast/s_tritemp.h | 66 | ||||
-rw-r--r-- | src/mesa/swrast/swrast.h | 3 |
5 files changed, 237 insertions, 117 deletions
diff --git a/src/mesa/swrast/s_arbshader.c b/src/mesa/swrast/s_arbshader.c index ba146dd1bb9..9cd96c5a366 100644 --- a/src/mesa/swrast/s_arbshader.c +++ b/src/mesa/swrast/s_arbshader.c @@ -1,99 +1,109 @@ -/*
- * Mesa 3-D graphics library
- * Version: 6.5
- *
- * Copyright (C) 2006 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.
- *
- * Authors:
- * Michal Krol
- */
-
-#include "glheader.h"
-#include "context.h"
-#include "colormac.h"
-#include "s_arbshader.h"
-#include "s_context.h"
-#include "shaderobjects.h"
-#include "shaderobjects_3dlabs.h"
-#include "slang_utility.h"
-#include "slang_link.h"
-
-void _swrast_exec_arbshader (GLcontext *ctx, struct sw_span *span)
-{
- struct gl2_program_intf **pro;
- GLuint i;
-
- if (!ctx->ShaderObjects._FragmentShaderPresent)
- return;
- pro = ctx->ShaderObjects.CurrentProgram;
- if (!ctx->ShaderObjects._VertexShaderPresent)
- (**pro).UpdateFixedUniforms (pro);
-
- for (i = span->start; i < span->end; i++)
- {
- /* only run shader on active fragments */
- if (span->array->mask[i]) {
- GLfloat vec[4];
- GLuint j;
- GLboolean discard;
-
- vec[0] = (GLfloat) span->x + i;
- vec[1] = (GLfloat) span->y;
- vec[2] = (GLfloat) span->array->z[i] / ctx->DrawBuffer->_DepthMaxF;
- vec[3] = span->w + span->dwdx * i;
- (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_FRAGCOORD, vec, 0,
- 4 * sizeof (GLfloat), GL_TRUE);
- vec[0] = CHAN_TO_FLOAT(span->array->rgba[i][RCOMP]);
- vec[1] = CHAN_TO_FLOAT(span->array->rgba[i][GCOMP]);
- vec[2] = CHAN_TO_FLOAT(span->array->rgba[i][BCOMP]);
- vec[3] = CHAN_TO_FLOAT(span->array->rgba[i][ACOMP]);
- (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_COLOR, vec, 0, 4 * sizeof (GLfloat),
- GL_TRUE);
- for (j = 0; j < ctx->Const.MaxTextureCoordUnits; j++)
- {
- vec[0] = span->array->texcoords[j][i][0];
- vec[1] = span->array->texcoords[j][i][1];
- vec[2] = span->array->texcoords[j][i][2];
- vec[3] = span->array->texcoords[j][i][3];
- (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_TEXCOORD, vec, j,
- 4 * sizeof (GLfloat), GL_TRUE);
- }
-
- _slang_exec_fragment_shader (pro);
-
- _slang_fetch_discard (pro, &discard);
- if (discard)
- {
- span->array->mask[i] = GL_FALSE;
- span->writeAll = GL_FALSE;
- }
- else
- {
- (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_FRAGCOLOR, vec, 0,
- 4 * sizeof (GLfloat), GL_FALSE);
- UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][RCOMP], vec[0]);
- UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][GCOMP], vec[1]);
- UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][BCOMP], vec[2]);
- UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][ACOMP], vec[3]);
- }
- }
- }
-}
-
+/* + * Mesa 3-D graphics library + * Version: 6.5 + * + * Copyright (C) 2006 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. + * + * Authors: + * Michal Krol + */ + +#include "glheader.h" +#include "context.h" +#include "colormac.h" +#include "s_arbshader.h" +#include "s_context.h" +#include "shaderobjects.h" +#include "shaderobjects_3dlabs.h" +#include "slang_utility.h" +#include "slang_link.h" + +void _swrast_exec_arbshader (GLcontext *ctx, struct sw_span *span) +{ + struct gl2_program_intf **pro; + GLuint i; + + if (!ctx->ShaderObjects._FragmentShaderPresent) + return; + pro = ctx->ShaderObjects.CurrentProgram; + if (!ctx->ShaderObjects._VertexShaderPresent) + (**pro).UpdateFixedUniforms (pro); + + for (i = span->start; i < span->end; i++) + { + /* only run shader on active fragments */ + if (span->array->mask[i]) { + GLfloat vec[4]; + GLuint j; + GLboolean discard; + + vec[0] = (GLfloat) span->x + i; + vec[1] = (GLfloat) span->y; + vec[2] = (GLfloat) span->array->z[i] / ctx->DrawBuffer->_DepthMaxF; + vec[3] = span->w + span->dwdx * i; + (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_FRAGCOORD, vec, 0, + 4 * sizeof (GLfloat), GL_TRUE); + vec[0] = CHAN_TO_FLOAT(span->array->rgba[i][RCOMP]); + vec[1] = CHAN_TO_FLOAT(span->array->rgba[i][GCOMP]); + vec[2] = CHAN_TO_FLOAT(span->array->rgba[i][BCOMP]); + vec[3] = CHAN_TO_FLOAT(span->array->rgba[i][ACOMP]); + (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_COLOR, vec, 0, 4 * sizeof (GLfloat), + GL_TRUE); + for (j = 0; j < ctx->Const.MaxTextureCoordUnits; j++) + { + vec[0] = span->array->texcoords[j][i][0]; + vec[1] = span->array->texcoords[j][i][1]; + vec[2] = span->array->texcoords[j][i][2]; + vec[3] = span->array->texcoords[j][i][3]; + (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_TEXCOORD, vec, j, + 4 * sizeof (GLfloat), GL_TRUE); + } + for (j = 0; j < MAX_VARYING_VECTORS; j++) + { + GLuint k; + + for (k = 0; k < VARYINGS_PER_VECTOR; k++) + { + (**pro).UpdateVarying (pro, j * VARYINGS_PER_VECTOR + k, + &span->array->varying[i][j][k], GL_FALSE); + } + } + + _slang_exec_fragment_shader (pro); + + _slang_fetch_discard (pro, &discard); + if (discard) + { + span->array->mask[i] = GL_FALSE; + span->writeAll = GL_FALSE; + } + else + { + (**pro).UpdateFixedVarying (pro, SLANG_FRAGMENT_FIXED_FRAGCOLOR, vec, 0, + 4 * sizeof (GLfloat), GL_FALSE); + UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][RCOMP], vec[0]); + UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][GCOMP], vec[1]); + UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][BCOMP], vec[2]); + UNCLAMPED_FLOAT_TO_CHAN(span->array->rgba[i][ACOMP], vec[3]); + } + } + } +} + diff --git a/src/mesa/swrast/s_context.h b/src/mesa/swrast/s_context.h index 5d9a35043be..3c5a4c32228 100644 --- a/src/mesa/swrast/s_context.h +++ b/src/mesa/swrast/s_context.h @@ -2,7 +2,7 @@ * Mesa 3-D graphics library * Version: 6.5 * - * Copyright (C) 1999-2005 Brian Paul All Rights Reserved. + * Copyright (C) 1999-2006 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"), @@ -66,6 +66,7 @@ #define SPAN_FLAT 0x400 /**< flat shading? */ #define SPAN_XY 0x800 #define SPAN_MASK 0x1000 +#define SPAN_VARYING 0x2000 /*@}*/ @@ -90,6 +91,7 @@ struct span_arrays { GLfloat texcoords[MAX_TEXTURE_COORD_UNITS][MAX_WIDTH][4]; GLfloat lambda[MAX_TEXTURE_COORD_UNITS][MAX_WIDTH]; GLfloat coverage[MAX_WIDTH]; + GLfloat varying[MAX_WIDTH][MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; /** This mask indicates which fragments are alive or culled */ GLubyte mask[MAX_WIDTH]; @@ -167,6 +169,9 @@ struct sw_span { GLfloat texStepX[MAX_TEXTURE_COORD_UNITS][4]; GLfloat texStepY[MAX_TEXTURE_COORD_UNITS][4]; GLfixed intTex[2], intTexStep[2]; /* s, t only */ + GLfloat var[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; + GLfloat varStepX[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; + GLfloat varStepY[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; /* partial derivatives wrt X and Y. */ GLfloat dzdx, dzdy; diff --git a/src/mesa/swrast/s_span.c b/src/mesa/swrast/s_span.c index 02901a7ed94..11457723b09 100644 --- a/src/mesa/swrast/s_span.c +++ b/src/mesa/swrast/s_span.c @@ -37,7 +37,7 @@ #include "imports.h" #include "s_atifragshader.h" -#include "s_alpha.h"
+#include "s_alpha.h" #include "s_arbshader.h" #include "s_blend.h" #include "s_context.h" @@ -434,7 +434,8 @@ interpolate_texcoords(GLcontext *ctx, struct sw_span *span) GLfloat r = span->tex[u][2]; GLfloat q = span->tex[u][3]; GLuint i; - if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled) { + if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled || + ctx->ShaderObjects._FragmentShaderPresent) { /* do perspective correction but don't divide s, t, r by q */ const GLfloat dwdx = span->dwdx; GLfloat w = span->w; @@ -485,7 +486,8 @@ interpolate_texcoords(GLcontext *ctx, struct sw_span *span) GLfloat r = span->tex[u][2]; GLfloat q = span->tex[u][3]; GLuint i; - if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled) { + if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled || + ctx->ShaderObjects._FragmentShaderPresent) { /* do perspective correction but don't divide s, t, r by q */ const GLfloat dwdx = span->dwdx; GLfloat w = span->w; @@ -568,7 +570,8 @@ interpolate_texcoords(GLcontext *ctx, struct sw_span *span) GLfloat r = span->tex[0][2]; GLfloat q = span->tex[0][3]; GLuint i; - if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled) { + if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled || + ctx->ShaderObjects._FragmentShaderPresent) { /* do perspective correction but don't divide s, t, r by q */ const GLfloat dwdx = span->dwdx; GLfloat w = span->w; @@ -619,7 +622,8 @@ interpolate_texcoords(GLcontext *ctx, struct sw_span *span) GLfloat r = span->tex[0][2]; GLfloat q = span->tex[0][3]; GLuint i; - if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled) { + if (ctx->FragmentProgram._Active || ctx->ATIFragmentShader._Enabled || + ctx->ShaderObjects._FragmentShaderPresent) { /* do perspective correction but don't divide s, t, r by q */ const GLfloat dwdx = span->dwdx; GLfloat w = span->w; @@ -668,6 +672,38 @@ interpolate_texcoords(GLcontext *ctx, struct sw_span *span) /** + * Fill in the span.varying array from the interpolation values. + */ +static void +interpolate_varying(GLcontext *ctx, struct sw_span *span) +{ + GLuint i, j; + + ASSERT(span->interpMask & SPAN_VARYING); + ASSERT(!(span->arrayMask & SPAN_VARYING)); + + span->arrayMask |= SPAN_VARYING; + + for (i = 0; i < MAX_VARYING_VECTORS; i++) { + for (j = 0; j < VARYINGS_PER_VECTOR; j++) { + const GLfloat dvdx = span->varStepX[i][j]; + GLfloat v = span->var[i][j]; + const GLfloat dwdx = span->dwdx; + GLfloat w = span->w; + GLuint k; + + for (k = 0; k < span->end; k++) { + GLfloat invW = 1.0f / w; + span->array->varying[k][i][j] = v * invW; + v += dvdx; + w += dwdx; + } + } + } +} + + +/** * Apply the current polygon stipple pattern to a span of pixels. */ static void @@ -1139,6 +1175,10 @@ _swrast_write_rgba_span( GLcontext *ctx, struct sw_span *span) interpolate_texcoords(ctx, span); } + if (ctx->ShaderObjects._FragmentShaderPresent) { + interpolate_varying(ctx, span); + } + /* This is the normal place to compute the resulting fragment color/Z. * As an optimization, we try to defer this until after Z/stencil * testing in order to try to avoid computing colors that we won't @@ -1155,11 +1195,11 @@ _swrast_write_rgba_span( GLcontext *ctx, struct sw_span *span) if (span->interpMask & SPAN_FOG) interpolate_fog(ctx, span); - /* Compute fragment colors with fragment program or texture lookups */
- if (ctx->ShaderObjects._FragmentShaderPresent) {
- if (span->interpMask & SPAN_Z)
- _swrast_span_interpolate_z (ctx, span);
- _swrast_exec_arbshader (ctx, span);
+ /* Compute fragment colors with fragment program or texture lookups */ + if (ctx->ShaderObjects._FragmentShaderPresent) { + if (span->interpMask & SPAN_Z) + _swrast_span_interpolate_z (ctx, span); + _swrast_exec_arbshader (ctx, span); } else if (ctx->FragmentProgram._Active) { /* frag prog may need Z values */ @@ -1240,11 +1280,11 @@ _swrast_write_rgba_span( GLcontext *ctx, struct sw_span *span) if (span->interpMask & SPAN_FOG) interpolate_fog(ctx, span); - if (ctx->ShaderObjects._FragmentShaderPresent) {
- if (span->interpMask & SPAN_Z)
- _swrast_span_interpolate_z (ctx, span);
- _swrast_exec_arbshader (ctx, span);
- }
+ if (ctx->ShaderObjects._FragmentShaderPresent) { + if (span->interpMask & SPAN_Z) + _swrast_span_interpolate_z (ctx, span); + _swrast_exec_arbshader (ctx, span); + } else if (ctx->FragmentProgram._Active) _swrast_exec_fragment_program( ctx, span ); else if (ctx->ATIFragmentShader._Enabled) diff --git a/src/mesa/swrast/s_tritemp.h b/src/mesa/swrast/s_tritemp.h index 7f581561ec5..29a7a94da15 100644 --- a/src/mesa/swrast/s_tritemp.h +++ b/src/mesa/swrast/s_tritemp.h @@ -28,7 +28,7 @@ * This file is #include'd to generate custom triangle rasterizers. * * The following macros may be defined to indicate what auxillary information - * must be interplated across the triangle: + * must be interpolated across the triangle: * INTERP_Z - if defined, interpolate vertex Z values * INTERP_W - if defined, interpolate vertex W values * INTERP_FOG - if defined, interpolate fog values @@ -41,6 +41,7 @@ * INTERP_TEX - if defined, interpolate set 0 float STRQ texcoords * NOTE: OpenGL STRQ = Mesa STUV (R was taken for red) * INTERP_MULTITEX - if defined, interpolate N units of STRQ texcoords + * INTERP_VARYING - if defined, interpolate M floats of GLSL varyings * * When one can directly address pixels in the color buffer the following * macros can be defined and used to compute pixel addresses during @@ -142,6 +143,20 @@ +#ifdef INTERP_VARYING +#define VARYING_LOOP(CODE)\ + {\ + GLuint iv, ic;\ + for (iv = 0; iv < MAX_VARYING_VECTORS; iv++) {\ + for (ic = 0; ic < VARYINGS_PER_VECTOR; ic++) {\ + CODE\ + }\ + }\ + } +#endif + + + /* * Some code we unfortunately need to prevent negative interpolated colors. */ @@ -648,6 +663,19 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, ) } #endif +#ifdef INTERP_VARYING + span.interpMask |= SPAN_VARYING; + { + /* win[3] is 1/W */ + const GLfloat wMax = vMax->win[3], wMin = vMin->win[3], wMid = vMid->win[3]; + VARYING_LOOP( + GLfloat eMaj_dvar = vMax->attribute[iv][ic] * wMax - vMin->attribute[iv][ic] * wMin; + GLfloat eBot_dvar = vMid->attribute[iv][ic] * wMid - vMin->attribute[iv][ic] * wMin; + span.varStepX[iv][ic] = oneOverArea * (eMaj_dvar * eBot.dy - eMaj.dy * eBot_dvar); + span.varStepY[iv][ic] = oneOverArea * (eMaj.dx * eBot_dvar - eMaj_dvar * eBot.dx); + ) + } +#endif /* * We always sample at pixel centers. However, we avoid @@ -751,6 +779,11 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, GLfloat duOuter[MAX_TEXTURE_COORD_UNITS], duInner[MAX_TEXTURE_COORD_UNITS]; GLfloat dvOuter[MAX_TEXTURE_COORD_UNITS], dvInner[MAX_TEXTURE_COORD_UNITS]; #endif +#ifdef INTERP_VARYING + GLfloat varLeft[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; + GLfloat dvarOuter[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; + GLfloat dvarInner[MAX_VARYING_VECTORS][VARYINGS_PER_VECTOR]; +#endif for (subTriangle=0; subTriangle<=1; subTriangle++) { EdgeT *eLeft, *eRight; @@ -1024,6 +1057,15 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, dvOuter[u] = span.texStepY[u][3] + dxOuter * span.texStepX[u][3]; ) #endif +#ifdef INTERP_VARYING + VARYING_LOOP( + const GLfloat invW = vLower->win[3]; + const GLfloat var0 = vLower->attribute[iv][ic] * invW; + varLeft[iv][ic] = var0 + (span.varStepX[iv][ic] * adjx + + span.varStepY[iv][ic] * adjy) * (1.0f / FIXED_SCALE); + dvarOuter[iv][ic] = span.varStepY[iv][ic] + dxOuter * span.varStepX[iv][ic]; + ) +#endif } /*if setupLeft*/ @@ -1086,6 +1128,11 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, dvInner[u] = dvOuter[u] + span.texStepX[u][3]; ) #endif +#ifdef INTERP_VARYING + VARYING_LOOP( + dvarInner[iv][ic] = dvarOuter[iv][ic] + span.varStepX[iv][ic]; + ) +#endif while (lines > 0) { /* initialize the span interpolants to the leftmost value */ @@ -1135,6 +1182,11 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, span.tex[u][3] = vLeft[u]; ) #endif +#ifdef INTERP_VARYING + VARYING_LOOP( + span.var[iv][ic] = varLeft[iv][ic]; + ) +#endif /* This is where we actually generate fragments */ /* XXX the test for span.y > 0 _shouldn't_ be needed but @@ -1223,6 +1275,11 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, vLeft[u] += dvOuter[u]; ) #endif +#ifdef INTERP_VARYING + VARYING_LOOP( + varLeft[iv][ic] += dvarOuter[iv][ic]; + ) +#endif } else { #ifdef PIXEL_ADDRESS @@ -1268,6 +1325,11 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, vLeft[u] += dvInner[u]; ) #endif +#ifdef INTERP_VARYING + VARYING_LOOP( + varLeft[iv][ic] += dvarInner[iv][ic]; + ) +#endif } } /*while lines>0*/ @@ -1299,7 +1361,9 @@ static void NAME(GLcontext *ctx, const SWvertex *v0, #undef INTERP_INT_TEX #undef INTERP_TEX #undef INTERP_MULTITEX +#undef INTERP_VARYING #undef TEX_UNIT_LOOP +#undef VARYING_LOOP #undef S_SCALE #undef T_SCALE diff --git a/src/mesa/swrast/swrast.h b/src/mesa/swrast/swrast.h index 4422195a524..2a212342539 100644 --- a/src/mesa/swrast/swrast.h +++ b/src/mesa/swrast/swrast.h @@ -2,7 +2,7 @@ * Mesa 3-D graphics library * Version: 6.5 * - * Copyright (C) 1999-2005 Brian Paul All Rights Reserved. + * Copyright (C) 1999-2006 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"), @@ -73,6 +73,7 @@ typedef struct { GLfloat fog; GLfloat index; GLfloat pointSize; + GLfloat attribute[MAX_VERTEX_ATTRIBS][4]; } SWvertex; |