Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | Download | RSS feed

  1. /*
  2.  * Mesa 3-D graphics library
  3.  * Version:  7.1
  4.  *
  5.  * Copyright (C) 1999-2008  Brian Paul   All Rights Reserved.
  6.  *
  7.  * Permission is hereby granted, free of charge, to any person obtaining a
  8.  * copy of this software and associated documentation files (the "Software"),
  9.  * to deal in the Software without restriction, including without limitation
  10.  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
  11.  * and/or sell copies of the Software, and to permit persons to whom the
  12.  * Software is furnished to do so, subject to the following conditions:
  13.  *
  14.  * The above copyright notice and this permission notice shall be included
  15.  * in all copies or substantial portions of the Software.
  16.  *
  17.  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
  18.  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  19.  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
  20.  * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
  21.  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  22.  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  23.  *
  24.  * Authors:
  25.  *    Keith Whitwell <keith@tungstengraphics.com>
  26.  *    Brian Paul
  27.  */
  28.  
  29. #include "main/imports.h"
  30. #include "main/bufferobj.h"
  31. #include "main/colormac.h"
  32. #include "main/mtypes.h"
  33. #include "main/teximage.h"
  34. #include "program/prog_parameter.h"
  35. #include "program/prog_statevars.h"
  36. #include "swrast.h"
  37. #include "s_blend.h"
  38. #include "s_context.h"
  39. #include "s_lines.h"
  40. #include "s_points.h"
  41. #include "s_span.h"
  42. #include "s_triangle.h"
  43. #include "s_texfilter.h"
  44.  
  45.  
  46. /**
  47.  * Recompute the value of swrast->_RasterMask, etc. according to
  48.  * the current context.  The _RasterMask field can be easily tested by
  49.  * drivers to determine certain basic GL state (does the primitive need
  50.  * stenciling, logic-op, fog, etc?).
  51.  */
  52. static void
  53. _swrast_update_rasterflags( struct gl_context *ctx )
  54. {
  55.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  56.    GLbitfield rasterMask = 0;
  57.    GLuint i;
  58.  
  59.    if (ctx->Color.AlphaEnabled)           rasterMask |= ALPHATEST_BIT;
  60.    if (ctx->Color.BlendEnabled)           rasterMask |= BLEND_BIT;
  61.    if (ctx->Depth.Test)                   rasterMask |= DEPTH_BIT;
  62.    if (swrast->_FogEnabled)               rasterMask |= FOG_BIT;
  63.    if (ctx->Scissor.Enabled)              rasterMask |= CLIP_BIT;
  64.    if (ctx->Stencil._Enabled)             rasterMask |= STENCIL_BIT;
  65.    for (i = 0; i < ctx->Const.MaxDrawBuffers; i++) {
  66.       if (!ctx->Color.ColorMask[i][0] ||
  67.           !ctx->Color.ColorMask[i][1] ||
  68.           !ctx->Color.ColorMask[i][2] ||
  69.           !ctx->Color.ColorMask[i][3]) {
  70.          rasterMask |= MASKING_BIT;
  71.          break;
  72.       }
  73.    }
  74.    if (ctx->Color._LogicOpEnabled)     rasterMask |= LOGIC_OP_BIT;
  75.    if (ctx->Texture._EnabledUnits)     rasterMask |= TEXTURE_BIT;
  76.    if (   ctx->Viewport.X < 0
  77.        || ctx->Viewport.X + ctx->Viewport.Width > (GLint) ctx->DrawBuffer->Width
  78.        || ctx->Viewport.Y < 0
  79.        || ctx->Viewport.Y + ctx->Viewport.Height > (GLint) ctx->DrawBuffer->Height) {
  80.       rasterMask |= CLIP_BIT;
  81.    }
  82.  
  83.    if (ctx->Query.CurrentOcclusionObject)
  84.       rasterMask |= OCCLUSION_BIT;
  85.  
  86.  
  87.    /* If we're not drawing to exactly one color buffer set the
  88.     * MULTI_DRAW_BIT flag.  Also set it if we're drawing to no
  89.     * buffers or the RGBA or CI mask disables all writes.
  90.     */
  91.    if (ctx->DrawBuffer->_NumColorDrawBuffers != 1) {
  92.       /* more than one color buffer designated for writing (or zero buffers) */
  93.       rasterMask |= MULTI_DRAW_BIT;
  94.    }
  95.  
  96.    for (i = 0; i < ctx->Const.MaxDrawBuffers; i++) {
  97.       if (ctx->Color.ColorMask[i][0] +
  98.           ctx->Color.ColorMask[i][1] +
  99.           ctx->Color.ColorMask[i][2] +
  100.           ctx->Color.ColorMask[i][3] == 0) {
  101.          rasterMask |= MULTI_DRAW_BIT; /* all RGBA channels disabled */
  102.          break;
  103.       }
  104.    }
  105.  
  106.  
  107.    if (ctx->FragmentProgram._Current) {
  108.       rasterMask |= FRAGPROG_BIT;
  109.    }
  110.  
  111.    if (ctx->ATIFragmentShader._Enabled) {
  112.       rasterMask |= ATIFRAGSHADER_BIT;
  113.    }
  114.  
  115. #if CHAN_TYPE == GL_FLOAT
  116.    if (ctx->Color.ClampFragmentColor == GL_TRUE) {
  117.       rasterMask |= CLAMPING_BIT;
  118.    }
  119. #endif
  120.  
  121.    SWRAST_CONTEXT(ctx)->_RasterMask = rasterMask;
  122. }
  123.  
  124.  
  125. /**
  126.  * Examine polygon cull state to compute the _BackfaceCullSign field.
  127.  * _BackfaceCullSign will be 0 if no culling, -1 if culling back-faces,
  128.  * and 1 if culling front-faces.  The Polygon FrontFace state also
  129.  * factors in.
  130.  */
  131. static void
  132. _swrast_update_polygon( struct gl_context *ctx )
  133. {
  134.    GLfloat backface_sign;
  135.  
  136.    if (ctx->Polygon.CullFlag) {
  137.       switch (ctx->Polygon.CullFaceMode) {
  138.       case GL_BACK:
  139.          backface_sign = -1.0F;
  140.          break;
  141.       case GL_FRONT:
  142.          backface_sign = 1.0F;
  143.          break;
  144.       case GL_FRONT_AND_BACK:
  145.          /* fallthrough */
  146.       default:
  147.          backface_sign = 0.0F;
  148.       }
  149.    }
  150.    else {
  151.       backface_sign = 0.0F;
  152.    }
  153.  
  154.    SWRAST_CONTEXT(ctx)->_BackfaceCullSign = backface_sign;
  155.  
  156.    /* This is for front/back-face determination, but not for culling */
  157.    SWRAST_CONTEXT(ctx)->_BackfaceSign
  158.       = (ctx->Polygon.FrontFace == GL_CW) ? -1.0F : 1.0F;
  159. }
  160.  
  161.  
  162.  
  163. /**
  164.  * Update the _PreferPixelFog field to indicate if we need to compute
  165.  * fog blend factors (from the fog coords) per-fragment.
  166.  */
  167. static void
  168. _swrast_update_fog_hint( struct gl_context *ctx )
  169. {
  170.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  171.    swrast->_PreferPixelFog = (!swrast->AllowVertexFog ||
  172.                               ctx->FragmentProgram._Current ||
  173.                               (ctx->Hint.Fog == GL_NICEST &&
  174.                                swrast->AllowPixelFog));
  175. }
  176.  
  177.  
  178.  
  179. /**
  180.  * Update the swrast->_TextureCombinePrimary flag.
  181.  */
  182. static void
  183. _swrast_update_texture_env( struct gl_context *ctx )
  184. {
  185.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  186.    GLuint i;
  187.  
  188.    swrast->_TextureCombinePrimary = GL_FALSE;
  189.  
  190.    for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
  191.       const struct gl_tex_env_combine_state *combine =
  192.          ctx->Texture.Unit[i]._CurrentCombine;
  193.       GLuint term;
  194.       for (term = 0; term < combine->_NumArgsRGB; term++) {
  195.          if (combine->SourceRGB[term] == GL_PRIMARY_COLOR) {
  196.             swrast->_TextureCombinePrimary = GL_TRUE;
  197.             return;
  198.          }
  199.          if (combine->SourceA[term] == GL_PRIMARY_COLOR) {
  200.             swrast->_TextureCombinePrimary = GL_TRUE;
  201.             return;
  202.          }
  203.       }
  204.    }
  205. }
  206.  
  207.  
  208. /**
  209.  * Determine if we can defer texturing/shading until after Z/stencil
  210.  * testing.  This potentially allows us to skip texturing/shading for
  211.  * lots of fragments.
  212.  */
  213. static void
  214. _swrast_update_deferred_texture(struct gl_context *ctx)
  215. {
  216.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  217.    if (ctx->Color.AlphaEnabled) {
  218.       /* alpha test depends on post-texture/shader colors */
  219.       swrast->_DeferredTexture = GL_FALSE;
  220.    }
  221.    else {
  222.       const struct gl_fragment_program *fprog
  223.          = ctx->FragmentProgram._Current;
  224.       if (fprog && (fprog->Base.OutputsWritten & (1 << FRAG_RESULT_DEPTH))) {
  225.          /* Z comes from fragment program/shader */
  226.          swrast->_DeferredTexture = GL_FALSE;
  227.       }
  228.       else if (fprog && fprog->UsesKill) {
  229.          swrast->_DeferredTexture = GL_FALSE;
  230.       }
  231.       else if (ctx->Query.CurrentOcclusionObject) {
  232.          /* occlusion query depends on shader discard/kill results */
  233.          swrast->_DeferredTexture = GL_FALSE;
  234.       }
  235.       else {
  236.          swrast->_DeferredTexture = GL_TRUE;
  237.       }
  238.    }
  239. }
  240.  
  241.  
  242. /**
  243.  * Update swrast->_FogColor and swrast->_FogEnable values.
  244.  */
  245. static void
  246. _swrast_update_fog_state( struct gl_context *ctx )
  247. {
  248.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  249.    const struct gl_fragment_program *fp = ctx->FragmentProgram._Current;
  250.  
  251.    /* determine if fog is needed, and if so, which fog mode */
  252.    swrast->_FogEnabled = GL_FALSE;
  253.    if (fp && fp->Base.Target == GL_FRAGMENT_PROGRAM_ARB) {
  254.       if (fp->FogOption != GL_NONE) {
  255.          swrast->_FogEnabled = GL_TRUE;
  256.          swrast->_FogMode = fp->FogOption;
  257.       }
  258.    }
  259.    else if (ctx->Fog.Enabled) {
  260.       swrast->_FogEnabled = GL_TRUE;
  261.       swrast->_FogMode = ctx->Fog.Mode;
  262.    }
  263. }
  264.  
  265.  
  266. /**
  267.  * Update state for running fragment programs.  Basically, load the
  268.  * program parameters with current state values.
  269.  */
  270. static void
  271. _swrast_update_fragment_program(struct gl_context *ctx, GLbitfield newState)
  272. {
  273.    const struct gl_fragment_program *fp = ctx->FragmentProgram._Current;
  274.    if (fp) {
  275.       _mesa_load_state_parameters(ctx, fp->Base.Parameters);
  276.    }
  277. }
  278.  
  279.  
  280. /**
  281.  * See if we can do early diffuse+specular (primary+secondary) color
  282.  * add per vertex instead of per-fragment.
  283.  */
  284. static void
  285. _swrast_update_specular_vertex_add(struct gl_context *ctx)
  286. {
  287.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  288.    GLboolean separateSpecular = ctx->Fog.ColorSumEnabled ||
  289.       (ctx->Light.Enabled &&
  290.        ctx->Light.Model.ColorControl == GL_SEPARATE_SPECULAR_COLOR);
  291.  
  292.    swrast->SpecularVertexAdd = (separateSpecular
  293.                                 && ctx->Texture._EnabledUnits == 0x0
  294.                                 && !ctx->FragmentProgram._Current
  295.                                 && !ctx->ATIFragmentShader._Enabled);
  296. }
  297.  
  298.  
  299. #define _SWRAST_NEW_DERIVED (_SWRAST_NEW_RASTERMASK |   \
  300.                              _NEW_PROGRAM_CONSTANTS |   \
  301.                              _NEW_TEXTURE |             \
  302.                              _NEW_HINT |                \
  303.                              _NEW_POLYGON )
  304.  
  305. /* State referenced by _swrast_choose_triangle, _swrast_choose_line.
  306.  */
  307. #define _SWRAST_NEW_TRIANGLE (_SWRAST_NEW_DERIVED |             \
  308.                               _NEW_RENDERMODE|                  \
  309.                               _NEW_POLYGON|                     \
  310.                               _NEW_DEPTH|                       \
  311.                               _NEW_STENCIL|                     \
  312.                               _NEW_COLOR|                       \
  313.                               _NEW_TEXTURE|                     \
  314.                               _SWRAST_NEW_RASTERMASK|           \
  315.                               _NEW_LIGHT|                       \
  316.                               _NEW_FOG |                        \
  317.                               _DD_NEW_SEPARATE_SPECULAR)
  318.  
  319. #define _SWRAST_NEW_LINE (_SWRAST_NEW_DERIVED |         \
  320.                           _NEW_RENDERMODE|              \
  321.                           _NEW_LINE|                    \
  322.                           _NEW_TEXTURE|                 \
  323.                           _NEW_LIGHT|                   \
  324.                           _NEW_FOG|                     \
  325.                           _NEW_DEPTH |                  \
  326.                           _DD_NEW_SEPARATE_SPECULAR)
  327.  
  328. #define _SWRAST_NEW_POINT (_SWRAST_NEW_DERIVED |        \
  329.                            _NEW_RENDERMODE |            \
  330.                            _NEW_POINT |                 \
  331.                            _NEW_TEXTURE |               \
  332.                            _NEW_LIGHT |                 \
  333.                            _NEW_FOG |                   \
  334.                            _DD_NEW_SEPARATE_SPECULAR)
  335.  
  336. #define _SWRAST_NEW_TEXTURE_SAMPLE_FUNC _NEW_TEXTURE
  337.  
  338. #define _SWRAST_NEW_TEXTURE_ENV_MODE _NEW_TEXTURE
  339.  
  340. #define _SWRAST_NEW_BLEND_FUNC _NEW_COLOR
  341.  
  342.  
  343.  
  344. /**
  345.  * Stub for swrast->Triangle to select a true triangle function
  346.  * after a state change.
  347.  */
  348. static void
  349. _swrast_validate_triangle( struct gl_context *ctx,
  350.                            const SWvertex *v0,
  351.                            const SWvertex *v1,
  352.                            const SWvertex *v2 )
  353. {
  354.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  355.  
  356.    _swrast_validate_derived( ctx );
  357.    swrast->choose_triangle( ctx );
  358.    ASSERT(swrast->Triangle);
  359.  
  360.    if (swrast->SpecularVertexAdd) {
  361.       /* separate specular color, but no texture */
  362.       swrast->SpecTriangle = swrast->Triangle;
  363.       swrast->Triangle = _swrast_add_spec_terms_triangle;
  364.    }
  365.  
  366.    swrast->Triangle( ctx, v0, v1, v2 );
  367. }
  368.  
  369. /**
  370.  * Called via swrast->Line.  Examine current GL state and choose a software
  371.  * line routine.  Then call it.
  372.  */
  373. static void
  374. _swrast_validate_line( struct gl_context *ctx, const SWvertex *v0, const SWvertex *v1 )
  375. {
  376.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  377.  
  378.    _swrast_validate_derived( ctx );
  379.    swrast->choose_line( ctx );
  380.    ASSERT(swrast->Line);
  381.  
  382.    if (swrast->SpecularVertexAdd) {
  383.       swrast->SpecLine = swrast->Line;
  384.       swrast->Line = _swrast_add_spec_terms_line;
  385.    }
  386.  
  387.    swrast->Line( ctx, v0, v1 );
  388. }
  389.  
  390. /**
  391.  * Called via swrast->Point.  Examine current GL state and choose a software
  392.  * point routine.  Then call it.
  393.  */
  394. static void
  395. _swrast_validate_point( struct gl_context *ctx, const SWvertex *v0 )
  396. {
  397.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  398.  
  399.    _swrast_validate_derived( ctx );
  400.    swrast->choose_point( ctx );
  401.  
  402.    if (swrast->SpecularVertexAdd) {
  403.       swrast->SpecPoint = swrast->Point;
  404.       swrast->Point = _swrast_add_spec_terms_point;
  405.    }
  406.  
  407.    swrast->Point( ctx, v0 );
  408. }
  409.  
  410.  
  411. /**
  412.  * Called via swrast->BlendFunc.  Examine GL state to choose a blending
  413.  * function, then call it.
  414.  */
  415. static void _ASMAPI
  416. _swrast_validate_blend_func(struct gl_context *ctx, GLuint n, const GLubyte mask[],
  417.                             GLvoid *src, const GLvoid *dst,
  418.                             GLenum chanType )
  419. {
  420.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  421.  
  422.    _swrast_validate_derived( ctx ); /* why is this needed? */
  423.    _swrast_choose_blend_func( ctx, chanType );
  424.  
  425.    swrast->BlendFunc( ctx, n, mask, src, dst, chanType );
  426. }
  427.  
  428.  
  429. /**
  430.  * Make sure we have texture image data for all the textures we may need
  431.  * for subsequent rendering.
  432.  */
  433. static void
  434. _swrast_validate_texture_images(struct gl_context *ctx)
  435. {
  436.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  437.    GLuint u;
  438.  
  439.    if (!swrast->ValidateTextureImage || !ctx->Texture._EnabledUnits) {
  440.       /* no textures enabled, or no way to validate images! */
  441.       return;
  442.    }
  443.  
  444.    for (u = 0; u < ctx->Const.MaxTextureImageUnits; u++) {
  445.       if (ctx->Texture.Unit[u]._ReallyEnabled) {
  446.          struct gl_texture_object *texObj = ctx->Texture.Unit[u]._Current;
  447.          ASSERT(texObj);
  448.          if (texObj) {
  449.             GLuint numFaces = (texObj->Target == GL_TEXTURE_CUBE_MAP) ? 6 : 1;
  450.             GLuint face;
  451.             for (face = 0; face < numFaces; face++) {
  452.                GLint lvl;
  453.                for (lvl = texObj->BaseLevel; lvl <= texObj->_MaxLevel; lvl++) {
  454.                   struct gl_texture_image *texImg = texObj->Image[face][lvl];
  455.                   if (texImg && !texImg->Data) {
  456.                      swrast->ValidateTextureImage(ctx, texObj, face, lvl);
  457.                      ASSERT(texObj->Image[face][lvl]->Data);
  458.                   }
  459.                }
  460.             }
  461.          }
  462.       }
  463.    }
  464. }
  465.  
  466.  
  467. /**
  468.  * Free the texture image data attached to all currently enabled
  469.  * textures.  Meant to be called by device drivers when transitioning
  470.  * from software to hardware rendering.
  471.  */
  472. void
  473. _swrast_eject_texture_images(struct gl_context *ctx)
  474. {
  475.    GLuint u;
  476.  
  477.    if (!ctx->Texture._EnabledUnits) {
  478.       /* no textures enabled */
  479.       return;
  480.    }
  481.  
  482.    for (u = 0; u < ctx->Const.MaxTextureImageUnits; u++) {
  483.       if (ctx->Texture.Unit[u]._ReallyEnabled) {
  484.          struct gl_texture_object *texObj = ctx->Texture.Unit[u]._Current;
  485.          ASSERT(texObj);
  486.          if (texObj) {
  487.             GLuint numFaces = (texObj->Target == GL_TEXTURE_CUBE_MAP) ? 6 : 1;
  488.             GLuint face;
  489.             for (face = 0; face < numFaces; face++) {
  490.                GLint lvl;
  491.                for (lvl = texObj->BaseLevel; lvl <= texObj->_MaxLevel; lvl++) {
  492.                   struct gl_texture_image *texImg = texObj->Image[face][lvl];
  493.                   if (texImg && texImg->Data) {
  494.                      _mesa_free_texmemory(texImg->Data);
  495.                      texImg->Data = NULL;
  496.                   }
  497.                }
  498.             }
  499.          }
  500.       }
  501.    }
  502. }
  503.  
  504.  
  505.  
  506. static void
  507. _swrast_sleep( struct gl_context *ctx, GLbitfield new_state )
  508. {
  509.    (void) ctx; (void) new_state;
  510. }
  511.  
  512.  
  513. static void
  514. _swrast_invalidate_state( struct gl_context *ctx, GLbitfield new_state )
  515. {
  516.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  517.    GLuint i;
  518.  
  519.    swrast->NewState |= new_state;
  520.  
  521.    /* After 10 statechanges without any swrast functions being called,
  522.     * put the module to sleep.
  523.     */
  524.    if (++swrast->StateChanges > 10) {
  525.       swrast->InvalidateState = _swrast_sleep;
  526.       swrast->NewState = ~0;
  527.       new_state = ~0;
  528.    }
  529.  
  530.    if (new_state & swrast->InvalidateTriangleMask)
  531.       swrast->Triangle = _swrast_validate_triangle;
  532.  
  533.    if (new_state & swrast->InvalidateLineMask)
  534.       swrast->Line = _swrast_validate_line;
  535.  
  536.    if (new_state & swrast->InvalidatePointMask)
  537.       swrast->Point = _swrast_validate_point;
  538.  
  539.    if (new_state & _SWRAST_NEW_BLEND_FUNC)
  540.       swrast->BlendFunc = _swrast_validate_blend_func;
  541.  
  542.    if (new_state & _SWRAST_NEW_TEXTURE_SAMPLE_FUNC)
  543.       for (i = 0 ; i < ctx->Const.MaxTextureImageUnits ; i++)
  544.          swrast->TextureSample[i] = NULL;
  545. }
  546.  
  547.  
  548. void
  549. _swrast_update_texture_samplers(struct gl_context *ctx)
  550. {
  551.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  552.    GLuint u;
  553.  
  554.    if (!swrast)
  555.       return; /* pipe hack */
  556.  
  557.    for (u = 0; u < ctx->Const.MaxTextureImageUnits; u++) {
  558.       const struct gl_texture_object *tObj = ctx->Texture.Unit[u]._Current;
  559.       /* Note: If tObj is NULL, the sample function will be a simple
  560.        * function that just returns opaque black (0,0,0,1).
  561.        */
  562.       swrast->TextureSample[u] = _swrast_choose_texture_sample_func(ctx, tObj);
  563.    }
  564. }
  565.  
  566.  
  567. /**
  568.  * Update swrast->_ActiveAttribs, swrast->_NumActiveAttribs,
  569.  * swrast->_ActiveAtttribMask.
  570.  */
  571. static void
  572. _swrast_update_active_attribs(struct gl_context *ctx)
  573. {
  574.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  575.    GLuint attribsMask;
  576.  
  577.    /*
  578.     * Compute _ActiveAttribsMask = which fragment attributes are needed.
  579.     */
  580.    if (ctx->FragmentProgram._Current) {
  581.       /* fragment program/shader */
  582.       attribsMask = ctx->FragmentProgram._Current->Base.InputsRead;
  583.       attribsMask &= ~FRAG_BIT_WPOS; /* WPOS is always handled specially */
  584.    }
  585.    else if (ctx->ATIFragmentShader._Enabled) {
  586.       attribsMask = ~0;  /* XXX fix me */
  587.    }
  588.    else {
  589.       /* fixed function */
  590.       attribsMask = 0x0;
  591.  
  592. #if CHAN_TYPE == GL_FLOAT
  593.       attribsMask |= FRAG_BIT_COL0;
  594. #endif
  595.  
  596.       if (ctx->Fog.ColorSumEnabled ||
  597.           (ctx->Light.Enabled &&
  598.            ctx->Light.Model.ColorControl == GL_SEPARATE_SPECULAR_COLOR)) {
  599.          attribsMask |= FRAG_BIT_COL1;
  600.       }
  601.  
  602.       if (swrast->_FogEnabled)
  603.          attribsMask |= FRAG_BIT_FOGC;
  604.  
  605.       attribsMask |= (ctx->Texture._EnabledUnits << FRAG_ATTRIB_TEX0);
  606.    }
  607.  
  608.    swrast->_ActiveAttribMask = attribsMask;
  609.  
  610.    /* Update _ActiveAttribs[] list */
  611.    {
  612.       GLuint i, num = 0;
  613.       for (i = 0; i < FRAG_ATTRIB_MAX; i++) {
  614.          if (attribsMask & (1 << i)) {
  615.             swrast->_ActiveAttribs[num++] = i;
  616.             /* how should this attribute be interpolated? */
  617.             if (i == FRAG_ATTRIB_COL0 || i == FRAG_ATTRIB_COL1)
  618.                swrast->_InterpMode[i] = ctx->Light.ShadeModel;
  619.             else
  620.                swrast->_InterpMode[i] = GL_SMOOTH;
  621.          }
  622.       }
  623.       swrast->_NumActiveAttribs = num;
  624.    }
  625. }
  626.  
  627.  
  628. void
  629. _swrast_validate_derived( struct gl_context *ctx )
  630. {
  631.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  632.  
  633.    if (swrast->NewState) {
  634.       if (swrast->NewState & _NEW_POLYGON)
  635.          _swrast_update_polygon( ctx );
  636.  
  637.       if (swrast->NewState & (_NEW_HINT | _NEW_PROGRAM))
  638.          _swrast_update_fog_hint( ctx );
  639.  
  640.       if (swrast->NewState & _SWRAST_NEW_TEXTURE_ENV_MODE)
  641.          _swrast_update_texture_env( ctx );
  642.  
  643.       if (swrast->NewState & (_NEW_FOG | _NEW_PROGRAM))
  644.          _swrast_update_fog_state( ctx );
  645.  
  646.       if (swrast->NewState & (_NEW_PROGRAM_CONSTANTS | _NEW_PROGRAM))
  647.          _swrast_update_fragment_program( ctx, swrast->NewState );
  648.  
  649.       if (swrast->NewState & (_NEW_TEXTURE | _NEW_PROGRAM)) {
  650.          _swrast_update_texture_samplers( ctx );
  651.          _swrast_validate_texture_images(ctx);
  652.       }
  653.  
  654.       if (swrast->NewState & (_NEW_COLOR | _NEW_PROGRAM))
  655.          _swrast_update_deferred_texture(ctx);
  656.  
  657.       if (swrast->NewState & _SWRAST_NEW_RASTERMASK)
  658.          _swrast_update_rasterflags( ctx );
  659.  
  660.       if (swrast->NewState & (_NEW_DEPTH |
  661.                               _NEW_FOG |
  662.                               _NEW_LIGHT |
  663.                               _NEW_PROGRAM |
  664.                               _NEW_TEXTURE))
  665.          _swrast_update_active_attribs(ctx);
  666.  
  667.       if (swrast->NewState & (_NEW_FOG |
  668.                               _NEW_PROGRAM |
  669.                               _NEW_LIGHT |
  670.                               _NEW_TEXTURE))
  671.          _swrast_update_specular_vertex_add(ctx);
  672.  
  673.       swrast->NewState = 0;
  674.       swrast->StateChanges = 0;
  675.       swrast->InvalidateState = _swrast_invalidate_state;
  676.    }
  677. }
  678.  
  679. #define SWRAST_DEBUG 0
  680.  
  681. /* Public entrypoints:  See also s_accum.c, s_bitmap.c, etc.
  682.  */
  683. void
  684. _swrast_Quad( struct gl_context *ctx,
  685.               const SWvertex *v0, const SWvertex *v1,
  686.               const SWvertex *v2, const SWvertex *v3 )
  687. {
  688.    if (SWRAST_DEBUG) {
  689.       _mesa_debug(ctx, "_swrast_Quad\n");
  690.       _swrast_print_vertex( ctx, v0 );
  691.       _swrast_print_vertex( ctx, v1 );
  692.       _swrast_print_vertex( ctx, v2 );
  693.       _swrast_print_vertex( ctx, v3 );
  694.    }
  695.    SWRAST_CONTEXT(ctx)->Triangle( ctx, v0, v1, v3 );
  696.    SWRAST_CONTEXT(ctx)->Triangle( ctx, v1, v2, v3 );
  697. }
  698.  
  699. void
  700. _swrast_Triangle( struct gl_context *ctx, const SWvertex *v0,
  701.                   const SWvertex *v1, const SWvertex *v2 )
  702. {
  703.    if (SWRAST_DEBUG) {
  704.       _mesa_debug(ctx, "_swrast_Triangle\n");
  705.       _swrast_print_vertex( ctx, v0 );
  706.       _swrast_print_vertex( ctx, v1 );
  707.       _swrast_print_vertex( ctx, v2 );
  708.    }
  709.    SWRAST_CONTEXT(ctx)->Triangle( ctx, v0, v1, v2 );
  710. }
  711.  
  712. void
  713. _swrast_Line( struct gl_context *ctx, const SWvertex *v0, const SWvertex *v1 )
  714. {
  715.    if (SWRAST_DEBUG) {
  716.       _mesa_debug(ctx, "_swrast_Line\n");
  717.       _swrast_print_vertex( ctx, v0 );
  718.       _swrast_print_vertex( ctx, v1 );
  719.    }
  720.    SWRAST_CONTEXT(ctx)->Line( ctx, v0, v1 );
  721. }
  722.  
  723. void
  724. _swrast_Point( struct gl_context *ctx, const SWvertex *v0 )
  725. {
  726.    if (SWRAST_DEBUG) {
  727.       _mesa_debug(ctx, "_swrast_Point\n");
  728.       _swrast_print_vertex( ctx, v0 );
  729.    }
  730.    SWRAST_CONTEXT(ctx)->Point( ctx, v0 );
  731. }
  732.  
  733. void
  734. _swrast_InvalidateState( struct gl_context *ctx, GLbitfield new_state )
  735. {
  736.    if (SWRAST_DEBUG) {
  737.       _mesa_debug(ctx, "_swrast_InvalidateState\n");
  738.    }
  739.    SWRAST_CONTEXT(ctx)->InvalidateState( ctx, new_state );
  740. }
  741.  
  742. void
  743. _swrast_ResetLineStipple( struct gl_context *ctx )
  744. {
  745.    if (SWRAST_DEBUG) {
  746.       _mesa_debug(ctx, "_swrast_ResetLineStipple\n");
  747.    }
  748.    SWRAST_CONTEXT(ctx)->StippleCounter = 0;
  749. }
  750.  
  751. void
  752. _swrast_SetFacing(struct gl_context *ctx, GLuint facing)
  753. {
  754.    SWRAST_CONTEXT(ctx)->PointLineFacing = facing;
  755. }
  756.  
  757. void
  758. _swrast_allow_vertex_fog( struct gl_context *ctx, GLboolean value )
  759. {
  760.    if (SWRAST_DEBUG) {
  761.       _mesa_debug(ctx, "_swrast_allow_vertex_fog %d\n", value);
  762.    }
  763.    SWRAST_CONTEXT(ctx)->InvalidateState( ctx, _NEW_HINT );
  764.    SWRAST_CONTEXT(ctx)->AllowVertexFog = value;
  765. }
  766.  
  767. void
  768. _swrast_allow_pixel_fog( struct gl_context *ctx, GLboolean value )
  769. {
  770.    if (SWRAST_DEBUG) {
  771.       _mesa_debug(ctx, "_swrast_allow_pixel_fog %d\n", value);
  772.    }
  773.    SWRAST_CONTEXT(ctx)->InvalidateState( ctx, _NEW_HINT );
  774.    SWRAST_CONTEXT(ctx)->AllowPixelFog = value;
  775. }
  776.  
  777.  
  778. GLboolean
  779. _swrast_CreateContext( struct gl_context *ctx )
  780. {
  781.    GLuint i;
  782.    SWcontext *swrast = (SWcontext *)CALLOC(sizeof(SWcontext));
  783.  
  784.    if (SWRAST_DEBUG) {
  785.       _mesa_debug(ctx, "_swrast_CreateContext\n");
  786.    }
  787.  
  788.    if (!swrast)
  789.       return GL_FALSE;
  790.  
  791.    swrast->NewState = ~0;
  792.  
  793.    swrast->choose_point = _swrast_choose_point;
  794.    swrast->choose_line = _swrast_choose_line;
  795.    swrast->choose_triangle = _swrast_choose_triangle;
  796.  
  797.    swrast->InvalidatePointMask = _SWRAST_NEW_POINT;
  798.    swrast->InvalidateLineMask = _SWRAST_NEW_LINE;
  799.    swrast->InvalidateTriangleMask = _SWRAST_NEW_TRIANGLE;
  800.  
  801.    swrast->Point = _swrast_validate_point;
  802.    swrast->Line = _swrast_validate_line;
  803.    swrast->Triangle = _swrast_validate_triangle;
  804.    swrast->InvalidateState = _swrast_sleep;
  805.    swrast->BlendFunc = _swrast_validate_blend_func;
  806.  
  807.    swrast->AllowVertexFog = GL_TRUE;
  808.    swrast->AllowPixelFog = GL_TRUE;
  809.  
  810.    /* Optimized Accum buffer */
  811.    swrast->_IntegerAccumMode = GL_FALSE;
  812.    swrast->_IntegerAccumScaler = 0.0;
  813.  
  814.    for (i = 0; i < MAX_TEXTURE_IMAGE_UNITS; i++)
  815.       swrast->TextureSample[i] = NULL;
  816.  
  817.    swrast->SpanArrays = MALLOC_STRUCT(sw_span_arrays);
  818.    if (!swrast->SpanArrays) {
  819.       FREE(swrast);
  820.       return GL_FALSE;
  821.    }
  822.    swrast->SpanArrays->ChanType = CHAN_TYPE;
  823. #if CHAN_TYPE == GL_UNSIGNED_BYTE
  824.    swrast->SpanArrays->rgba = swrast->SpanArrays->rgba8;
  825. #elif CHAN_TYPE == GL_UNSIGNED_SHORT
  826.    swrast->SpanArrays->rgba = swrast->SpanArrays->rgba16;
  827. #else
  828.    swrast->SpanArrays->rgba = swrast->SpanArrays->attribs[FRAG_ATTRIB_COL0];
  829. #endif
  830.  
  831.    /* init point span buffer */
  832.    swrast->PointSpan.primitive = GL_POINT;
  833.    swrast->PointSpan.end = 0;
  834.    swrast->PointSpan.facing = 0;
  835.    swrast->PointSpan.array = swrast->SpanArrays;
  836.  
  837.    swrast->TexelBuffer = (GLfloat *) MALLOC(ctx->Const.MaxTextureImageUnits *
  838.                                            MAX_WIDTH * 4 * sizeof(GLfloat));
  839.    if (!swrast->TexelBuffer) {
  840.       FREE(swrast->SpanArrays);
  841.       FREE(swrast);
  842.       return GL_FALSE;
  843.    }
  844.  
  845.    ctx->swrast_context = swrast;
  846.  
  847.    return GL_TRUE;
  848. }
  849.  
  850. void
  851. _swrast_DestroyContext( struct gl_context *ctx )
  852. {
  853.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  854.  
  855.    if (SWRAST_DEBUG) {
  856.       _mesa_debug(ctx, "_swrast_DestroyContext\n");
  857.    }
  858.  
  859.    FREE( swrast->SpanArrays );
  860.    if (swrast->ZoomedArrays)
  861.       FREE( swrast->ZoomedArrays );
  862.    FREE( swrast->TexelBuffer );
  863.    FREE( swrast );
  864.  
  865.    ctx->swrast_context = 0;
  866. }
  867.  
  868.  
  869. struct swrast_device_driver *
  870. _swrast_GetDeviceDriverReference( struct gl_context *ctx )
  871. {
  872.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  873.    return &swrast->Driver;
  874. }
  875.  
  876. void
  877. _swrast_flush( struct gl_context *ctx )
  878. {
  879.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  880.    /* flush any pending fragments from rendering points */
  881.    if (swrast->PointSpan.end > 0) {
  882.       _swrast_write_rgba_span(ctx, &(swrast->PointSpan));
  883.       swrast->PointSpan.end = 0;
  884.    }
  885. }
  886.  
  887. void
  888. _swrast_render_primitive( struct gl_context *ctx, GLenum prim )
  889. {
  890.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  891.    if (swrast->Primitive == GL_POINTS && prim != GL_POINTS) {
  892.       _swrast_flush(ctx);
  893.    }
  894.    swrast->Primitive = prim;
  895. }
  896.  
  897.  
  898. void
  899. _swrast_render_start( struct gl_context *ctx )
  900. {
  901.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  902.    if (swrast->Driver.SpanRenderStart)
  903.       swrast->Driver.SpanRenderStart( ctx );
  904.    swrast->PointSpan.end = 0;
  905. }
  906.  
  907. void
  908. _swrast_render_finish( struct gl_context *ctx )
  909. {
  910.    SWcontext *swrast = SWRAST_CONTEXT(ctx);
  911.    if (swrast->Driver.SpanRenderFinish)
  912.       swrast->Driver.SpanRenderFinish( ctx );
  913.  
  914.    _swrast_flush(ctx);
  915. }
  916.  
  917.  
  918. #define SWRAST_DEBUG_VERTICES 0
  919.  
  920. void
  921. _swrast_print_vertex( struct gl_context *ctx, const SWvertex *v )
  922. {
  923.    GLuint i;
  924.  
  925.    if (SWRAST_DEBUG_VERTICES) {
  926.       _mesa_debug(ctx, "win %f %f %f %f\n",
  927.                   v->attrib[FRAG_ATTRIB_WPOS][0],
  928.                   v->attrib[FRAG_ATTRIB_WPOS][1],
  929.                   v->attrib[FRAG_ATTRIB_WPOS][2],
  930.                   v->attrib[FRAG_ATTRIB_WPOS][3]);
  931.  
  932.       for (i = 0 ; i < ctx->Const.MaxTextureCoordUnits ; i++)
  933.          if (ctx->Texture.Unit[i]._ReallyEnabled)
  934.             _mesa_debug(ctx, "texcoord[%d] %f %f %f %f\n", i,
  935.                         v->attrib[FRAG_ATTRIB_TEX0 + i][0],
  936.                         v->attrib[FRAG_ATTRIB_TEX0 + i][1],
  937.                         v->attrib[FRAG_ATTRIB_TEX0 + i][2],
  938.                         v->attrib[FRAG_ATTRIB_TEX0 + i][3]);
  939.  
  940. #if CHAN_TYPE == GL_FLOAT
  941.       _mesa_debug(ctx, "color %f %f %f %f\n",
  942.                   v->color[0], v->color[1], v->color[2], v->color[3]);
  943. #else
  944.       _mesa_debug(ctx, "color %d %d %d %d\n",
  945.                   v->color[0], v->color[1], v->color[2], v->color[3]);
  946. #endif
  947.       _mesa_debug(ctx, "spec %g %g %g %g\n",
  948.                   v->attrib[FRAG_ATTRIB_COL1][0],
  949.                   v->attrib[FRAG_ATTRIB_COL1][1],
  950.                   v->attrib[FRAG_ATTRIB_COL1][2],
  951.                   v->attrib[FRAG_ATTRIB_COL1][3]);
  952.       _mesa_debug(ctx, "fog %f\n", v->attrib[FRAG_ATTRIB_FOGC][0]);
  953.       _mesa_debug(ctx, "index %f\n", v->attrib[FRAG_ATTRIB_CI][0]);
  954.       _mesa_debug(ctx, "pointsize %f\n", v->pointSize);
  955.       _mesa_debug(ctx, "\n");
  956.    }
  957. }
  958.