Home | History | Annotate | Download | only in i915
      1 /**************************************************************************
      2  *
      3  * Copyright 2003 Tungsten Graphics, Inc., Cedar Park, Texas.
      4  * All Rights Reserved.
      5  *
      6  * Permission is hereby granted, free of charge, to any person obtaining a
      7  * copy of this software and associated documentation files (the
      8  * "Software"), to deal in the Software without restriction, including
      9  * without limitation the rights to use, copy, modify, merge, publish,
     10  * distribute, sub license, and/or sell copies of the Software, and to
     11  * permit persons to whom the Software is furnished to do so, subject to
     12  * the following conditions:
     13  *
     14  * The above copyright notice and this permission notice (including the
     15  * next paragraph) shall be included in all copies or substantial portions
     16  * of the Software.
     17  *
     18  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
     19  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
     20  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
     21  * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
     22  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
     23  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
     24  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
     25  *
     26  **************************************************************************/
     27 
     28 
     29 #include "main/glheader.h"
     30 #include "main/context.h"
     31 #include "main/macros.h"
     32 #include "main/enums.h"
     33 #include "main/fbobject.h"
     34 #include "main/dd.h"
     35 #include "main/state.h"
     36 
     37 #include "drivers/common/driverfuncs.h"
     38 
     39 #include "intel_screen.h"
     40 #include "intel_batchbuffer.h"
     41 #include "intel_mipmap_tree.h"
     42 #include "intel_fbo.h"
     43 #include "intel_buffers.h"
     44 
     45 #include "i830_context.h"
     46 #include "i830_reg.h"
     47 
     48 #define FILE_DEBUG_FLAG DEBUG_STATE
     49 
     50 static void
     51 i830StencilFuncSeparate(struct gl_context * ctx, GLenum face, GLenum func, GLint ref,
     52                         GLuint mask)
     53 {
     54    struct i830_context *i830 = i830_context(ctx);
     55    int test = intel_translate_compare_func(func);
     56 
     57    mask = mask & 0xff;
     58 
     59    DBG("%s : func: %s, ref : 0x%x, mask: 0x%x\n", __FUNCTION__,
     60        _mesa_lookup_enum_by_nr(func), ref, mask);
     61 
     62 
     63    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
     64    i830->state.Ctx[I830_CTXREG_STATE4] &= ~MODE4_ENABLE_STENCIL_TEST_MASK;
     65    i830->state.Ctx[I830_CTXREG_STATE4] |= (ENABLE_STENCIL_TEST_MASK |
     66                                            STENCIL_TEST_MASK(mask));
     67    i830->state.Ctx[I830_CTXREG_STENCILTST] &= ~(STENCIL_REF_VALUE_MASK |
     68                                                 ENABLE_STENCIL_TEST_FUNC_MASK);
     69    i830->state.Ctx[I830_CTXREG_STENCILTST] |= (ENABLE_STENCIL_REF_VALUE |
     70                                                ENABLE_STENCIL_TEST_FUNC |
     71                                                STENCIL_REF_VALUE(ref) |
     72                                                STENCIL_TEST_FUNC(test));
     73 }
     74 
     75 static void
     76 i830StencilMaskSeparate(struct gl_context * ctx, GLenum face, GLuint mask)
     77 {
     78    struct i830_context *i830 = i830_context(ctx);
     79 
     80    DBG("%s : mask 0x%x\n", __FUNCTION__, mask);
     81 
     82    mask = mask & 0xff;
     83 
     84    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
     85    i830->state.Ctx[I830_CTXREG_STATE4] &= ~MODE4_ENABLE_STENCIL_WRITE_MASK;
     86    i830->state.Ctx[I830_CTXREG_STATE4] |= (ENABLE_STENCIL_WRITE_MASK |
     87                                            STENCIL_WRITE_MASK(mask));
     88 }
     89 
     90 static void
     91 i830StencilOpSeparate(struct gl_context * ctx, GLenum face, GLenum fail, GLenum zfail,
     92                       GLenum zpass)
     93 {
     94    struct i830_context *i830 = i830_context(ctx);
     95    int fop, dfop, dpop;
     96 
     97    DBG("%s: fail : %s, zfail: %s, zpass : %s\n", __FUNCTION__,
     98        _mesa_lookup_enum_by_nr(fail),
     99        _mesa_lookup_enum_by_nr(zfail),
    100        _mesa_lookup_enum_by_nr(zpass));
    101 
    102    fop = 0;
    103    dfop = 0;
    104    dpop = 0;
    105 
    106    switch (fail) {
    107    case GL_KEEP:
    108       fop = STENCILOP_KEEP;
    109       break;
    110    case GL_ZERO:
    111       fop = STENCILOP_ZERO;
    112       break;
    113    case GL_REPLACE:
    114       fop = STENCILOP_REPLACE;
    115       break;
    116    case GL_INCR:
    117       fop = STENCILOP_INCRSAT;
    118       break;
    119    case GL_DECR:
    120       fop = STENCILOP_DECRSAT;
    121       break;
    122    case GL_INCR_WRAP:
    123       fop = STENCILOP_INCR;
    124       break;
    125    case GL_DECR_WRAP:
    126       fop = STENCILOP_DECR;
    127       break;
    128    case GL_INVERT:
    129       fop = STENCILOP_INVERT;
    130       break;
    131    default:
    132       break;
    133    }
    134    switch (zfail) {
    135    case GL_KEEP:
    136       dfop = STENCILOP_KEEP;
    137       break;
    138    case GL_ZERO:
    139       dfop = STENCILOP_ZERO;
    140       break;
    141    case GL_REPLACE:
    142       dfop = STENCILOP_REPLACE;
    143       break;
    144    case GL_INCR:
    145       dfop = STENCILOP_INCRSAT;
    146       break;
    147    case GL_DECR:
    148       dfop = STENCILOP_DECRSAT;
    149       break;
    150    case GL_INCR_WRAP:
    151       dfop = STENCILOP_INCR;
    152       break;
    153    case GL_DECR_WRAP:
    154       dfop = STENCILOP_DECR;
    155       break;
    156    case GL_INVERT:
    157       dfop = STENCILOP_INVERT;
    158       break;
    159    default:
    160       break;
    161    }
    162    switch (zpass) {
    163    case GL_KEEP:
    164       dpop = STENCILOP_KEEP;
    165       break;
    166    case GL_ZERO:
    167       dpop = STENCILOP_ZERO;
    168       break;
    169    case GL_REPLACE:
    170       dpop = STENCILOP_REPLACE;
    171       break;
    172    case GL_INCR:
    173       dpop = STENCILOP_INCRSAT;
    174       break;
    175    case GL_DECR:
    176       dpop = STENCILOP_DECRSAT;
    177       break;
    178    case GL_INCR_WRAP:
    179       dpop = STENCILOP_INCR;
    180       break;
    181    case GL_DECR_WRAP:
    182       dpop = STENCILOP_DECR;
    183       break;
    184    case GL_INVERT:
    185       dpop = STENCILOP_INVERT;
    186       break;
    187    default:
    188       break;
    189    }
    190 
    191 
    192    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    193    i830->state.Ctx[I830_CTXREG_STENCILTST] &= ~(STENCIL_OPS_MASK);
    194    i830->state.Ctx[I830_CTXREG_STENCILTST] |= (ENABLE_STENCIL_PARMS |
    195                                                STENCIL_FAIL_OP(fop) |
    196                                                STENCIL_PASS_DEPTH_FAIL_OP
    197                                                (dfop) |
    198                                                STENCIL_PASS_DEPTH_PASS_OP
    199                                                (dpop));
    200 }
    201 
    202 static void
    203 i830AlphaFunc(struct gl_context * ctx, GLenum func, GLfloat ref)
    204 {
    205    struct i830_context *i830 = i830_context(ctx);
    206    int test = intel_translate_compare_func(func);
    207    GLubyte refByte;
    208    GLuint refInt;
    209 
    210    UNCLAMPED_FLOAT_TO_UBYTE(refByte, ref);
    211    refInt = (GLuint) refByte;
    212 
    213    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    214    i830->state.Ctx[I830_CTXREG_STATE2] &= ~ALPHA_TEST_REF_MASK;
    215    i830->state.Ctx[I830_CTXREG_STATE2] |= (ENABLE_ALPHA_TEST_FUNC |
    216                                            ENABLE_ALPHA_REF_VALUE |
    217                                            ALPHA_TEST_FUNC(test) |
    218                                            ALPHA_REF_VALUE(refInt));
    219 }
    220 
    221 /**
    222  * Makes sure that the proper enables are set for LogicOp, Independant Alpha
    223  * Blend, and Blending.  It needs to be called from numerous places where we
    224  * could change the LogicOp or Independant Alpha Blend without subsequent
    225  * calls to glEnable.
    226  *
    227  * \todo
    228  * This function is substantially different from the old i830-specific driver.
    229  * I'm not sure which is correct.
    230  */
    231 static void
    232 i830EvalLogicOpBlendState(struct gl_context * ctx)
    233 {
    234    struct i830_context *i830 = i830_context(ctx);
    235 
    236    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    237 
    238    if (ctx->Color.ColorLogicOpEnabled) {
    239       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~(ENABLE_COLOR_BLEND |
    240                                                   ENABLE_LOGIC_OP_MASK);
    241       i830->state.Ctx[I830_CTXREG_ENABLES_1] |= (DISABLE_COLOR_BLEND |
    242                                                  ENABLE_LOGIC_OP);
    243    }
    244    else if (ctx->Color.BlendEnabled) {
    245       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~(ENABLE_COLOR_BLEND |
    246                                                   ENABLE_LOGIC_OP_MASK);
    247       i830->state.Ctx[I830_CTXREG_ENABLES_1] |= (ENABLE_COLOR_BLEND |
    248                                                  DISABLE_LOGIC_OP);
    249    }
    250    else {
    251       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~(ENABLE_COLOR_BLEND |
    252                                                   ENABLE_LOGIC_OP_MASK);
    253       i830->state.Ctx[I830_CTXREG_ENABLES_1] |= (DISABLE_COLOR_BLEND |
    254                                                  DISABLE_LOGIC_OP);
    255    }
    256 }
    257 
    258 static void
    259 i830BlendColor(struct gl_context * ctx, const GLfloat color[4])
    260 {
    261    struct i830_context *i830 = i830_context(ctx);
    262    GLubyte r, g, b, a;
    263 
    264    DBG("%s\n", __FUNCTION__);
    265 
    266    UNCLAMPED_FLOAT_TO_UBYTE(r, color[RCOMP]);
    267    UNCLAMPED_FLOAT_TO_UBYTE(g, color[GCOMP]);
    268    UNCLAMPED_FLOAT_TO_UBYTE(b, color[BCOMP]);
    269    UNCLAMPED_FLOAT_TO_UBYTE(a, color[ACOMP]);
    270 
    271    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    272    i830->state.Ctx[I830_CTXREG_BLENDCOLOR1] =
    273       (a << 24) | (r << 16) | (g << 8) | b;
    274 }
    275 
    276 /**
    277  * Sets both the blend equation (called "function" in i830 docs) and the
    278  * blend function (called "factor" in i830 docs).  This is done in a single
    279  * function because some blend equations (i.e., \c GL_MIN and \c GL_MAX)
    280  * change the interpretation of the blend function.
    281  */
    282 static void
    283 i830_set_blend_state(struct gl_context * ctx)
    284 {
    285    struct i830_context *i830 = i830_context(ctx);
    286    int funcA;
    287    int funcRGB;
    288    int eqnA;
    289    int eqnRGB;
    290    int iab;
    291    int s1;
    292 
    293 
    294    funcRGB =
    295       SRC_BLND_FACT(intel_translate_blend_factor(ctx->Color.Blend[0].SrcRGB))
    296       | DST_BLND_FACT(intel_translate_blend_factor(ctx->Color.Blend[0].DstRGB));
    297 
    298    switch (ctx->Color.Blend[0].EquationRGB) {
    299    case GL_FUNC_ADD:
    300       eqnRGB = BLENDFUNC_ADD;
    301       break;
    302    case GL_MIN:
    303       eqnRGB = BLENDFUNC_MIN;
    304       funcRGB = SRC_BLND_FACT(BLENDFACT_ONE) | DST_BLND_FACT(BLENDFACT_ONE);
    305       break;
    306    case GL_MAX:
    307       eqnRGB = BLENDFUNC_MAX;
    308       funcRGB = SRC_BLND_FACT(BLENDFACT_ONE) | DST_BLND_FACT(BLENDFACT_ONE);
    309       break;
    310    case GL_FUNC_SUBTRACT:
    311       eqnRGB = BLENDFUNC_SUB;
    312       break;
    313    case GL_FUNC_REVERSE_SUBTRACT:
    314       eqnRGB = BLENDFUNC_RVRSE_SUB;
    315       break;
    316    default:
    317       fprintf(stderr, "[%s:%u] Invalid RGB blend equation (0x%04x).\n",
    318               __FUNCTION__, __LINE__, ctx->Color.Blend[0].EquationRGB);
    319       return;
    320    }
    321 
    322 
    323    funcA = SRC_ABLEND_FACT(intel_translate_blend_factor(ctx->Color.Blend[0].SrcA))
    324       | DST_ABLEND_FACT(intel_translate_blend_factor(ctx->Color.Blend[0].DstA));
    325 
    326    switch (ctx->Color.Blend[0].EquationA) {
    327    case GL_FUNC_ADD:
    328       eqnA = BLENDFUNC_ADD;
    329       break;
    330    case GL_MIN:
    331       eqnA = BLENDFUNC_MIN;
    332       funcA = SRC_BLND_FACT(BLENDFACT_ONE) | DST_BLND_FACT(BLENDFACT_ONE);
    333       break;
    334    case GL_MAX:
    335       eqnA = BLENDFUNC_MAX;
    336       funcA = SRC_BLND_FACT(BLENDFACT_ONE) | DST_BLND_FACT(BLENDFACT_ONE);
    337       break;
    338    case GL_FUNC_SUBTRACT:
    339       eqnA = BLENDFUNC_SUB;
    340       break;
    341    case GL_FUNC_REVERSE_SUBTRACT:
    342       eqnA = BLENDFUNC_RVRSE_SUB;
    343       break;
    344    default:
    345       fprintf(stderr, "[%s:%u] Invalid alpha blend equation (0x%04x).\n",
    346               __FUNCTION__, __LINE__, ctx->Color.Blend[0].EquationA);
    347       return;
    348    }
    349 
    350    iab = eqnA | funcA
    351       | _3DSTATE_INDPT_ALPHA_BLEND_CMD
    352       | ENABLE_SRC_ABLEND_FACTOR | ENABLE_DST_ABLEND_FACTOR
    353       | ENABLE_ALPHA_BLENDFUNC;
    354    s1 = eqnRGB | funcRGB
    355       | _3DSTATE_MODES_1_CMD
    356       | ENABLE_SRC_BLND_FACTOR | ENABLE_DST_BLND_FACTOR
    357       | ENABLE_COLR_BLND_FUNC;
    358 
    359    if ((eqnA | funcA) != (eqnRGB | funcRGB))
    360       iab |= ENABLE_INDPT_ALPHA_BLEND;
    361    else
    362       iab |= DISABLE_INDPT_ALPHA_BLEND;
    363 
    364    if (iab != i830->state.Ctx[I830_CTXREG_IALPHAB] ||
    365        s1 != i830->state.Ctx[I830_CTXREG_STATE1]) {
    366       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    367       i830->state.Ctx[I830_CTXREG_IALPHAB] = iab;
    368       i830->state.Ctx[I830_CTXREG_STATE1] = s1;
    369    }
    370 
    371    /* This will catch a logicop blend equation.  It will also ensure
    372     * independant alpha blend is really in the correct state (either enabled
    373     * or disabled) if blending is already enabled.
    374     */
    375 
    376    i830EvalLogicOpBlendState(ctx);
    377 
    378    if (0) {
    379       fprintf(stderr,
    380               "[%s:%u] STATE1: 0x%08x IALPHAB: 0x%08x blend is %sabled\n",
    381               __FUNCTION__, __LINE__, i830->state.Ctx[I830_CTXREG_STATE1],
    382               i830->state.Ctx[I830_CTXREG_IALPHAB],
    383               (ctx->Color.BlendEnabled) ? "en" : "dis");
    384    }
    385 }
    386 
    387 
    388 static void
    389 i830BlendEquationSeparate(struct gl_context * ctx, GLenum modeRGB, GLenum modeA)
    390 {
    391    DBG("%s -> %s, %s\n", __FUNCTION__,
    392        _mesa_lookup_enum_by_nr(modeRGB),
    393        _mesa_lookup_enum_by_nr(modeA));
    394 
    395    (void) modeRGB;
    396    (void) modeA;
    397    i830_set_blend_state(ctx);
    398 }
    399 
    400 
    401 static void
    402 i830BlendFuncSeparate(struct gl_context * ctx, GLenum sfactorRGB,
    403                       GLenum dfactorRGB, GLenum sfactorA, GLenum dfactorA)
    404 {
    405    DBG("%s -> RGB(%s, %s) A(%s, %s)\n", __FUNCTION__,
    406        _mesa_lookup_enum_by_nr(sfactorRGB),
    407        _mesa_lookup_enum_by_nr(dfactorRGB),
    408        _mesa_lookup_enum_by_nr(sfactorA),
    409        _mesa_lookup_enum_by_nr(dfactorA));
    410 
    411    (void) sfactorRGB;
    412    (void) dfactorRGB;
    413    (void) sfactorA;
    414    (void) dfactorA;
    415    i830_set_blend_state(ctx);
    416 }
    417 
    418 
    419 
    420 static void
    421 i830DepthFunc(struct gl_context * ctx, GLenum func)
    422 {
    423    struct i830_context *i830 = i830_context(ctx);
    424    int test = intel_translate_compare_func(func);
    425 
    426    DBG("%s\n", __FUNCTION__);
    427 
    428    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    429    i830->state.Ctx[I830_CTXREG_STATE3] &= ~DEPTH_TEST_FUNC_MASK;
    430    i830->state.Ctx[I830_CTXREG_STATE3] |= (ENABLE_DEPTH_TEST_FUNC |
    431                                            DEPTH_TEST_FUNC(test));
    432 }
    433 
    434 static void
    435 i830DepthMask(struct gl_context * ctx, GLboolean flag)
    436 {
    437    struct i830_context *i830 = i830_context(ctx);
    438 
    439    DBG("%s flag (%d)\n", __FUNCTION__, flag);
    440 
    441    if (!ctx->DrawBuffer || !ctx->DrawBuffer->Visual.depthBits)
    442       flag = false;
    443 
    444    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    445 
    446    i830->state.Ctx[I830_CTXREG_ENABLES_2] &= ~ENABLE_DIS_DEPTH_WRITE_MASK;
    447 
    448    if (flag && ctx->Depth.Test)
    449       i830->state.Ctx[I830_CTXREG_ENABLES_2] |= ENABLE_DEPTH_WRITE;
    450    else
    451       i830->state.Ctx[I830_CTXREG_ENABLES_2] |= DISABLE_DEPTH_WRITE;
    452 }
    453 
    454 /** Called from ctx->Driver.Viewport() */
    455 static void
    456 i830Viewport(struct gl_context * ctx,
    457               GLint x, GLint y, GLsizei width, GLsizei height)
    458 {
    459    intelCalcViewport(ctx);
    460 }
    461 
    462 
    463 /** Called from ctx->Driver.DepthRange() */
    464 static void
    465 i830DepthRange(struct gl_context * ctx, GLclampd nearval, GLclampd farval)
    466 {
    467    intelCalcViewport(ctx);
    468 }
    469 
    470 /* =============================================================
    471  * Polygon stipple
    472  *
    473  * The i830 supports a 4x4 stipple natively, GL wants 32x32.
    474  * Fortunately stipple is usually a repeating pattern.
    475  */
    476 static void
    477 i830PolygonStipple(struct gl_context * ctx, const GLubyte * mask)
    478 {
    479    struct i830_context *i830 = i830_context(ctx);
    480    const GLubyte *m;
    481    GLubyte p[4];
    482    int i, j, k;
    483    int active = (ctx->Polygon.StippleFlag &&
    484                  i830->intel.reduced_primitive == GL_TRIANGLES);
    485    GLuint newMask;
    486 
    487    if (active) {
    488       I830_STATECHANGE(i830, I830_UPLOAD_STIPPLE);
    489       i830->state.Stipple[I830_STPREG_ST1] &= ~ST1_ENABLE;
    490    }
    491 
    492    /* Use the already unpacked stipple data from the context rather than the
    493     * uninterpreted mask passed in.
    494     */
    495    mask = (const GLubyte *)ctx->PolygonStipple;
    496    m = mask;
    497 
    498    p[0] = mask[12] & 0xf;
    499    p[0] |= p[0] << 4;
    500    p[1] = mask[8] & 0xf;
    501    p[1] |= p[1] << 4;
    502    p[2] = mask[4] & 0xf;
    503    p[2] |= p[2] << 4;
    504    p[3] = mask[0] & 0xf;
    505    p[3] |= p[3] << 4;
    506 
    507    for (k = 0; k < 8; k++)
    508       for (j = 3; j >= 0; j--)
    509          for (i = 0; i < 4; i++, m++)
    510             if (*m != p[j]) {
    511                i830->intel.hw_stipple = 0;
    512                return;
    513             }
    514 
    515    newMask = (((p[0] & 0xf) << 0) |
    516               ((p[1] & 0xf) << 4) |
    517               ((p[2] & 0xf) << 8) | ((p[3] & 0xf) << 12));
    518 
    519 
    520    if (newMask == 0xffff || newMask == 0x0) {
    521       /* this is needed to make conform pass */
    522       i830->intel.hw_stipple = 0;
    523       return;
    524    }
    525 
    526    i830->state.Stipple[I830_STPREG_ST1] &= ~0xffff;
    527    i830->state.Stipple[I830_STPREG_ST1] |= newMask;
    528    i830->intel.hw_stipple = 1;
    529 
    530    if (active)
    531       i830->state.Stipple[I830_STPREG_ST1] |= ST1_ENABLE;
    532 }
    533 
    534 
    535 /* =============================================================
    536  * Hardware clipping
    537  */
    538 static void
    539 i830Scissor(struct gl_context * ctx, GLint x, GLint y, GLsizei w, GLsizei h)
    540 {
    541    struct i830_context *i830 = i830_context(ctx);
    542    int x1, y1, x2, y2;
    543 
    544    if (!ctx->DrawBuffer)
    545       return;
    546 
    547    DBG("%s %d,%d %dx%d\n", __FUNCTION__, x, y, w, h);
    548 
    549    if (_mesa_is_winsys_fbo(ctx->DrawBuffer)) {
    550       x1 = x;
    551       y1 = ctx->DrawBuffer->Height - (y + h);
    552       x2 = x + w - 1;
    553       y2 = y1 + h - 1;
    554       DBG("%s %d..%d,%d..%d (inverted)\n", __FUNCTION__, x1, x2, y1, y2);
    555    }
    556    else {
    557       /* FBO - not inverted
    558        */
    559       x1 = x;
    560       y1 = y;
    561       x2 = x + w - 1;
    562       y2 = y + h - 1;
    563       DBG("%s %d..%d,%d..%d (not inverted)\n", __FUNCTION__, x1, x2, y1, y2);
    564    }
    565 
    566    x1 = CLAMP(x1, 0, ctx->DrawBuffer->Width - 1);
    567    y1 = CLAMP(y1, 0, ctx->DrawBuffer->Height - 1);
    568    x2 = CLAMP(x2, 0, ctx->DrawBuffer->Width - 1);
    569    y2 = CLAMP(y2, 0, ctx->DrawBuffer->Height - 1);
    570 
    571    DBG("%s %d..%d,%d..%d (clamped)\n", __FUNCTION__, x1, x2, y1, y2);
    572 
    573    I830_STATECHANGE(i830, I830_UPLOAD_BUFFERS);
    574    i830->state.Buffer[I830_DESTREG_SR1] = (y1 << 16) | (x1 & 0xffff);
    575    i830->state.Buffer[I830_DESTREG_SR2] = (y2 << 16) | (x2 & 0xffff);
    576 }
    577 
    578 static void
    579 i830LogicOp(struct gl_context * ctx, GLenum opcode)
    580 {
    581    struct i830_context *i830 = i830_context(ctx);
    582    int tmp = intel_translate_logic_op(opcode);
    583 
    584    DBG("%s\n", __FUNCTION__);
    585 
    586    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    587    i830->state.Ctx[I830_CTXREG_STATE4] &= ~LOGICOP_MASK;
    588    i830->state.Ctx[I830_CTXREG_STATE4] |= LOGIC_OP_FUNC(tmp);
    589 }
    590 
    591 
    592 
    593 static void
    594 i830CullFaceFrontFace(struct gl_context * ctx, GLenum unused)
    595 {
    596    struct i830_context *i830 = i830_context(ctx);
    597    GLuint mode;
    598 
    599    DBG("%s\n", __FUNCTION__);
    600 
    601    if (!ctx->Polygon.CullFlag) {
    602       mode = CULLMODE_NONE;
    603    }
    604    else if (ctx->Polygon.CullFaceMode != GL_FRONT_AND_BACK) {
    605       mode = CULLMODE_CW;
    606 
    607       if (ctx->Polygon.CullFaceMode == GL_FRONT)
    608          mode ^= (CULLMODE_CW ^ CULLMODE_CCW);
    609       if (ctx->Polygon.FrontFace != GL_CCW)
    610          mode ^= (CULLMODE_CW ^ CULLMODE_CCW);
    611    }
    612    else {
    613       mode = CULLMODE_BOTH;
    614    }
    615 
    616    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    617    i830->state.Ctx[I830_CTXREG_STATE3] &= ~CULLMODE_MASK;
    618    i830->state.Ctx[I830_CTXREG_STATE3] |= ENABLE_CULL_MODE | mode;
    619 }
    620 
    621 static void
    622 i830LineWidth(struct gl_context * ctx, GLfloat widthf)
    623 {
    624    struct i830_context *i830 = i830_context(ctx);
    625    int width;
    626    int state5;
    627 
    628    DBG("%s\n", __FUNCTION__);
    629 
    630    width = (int) (widthf * 2);
    631    width = CLAMP(width, 1, 15);
    632 
    633    state5 = i830->state.Ctx[I830_CTXREG_STATE5] & ~FIXED_LINE_WIDTH_MASK;
    634    state5 |= (ENABLE_FIXED_LINE_WIDTH | FIXED_LINE_WIDTH(width));
    635 
    636    if (state5 != i830->state.Ctx[I830_CTXREG_STATE5]) {
    637       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    638       i830->state.Ctx[I830_CTXREG_STATE5] = state5;
    639    }
    640 }
    641 
    642 static void
    643 i830PointSize(struct gl_context * ctx, GLfloat size)
    644 {
    645    struct i830_context *i830 = i830_context(ctx);
    646    GLint point_size = (int) size;
    647 
    648    DBG("%s\n", __FUNCTION__);
    649 
    650    point_size = CLAMP(point_size, 1, 256);
    651    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    652    i830->state.Ctx[I830_CTXREG_STATE5] &= ~FIXED_POINT_WIDTH_MASK;
    653    i830->state.Ctx[I830_CTXREG_STATE5] |= (ENABLE_FIXED_POINT_WIDTH |
    654                                            FIXED_POINT_WIDTH(point_size));
    655 }
    656 
    657 
    658 /* =============================================================
    659  * Color masks
    660  */
    661 
    662 static void
    663 i830ColorMask(struct gl_context * ctx,
    664               GLboolean r, GLboolean g, GLboolean b, GLboolean a)
    665 {
    666    struct i830_context *i830 = i830_context(ctx);
    667    GLuint tmp = 0;
    668 
    669    DBG("%s r(%d) g(%d) b(%d) a(%d)\n", __FUNCTION__, r, g, b, a);
    670 
    671    tmp = ((i830->state.Ctx[I830_CTXREG_ENABLES_2] & ~WRITEMASK_MASK) |
    672           ENABLE_COLOR_MASK |
    673           ENABLE_COLOR_WRITE |
    674           ((!r) << WRITEMASK_RED_SHIFT) |
    675           ((!g) << WRITEMASK_GREEN_SHIFT) |
    676           ((!b) << WRITEMASK_BLUE_SHIFT) | ((!a) << WRITEMASK_ALPHA_SHIFT));
    677 
    678    if (tmp != i830->state.Ctx[I830_CTXREG_ENABLES_2]) {
    679       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    680       i830->state.Ctx[I830_CTXREG_ENABLES_2] = tmp;
    681    }
    682 }
    683 
    684 static void
    685 update_specular(struct gl_context * ctx)
    686 {
    687    struct i830_context *i830 = i830_context(ctx);
    688 
    689    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    690    i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~ENABLE_SPEC_ADD_MASK;
    691 
    692    if (_mesa_need_secondary_color(ctx))
    693       i830->state.Ctx[I830_CTXREG_ENABLES_1] |= ENABLE_SPEC_ADD;
    694    else
    695       i830->state.Ctx[I830_CTXREG_ENABLES_1] |= DISABLE_SPEC_ADD;
    696 }
    697 
    698 static void
    699 i830LightModelfv(struct gl_context * ctx, GLenum pname, const GLfloat * param)
    700 {
    701    DBG("%s\n", __FUNCTION__);
    702 
    703    if (pname == GL_LIGHT_MODEL_COLOR_CONTROL) {
    704       update_specular(ctx);
    705    }
    706 }
    707 
    708 /* In Mesa 3.5 we can reliably do native flatshading.
    709  */
    710 static void
    711 i830ShadeModel(struct gl_context * ctx, GLenum mode)
    712 {
    713    struct i830_context *i830 = i830_context(ctx);
    714    I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    715 
    716 
    717 #define SHADE_MODE_MASK ((1<<10)|(1<<8)|(1<<6)|(1<<4))
    718 
    719    i830->state.Ctx[I830_CTXREG_STATE3] &= ~SHADE_MODE_MASK;
    720 
    721    if (mode == GL_FLAT) {
    722       i830->state.Ctx[I830_CTXREG_STATE3] |=
    723          (ALPHA_SHADE_MODE(SHADE_MODE_FLAT) | FOG_SHADE_MODE(SHADE_MODE_FLAT)
    724           | SPEC_SHADE_MODE(SHADE_MODE_FLAT) |
    725           COLOR_SHADE_MODE(SHADE_MODE_FLAT));
    726    }
    727    else {
    728       i830->state.Ctx[I830_CTXREG_STATE3] |=
    729          (ALPHA_SHADE_MODE(SHADE_MODE_LINEAR) |
    730           FOG_SHADE_MODE(SHADE_MODE_LINEAR) |
    731           SPEC_SHADE_MODE(SHADE_MODE_LINEAR) |
    732           COLOR_SHADE_MODE(SHADE_MODE_LINEAR));
    733    }
    734 }
    735 
    736 /* =============================================================
    737  * Fog
    738  */
    739 static void
    740 i830Fogfv(struct gl_context * ctx, GLenum pname, const GLfloat * param)
    741 {
    742    struct i830_context *i830 = i830_context(ctx);
    743 
    744    DBG("%s\n", __FUNCTION__);
    745 
    746    if (pname == GL_FOG_COLOR) {
    747       GLuint color = (((GLubyte) (ctx->Fog.Color[0] * 255.0F) << 16) |
    748                       ((GLubyte) (ctx->Fog.Color[1] * 255.0F) << 8) |
    749                       ((GLubyte) (ctx->Fog.Color[2] * 255.0F) << 0));
    750 
    751       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    752       i830->state.Ctx[I830_CTXREG_FOGCOLOR] =
    753          (_3DSTATE_FOG_COLOR_CMD | color);
    754    }
    755 }
    756 
    757 /* =============================================================
    758  */
    759 
    760 static void
    761 i830Enable(struct gl_context * ctx, GLenum cap, GLboolean state)
    762 {
    763    struct i830_context *i830 = i830_context(ctx);
    764 
    765    switch (cap) {
    766    case GL_LIGHTING:
    767    case GL_COLOR_SUM:
    768       update_specular(ctx);
    769       break;
    770 
    771    case GL_ALPHA_TEST:
    772       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    773       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~ENABLE_DIS_ALPHA_TEST_MASK;
    774       if (state)
    775          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= ENABLE_ALPHA_TEST;
    776       else
    777          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= DISABLE_ALPHA_TEST;
    778 
    779       break;
    780 
    781    case GL_BLEND:
    782       i830EvalLogicOpBlendState(ctx);
    783       break;
    784 
    785    case GL_COLOR_LOGIC_OP:
    786       i830EvalLogicOpBlendState(ctx);
    787 
    788       /* Logicop doesn't seem to work at 16bpp:
    789        */
    790       if (i830->intel.ctx.Visual.rgbBits == 16)
    791          FALLBACK(&i830->intel, I830_FALLBACK_LOGICOP, state);
    792       break;
    793 
    794    case GL_DITHER:
    795       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    796       i830->state.Ctx[I830_CTXREG_ENABLES_2] &= ~ENABLE_DITHER;
    797 
    798       if (state)
    799          i830->state.Ctx[I830_CTXREG_ENABLES_2] |= ENABLE_DITHER;
    800       else
    801          i830->state.Ctx[I830_CTXREG_ENABLES_2] |= DISABLE_DITHER;
    802       break;
    803 
    804    case GL_DEPTH_TEST:
    805       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    806       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~ENABLE_DIS_DEPTH_TEST_MASK;
    807 
    808       if (!ctx->DrawBuffer || !ctx->DrawBuffer->Visual.depthBits)
    809 	 state = false;
    810 
    811       if (state)
    812          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= ENABLE_DEPTH_TEST;
    813       else
    814          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= DISABLE_DEPTH_TEST;
    815 
    816       /* Also turn off depth writes when GL_DEPTH_TEST is disabled:
    817        */
    818       i830DepthMask(ctx, ctx->Depth.Mask);
    819       break;
    820 
    821    case GL_SCISSOR_TEST:
    822       I830_STATECHANGE(i830, I830_UPLOAD_BUFFERS);
    823 
    824       if (state)
    825          i830->state.Buffer[I830_DESTREG_SENABLE] =
    826             (_3DSTATE_SCISSOR_ENABLE_CMD | ENABLE_SCISSOR_RECT);
    827       else
    828          i830->state.Buffer[I830_DESTREG_SENABLE] =
    829             (_3DSTATE_SCISSOR_ENABLE_CMD | DISABLE_SCISSOR_RECT);
    830 
    831       break;
    832 
    833    case GL_LINE_SMOOTH:
    834       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    835 
    836       i830->state.Ctx[I830_CTXREG_AA] &= ~AA_LINE_ENABLE;
    837       if (state)
    838          i830->state.Ctx[I830_CTXREG_AA] |= AA_LINE_ENABLE;
    839       else
    840          i830->state.Ctx[I830_CTXREG_AA] |= AA_LINE_DISABLE;
    841       break;
    842 
    843    case GL_FOG:
    844       I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    845       i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~ENABLE_DIS_FOG_MASK;
    846       if (state)
    847          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= ENABLE_FOG;
    848       else
    849          i830->state.Ctx[I830_CTXREG_ENABLES_1] |= DISABLE_FOG;
    850       break;
    851 
    852    case GL_CULL_FACE:
    853       i830CullFaceFrontFace(ctx, 0);
    854       break;
    855 
    856    case GL_TEXTURE_2D:
    857       break;
    858 
    859    case GL_STENCIL_TEST:
    860       {
    861          bool hw_stencil = false;
    862          if (ctx->DrawBuffer) {
    863             struct intel_renderbuffer *irbStencil
    864                = intel_get_renderbuffer(ctx->DrawBuffer, BUFFER_STENCIL);
    865             hw_stencil = (irbStencil && irbStencil->mt);
    866          }
    867          if (hw_stencil) {
    868             I830_STATECHANGE(i830, I830_UPLOAD_CTX);
    869 
    870             if (state) {
    871                i830->state.Ctx[I830_CTXREG_ENABLES_1] |= ENABLE_STENCIL_TEST;
    872                i830->state.Ctx[I830_CTXREG_ENABLES_2] |= ENABLE_STENCIL_WRITE;
    873             }
    874             else {
    875                i830->state.Ctx[I830_CTXREG_ENABLES_1] &= ~ENABLE_STENCIL_TEST;
    876                i830->state.Ctx[I830_CTXREG_ENABLES_2] &=
    877                   ~ENABLE_STENCIL_WRITE;
    878                i830->state.Ctx[I830_CTXREG_ENABLES_1] |= DISABLE_STENCIL_TEST;
    879                i830->state.Ctx[I830_CTXREG_ENABLES_2] |=
    880                   DISABLE_STENCIL_WRITE;
    881             }
    882          }
    883          else {
    884             FALLBACK(&i830->intel, I830_FALLBACK_STENCIL, state);
    885          }
    886       }
    887       break;
    888 
    889    case GL_POLYGON_STIPPLE:
    890       /* The stipple command worked on my 855GM box, but not my 845G.
    891        * I'll do more testing later to find out exactly which hardware
    892        * supports it.  Disabled for now.
    893        */
    894       if (i830->intel.hw_stipple &&
    895           i830->intel.reduced_primitive == GL_TRIANGLES) {
    896          I830_STATECHANGE(i830, I830_UPLOAD_STIPPLE);
    897          i830->state.Stipple[I830_STPREG_ST1] &= ~ST1_ENABLE;
    898          if (state)
    899             i830->state.Stipple[I830_STPREG_ST1] |= ST1_ENABLE;
    900       }
    901       break;
    902 
    903    default:
    904       ;
    905    }
    906 }
    907 
    908 
    909 static void
    910 i830_init_packets(struct i830_context *i830)
    911 {
    912    /* Zero all state */
    913    memset(&i830->state, 0, sizeof(i830->state));
    914 
    915    /* Set default blend state */
    916    i830->state.TexBlend[0][0] = (_3DSTATE_MAP_BLEND_OP_CMD(0) |
    917                                  TEXPIPE_COLOR |
    918                                  ENABLE_TEXOUTPUT_WRT_SEL |
    919                                  TEXOP_OUTPUT_CURRENT |
    920                                  DISABLE_TEX_CNTRL_STAGE |
    921                                  TEXOP_SCALE_1X |
    922                                  TEXOP_MODIFY_PARMS |
    923                                  TEXOP_LAST_STAGE | TEXBLENDOP_ARG1);
    924    i830->state.TexBlend[0][1] = (_3DSTATE_MAP_BLEND_OP_CMD(0) |
    925                                  TEXPIPE_ALPHA |
    926                                  ENABLE_TEXOUTPUT_WRT_SEL |
    927                                  TEXOP_OUTPUT_CURRENT |
    928                                  TEXOP_SCALE_1X |
    929                                  TEXOP_MODIFY_PARMS | TEXBLENDOP_ARG1);
    930    i830->state.TexBlend[0][2] = (_3DSTATE_MAP_BLEND_ARG_CMD(0) |
    931                                  TEXPIPE_COLOR |
    932                                  TEXBLEND_ARG1 |
    933                                  TEXBLENDARG_MODIFY_PARMS |
    934                                  TEXBLENDARG_DIFFUSE);
    935    i830->state.TexBlend[0][3] = (_3DSTATE_MAP_BLEND_ARG_CMD(0) |
    936                                  TEXPIPE_ALPHA |
    937                                  TEXBLEND_ARG1 |
    938                                  TEXBLENDARG_MODIFY_PARMS |
    939                                  TEXBLENDARG_DIFFUSE);
    940 
    941    i830->state.TexBlendWordsUsed[0] = 4;
    942 
    943 
    944    i830->state.Ctx[I830_CTXREG_VF] = 0;
    945    i830->state.Ctx[I830_CTXREG_VF2] = 0;
    946 
    947    i830->state.Ctx[I830_CTXREG_AA] = (_3DSTATE_AA_CMD |
    948                                       AA_LINE_ECAAR_WIDTH_ENABLE |
    949                                       AA_LINE_ECAAR_WIDTH_1_0 |
    950                                       AA_LINE_REGION_WIDTH_ENABLE |
    951                                       AA_LINE_REGION_WIDTH_1_0 |
    952                                       AA_LINE_DISABLE);
    953 
    954    i830->state.Ctx[I830_CTXREG_ENABLES_1] = (_3DSTATE_ENABLES_1_CMD |
    955                                              DISABLE_LOGIC_OP |
    956                                              DISABLE_STENCIL_TEST |
    957                                              DISABLE_DEPTH_BIAS |
    958                                              DISABLE_SPEC_ADD |
    959                                              DISABLE_FOG |
    960                                              DISABLE_ALPHA_TEST |
    961                                              DISABLE_COLOR_BLEND |
    962                                              DISABLE_DEPTH_TEST);
    963 
    964 #if 000                         /* XXX all the stencil enable state is set in i830Enable(), right? */
    965    if (i830->intel.hw_stencil) {
    966       i830->state.Ctx[I830_CTXREG_ENABLES_2] = (_3DSTATE_ENABLES_2_CMD |
    967                                                 ENABLE_STENCIL_WRITE |
    968                                                 ENABLE_TEX_CACHE |
    969                                                 ENABLE_DITHER |
    970                                                 ENABLE_COLOR_MASK |
    971                                                 /* set no color comps disabled */
    972                                                 ENABLE_COLOR_WRITE |
    973                                                 ENABLE_DEPTH_WRITE);
    974    }
    975    else
    976 #endif
    977    {
    978       i830->state.Ctx[I830_CTXREG_ENABLES_2] = (_3DSTATE_ENABLES_2_CMD |
    979                                                 DISABLE_STENCIL_WRITE |
    980                                                 ENABLE_TEX_CACHE |
    981                                                 ENABLE_DITHER |
    982                                                 ENABLE_COLOR_MASK |
    983                                                 /* set no color comps disabled */
    984                                                 ENABLE_COLOR_WRITE |
    985                                                 ENABLE_DEPTH_WRITE);
    986    }
    987 
    988    i830->state.Ctx[I830_CTXREG_STATE1] = (_3DSTATE_MODES_1_CMD |
    989                                           ENABLE_COLR_BLND_FUNC |
    990                                           BLENDFUNC_ADD |
    991                                           ENABLE_SRC_BLND_FACTOR |
    992                                           SRC_BLND_FACT(BLENDFACT_ONE) |
    993                                           ENABLE_DST_BLND_FACTOR |
    994                                           DST_BLND_FACT(BLENDFACT_ZERO));
    995 
    996    i830->state.Ctx[I830_CTXREG_STATE2] = (_3DSTATE_MODES_2_CMD |
    997                                           ENABLE_GLOBAL_DEPTH_BIAS |
    998                                           GLOBAL_DEPTH_BIAS(0) |
    999                                           ENABLE_ALPHA_TEST_FUNC |
   1000                                           ALPHA_TEST_FUNC(COMPAREFUNC_ALWAYS)
   1001                                           | ALPHA_REF_VALUE(0));
   1002 
   1003    i830->state.Ctx[I830_CTXREG_STATE3] = (_3DSTATE_MODES_3_CMD |
   1004                                           ENABLE_DEPTH_TEST_FUNC |
   1005                                           DEPTH_TEST_FUNC(COMPAREFUNC_LESS) |
   1006                                           ENABLE_ALPHA_SHADE_MODE |
   1007                                           ALPHA_SHADE_MODE(SHADE_MODE_LINEAR)
   1008                                           | ENABLE_FOG_SHADE_MODE |
   1009                                           FOG_SHADE_MODE(SHADE_MODE_LINEAR) |
   1010                                           ENABLE_SPEC_SHADE_MODE |
   1011                                           SPEC_SHADE_MODE(SHADE_MODE_LINEAR) |
   1012                                           ENABLE_COLOR_SHADE_MODE |
   1013                                           COLOR_SHADE_MODE(SHADE_MODE_LINEAR)
   1014                                           | ENABLE_CULL_MODE | CULLMODE_NONE);
   1015 
   1016    i830->state.Ctx[I830_CTXREG_STATE4] = (_3DSTATE_MODES_4_CMD |
   1017                                           ENABLE_LOGIC_OP_FUNC |
   1018                                           LOGIC_OP_FUNC(LOGICOP_COPY) |
   1019                                           ENABLE_STENCIL_TEST_MASK |
   1020                                           STENCIL_TEST_MASK(0xff) |
   1021                                           ENABLE_STENCIL_WRITE_MASK |
   1022                                           STENCIL_WRITE_MASK(0xff));
   1023 
   1024    i830->state.Ctx[I830_CTXREG_STENCILTST] = (_3DSTATE_STENCIL_TEST_CMD |
   1025                                               ENABLE_STENCIL_PARMS |
   1026                                               STENCIL_FAIL_OP(STENCILOP_KEEP)
   1027                                               |
   1028                                               STENCIL_PASS_DEPTH_FAIL_OP
   1029                                               (STENCILOP_KEEP) |
   1030                                               STENCIL_PASS_DEPTH_PASS_OP
   1031                                               (STENCILOP_KEEP) |
   1032                                               ENABLE_STENCIL_TEST_FUNC |
   1033                                               STENCIL_TEST_FUNC
   1034                                               (COMPAREFUNC_ALWAYS) |
   1035                                               ENABLE_STENCIL_REF_VALUE |
   1036                                               STENCIL_REF_VALUE(0));
   1037 
   1038    i830->state.Ctx[I830_CTXREG_STATE5] = (_3DSTATE_MODES_5_CMD | FLUSH_TEXTURE_CACHE | ENABLE_SPRITE_POINT_TEX | SPRITE_POINT_TEX_OFF | ENABLE_FIXED_LINE_WIDTH | FIXED_LINE_WIDTH(0x2) |       /* 1.0 */
   1039                                           ENABLE_FIXED_POINT_WIDTH |
   1040                                           FIXED_POINT_WIDTH(1));
   1041 
   1042    i830->state.Ctx[I830_CTXREG_IALPHAB] = (_3DSTATE_INDPT_ALPHA_BLEND_CMD |
   1043                                            DISABLE_INDPT_ALPHA_BLEND |
   1044                                            ENABLE_ALPHA_BLENDFUNC |
   1045                                            ABLENDFUNC_ADD);
   1046 
   1047    i830->state.Ctx[I830_CTXREG_FOGCOLOR] = (_3DSTATE_FOG_COLOR_CMD |
   1048                                             FOG_COLOR_RED(0) |
   1049                                             FOG_COLOR_GREEN(0) |
   1050                                             FOG_COLOR_BLUE(0));
   1051 
   1052    i830->state.Ctx[I830_CTXREG_BLENDCOLOR0] = _3DSTATE_CONST_BLEND_COLOR_CMD;
   1053    i830->state.Ctx[I830_CTXREG_BLENDCOLOR1] = 0;
   1054 
   1055    i830->state.Ctx[I830_CTXREG_MCSB0] = _3DSTATE_MAP_COORD_SETBIND_CMD;
   1056    i830->state.Ctx[I830_CTXREG_MCSB1] = (TEXBIND_SET3(TEXCOORDSRC_VTXSET_3) |
   1057                                          TEXBIND_SET2(TEXCOORDSRC_VTXSET_2) |
   1058                                          TEXBIND_SET1(TEXCOORDSRC_VTXSET_1) |
   1059                                          TEXBIND_SET0(TEXCOORDSRC_VTXSET_0));
   1060 
   1061    i830->state.RasterRules[I830_RASTER_RULES] = (_3DSTATE_RASTER_RULES_CMD |
   1062 						 ENABLE_POINT_RASTER_RULE |
   1063 						 OGL_POINT_RASTER_RULE |
   1064 						 ENABLE_LINE_STRIP_PROVOKE_VRTX |
   1065 						 ENABLE_TRI_FAN_PROVOKE_VRTX |
   1066 						 ENABLE_TRI_STRIP_PROVOKE_VRTX |
   1067 						 LINE_STRIP_PROVOKE_VRTX(1) |
   1068 						 TRI_FAN_PROVOKE_VRTX(2) |
   1069 						 TRI_STRIP_PROVOKE_VRTX(2));
   1070 
   1071 
   1072    i830->state.Stipple[I830_STPREG_ST0] = _3DSTATE_STIPPLE;
   1073 
   1074    i830->state.Buffer[I830_DESTREG_DV0] = _3DSTATE_DST_BUF_VARS_CMD;
   1075    i830->state.Buffer[I830_DESTREG_SENABLE] = (_3DSTATE_SCISSOR_ENABLE_CMD |
   1076                                                DISABLE_SCISSOR_RECT);
   1077    i830->state.Buffer[I830_DESTREG_SR0] = _3DSTATE_SCISSOR_RECT_0_CMD;
   1078    i830->state.Buffer[I830_DESTREG_SR1] = 0;
   1079    i830->state.Buffer[I830_DESTREG_SR2] = 0;
   1080 }
   1081 
   1082 void
   1083 i830_update_provoking_vertex(struct gl_context * ctx)
   1084 {
   1085    struct i830_context *i830 = i830_context(ctx);
   1086 
   1087    I830_STATECHANGE(i830, I830_UPLOAD_RASTER_RULES);
   1088    i830->state.RasterRules[I830_RASTER_RULES] &= ~(LINE_STRIP_PROVOKE_VRTX_MASK |
   1089 						   TRI_FAN_PROVOKE_VRTX_MASK |
   1090 						   TRI_STRIP_PROVOKE_VRTX_MASK);
   1091 
   1092    /* _NEW_LIGHT */
   1093    if (ctx->Light.ProvokingVertex == GL_LAST_VERTEX_CONVENTION) {
   1094       i830->state.RasterRules[I830_RASTER_RULES] |= (LINE_STRIP_PROVOKE_VRTX(1) |
   1095 						     TRI_FAN_PROVOKE_VRTX(2) |
   1096 						     TRI_STRIP_PROVOKE_VRTX(2));
   1097    } else {
   1098       i830->state.RasterRules[I830_RASTER_RULES] |= (LINE_STRIP_PROVOKE_VRTX(0) |
   1099 						     TRI_FAN_PROVOKE_VRTX(1) |
   1100 						     TRI_STRIP_PROVOKE_VRTX(0));
   1101     }
   1102 }
   1103 
   1104 /* Fallback to swrast for select and feedback.
   1105  */
   1106 static void
   1107 i830RenderMode(struct gl_context *ctx, GLenum mode)
   1108 {
   1109    struct intel_context *intel = intel_context(ctx);
   1110    FALLBACK(intel, INTEL_FALLBACK_RENDERMODE, (mode != GL_RENDER));
   1111 }
   1112 
   1113 void
   1114 i830InitStateFuncs(struct dd_function_table *functions)
   1115 {
   1116    functions->AlphaFunc = i830AlphaFunc;
   1117    functions->BlendColor = i830BlendColor;
   1118    functions->BlendEquationSeparate = i830BlendEquationSeparate;
   1119    functions->BlendFuncSeparate = i830BlendFuncSeparate;
   1120    functions->ColorMask = i830ColorMask;
   1121    functions->CullFace = i830CullFaceFrontFace;
   1122    functions->DepthFunc = i830DepthFunc;
   1123    functions->DepthMask = i830DepthMask;
   1124    functions->Enable = i830Enable;
   1125    functions->Fogfv = i830Fogfv;
   1126    functions->FrontFace = i830CullFaceFrontFace;
   1127    functions->LightModelfv = i830LightModelfv;
   1128    functions->LineWidth = i830LineWidth;
   1129    functions->LogicOpcode = i830LogicOp;
   1130    functions->PointSize = i830PointSize;
   1131    functions->PolygonStipple = i830PolygonStipple;
   1132    functions->RenderMode = i830RenderMode;
   1133    functions->Scissor = i830Scissor;
   1134    functions->ShadeModel = i830ShadeModel;
   1135    functions->StencilFuncSeparate = i830StencilFuncSeparate;
   1136    functions->StencilMaskSeparate = i830StencilMaskSeparate;
   1137    functions->StencilOpSeparate = i830StencilOpSeparate;
   1138    functions->DepthRange = i830DepthRange;
   1139    functions->Viewport = i830Viewport;
   1140 }
   1141 
   1142 void
   1143 i830InitState(struct i830_context *i830)
   1144 {
   1145    struct gl_context *ctx = &i830->intel.ctx;
   1146 
   1147    i830_init_packets(i830);
   1148 
   1149    _mesa_init_driver_state(ctx);
   1150 
   1151    i830->state.emitted = 0;
   1152    i830->state.active = (I830_UPLOAD_INVARIENT |
   1153                          I830_UPLOAD_RASTER_RULES |
   1154                          I830_UPLOAD_TEXBLEND(0) |
   1155                          I830_UPLOAD_STIPPLE |
   1156                          I830_UPLOAD_CTX | I830_UPLOAD_BUFFERS);
   1157 }
   1158