i915: Add support for EXT_stencil_two_side and ATI_separate_stencil.
Passes tests/stencil_twoside and glean/stencil2.
This commit is contained in:
@@ -75,6 +75,8 @@ i915InvalidateState(GLcontext * ctx, GLuint new_state)
|
||||
|
||||
if (new_state & (_NEW_FOG | _NEW_HINT | _NEW_PROGRAM | _NEW_PROGRAM_CONSTANTS))
|
||||
i915_update_fog(ctx);
|
||||
if (new_state & (_NEW_STENCIL | _NEW_BUFFERS | _NEW_POLYGON))
|
||||
i915_update_stencil(ctx);
|
||||
}
|
||||
|
||||
|
||||
|
@@ -82,7 +82,9 @@
|
||||
#define I915_CTXREG_IAB 6
|
||||
#define I915_CTXREG_BLENDCOLOR0 7
|
||||
#define I915_CTXREG_BLENDCOLOR1 8
|
||||
#define I915_CTX_SETUP_SIZE 9
|
||||
#define I915_CTXREG_BF_STENCIL_OPS 9
|
||||
#define I915_CTXREG_BF_STENCIL_MASKS 10
|
||||
#define I915_CTX_SETUP_SIZE 11
|
||||
|
||||
#define I915_FOGREG_COLOR 0
|
||||
#define I915_FOGREG_MODE0 1
|
||||
@@ -321,6 +323,7 @@ extern void i915_print_ureg(const char *msg, GLuint ureg);
|
||||
extern void i915InitStateFunctions(struct dd_function_table *functions);
|
||||
extern void i915InitState(struct i915_context *i915);
|
||||
extern void i915_update_fog(GLcontext * ctx);
|
||||
extern void i915_update_stencil(GLcontext * ctx);
|
||||
|
||||
|
||||
/*======================================================================
|
||||
|
@@ -86,8 +86,10 @@
|
||||
#define BFM_ENABLE_STENCIL_WRITE_MASK (1<<16)
|
||||
#define BFM_STENCIL_TEST_MASK_SHIFT 8
|
||||
#define BFM_STENCIL_TEST_MASK_MASK (0xff<<8)
|
||||
#define BFM_STENCIL_TEST_MASK(x) (((x)&0xff) << 8)
|
||||
#define BFM_STENCIL_WRITE_MASK_SHIFT 0
|
||||
#define BFM_STENCIL_WRITE_MASK_MASK (0xff<<0)
|
||||
#define BFM_STENCIL_WRITE_MASK(x) ((x)&0xff)
|
||||
|
||||
|
||||
|
||||
|
@@ -48,73 +48,119 @@
|
||||
|
||||
#define FILE_DEBUG_FLAG DEBUG_STATE
|
||||
|
||||
void
|
||||
i915_update_stencil(GLcontext * ctx)
|
||||
{
|
||||
struct i915_context *i915 = I915_CONTEXT(ctx);
|
||||
GLuint front_ref, front_writemask, front_mask;
|
||||
GLenum front_func, front_fail, front_pass_z_fail, front_pass_z_pass;
|
||||
GLuint back_ref, back_writemask, back_mask;
|
||||
GLenum back_func, back_fail, back_pass_z_fail, back_pass_z_pass;
|
||||
|
||||
I915_STATECHANGE(i915, I915_UPLOAD_CTX);
|
||||
|
||||
/* The 915 considers CW to be "front" for two-sided stencil, so choose
|
||||
* appropriately.
|
||||
*/
|
||||
/* _NEW_POLYGON | _NEW_STENCIL */
|
||||
if (ctx->Polygon.FrontFace == GL_CW) {
|
||||
front_ref = ctx->Stencil.Ref[0];
|
||||
front_mask = ctx->Stencil.ValueMask[0];
|
||||
front_writemask = ctx->Stencil.WriteMask[0];
|
||||
front_func = ctx->Stencil.Function[0];
|
||||
front_fail = ctx->Stencil.FailFunc[0];
|
||||
front_pass_z_fail = ctx->Stencil.ZFailFunc[0];
|
||||
front_pass_z_pass = ctx->Stencil.ZPassFunc[0];
|
||||
back_ref = ctx->Stencil.Ref[ctx->Stencil._BackFace];
|
||||
back_mask = ctx->Stencil.ValueMask[ctx->Stencil._BackFace];
|
||||
back_writemask = ctx->Stencil.WriteMask[ctx->Stencil._BackFace];
|
||||
back_func = ctx->Stencil.Function[ctx->Stencil._BackFace];
|
||||
back_fail = ctx->Stencil.FailFunc[ctx->Stencil._BackFace];
|
||||
back_pass_z_fail = ctx->Stencil.ZFailFunc[ctx->Stencil._BackFace];
|
||||
back_pass_z_pass = ctx->Stencil.ZPassFunc[ctx->Stencil._BackFace];
|
||||
} else {
|
||||
front_ref = ctx->Stencil.Ref[ctx->Stencil._BackFace];
|
||||
front_mask = ctx->Stencil.ValueMask[ctx->Stencil._BackFace];
|
||||
front_writemask = ctx->Stencil.WriteMask[ctx->Stencil._BackFace];
|
||||
front_func = ctx->Stencil.Function[ctx->Stencil._BackFace];
|
||||
front_fail = ctx->Stencil.FailFunc[ctx->Stencil._BackFace];
|
||||
front_pass_z_fail = ctx->Stencil.ZFailFunc[ctx->Stencil._BackFace];
|
||||
front_pass_z_pass = ctx->Stencil.ZPassFunc[ctx->Stencil._BackFace];
|
||||
back_ref = ctx->Stencil.Ref[0];
|
||||
back_mask = ctx->Stencil.ValueMask[0];
|
||||
back_writemask = ctx->Stencil.WriteMask[0];
|
||||
back_func = ctx->Stencil.Function[0];
|
||||
back_fail = ctx->Stencil.FailFunc[0];
|
||||
back_pass_z_fail = ctx->Stencil.ZFailFunc[0];
|
||||
back_pass_z_pass = ctx->Stencil.ZPassFunc[0];
|
||||
}
|
||||
|
||||
/* Set front state. */
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] &= ~(MODE4_ENABLE_STENCIL_TEST_MASK |
|
||||
MODE4_ENABLE_STENCIL_WRITE_MASK);
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] |= (ENABLE_STENCIL_TEST_MASK |
|
||||
ENABLE_STENCIL_WRITE_MASK |
|
||||
STENCIL_TEST_MASK(front_mask) |
|
||||
STENCIL_WRITE_MASK(front_writemask));
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] &= ~(S5_STENCIL_REF_MASK |
|
||||
S5_STENCIL_TEST_FUNC_MASK |
|
||||
S5_STENCIL_FAIL_MASK |
|
||||
S5_STENCIL_PASS_Z_FAIL_MASK |
|
||||
S5_STENCIL_PASS_Z_PASS_MASK);
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] |=
|
||||
(front_ref << S5_STENCIL_REF_SHIFT) |
|
||||
(intel_translate_compare_func(front_func) << S5_STENCIL_TEST_FUNC_SHIFT) |
|
||||
(intel_translate_stencil_op(front_fail) << S5_STENCIL_FAIL_SHIFT) |
|
||||
(intel_translate_stencil_op(front_pass_z_fail) <<
|
||||
S5_STENCIL_PASS_Z_FAIL_SHIFT) |
|
||||
(intel_translate_stencil_op(front_pass_z_pass) <<
|
||||
S5_STENCIL_PASS_Z_PASS_SHIFT);
|
||||
|
||||
/* Set back state if different from front. */
|
||||
if (ctx->Stencil._TestTwoSide) {
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_OPS] &=
|
||||
~(BFO_STENCIL_REF_MASK |
|
||||
BFO_STENCIL_TEST_MASK |
|
||||
BFO_STENCIL_FAIL_MASK |
|
||||
BFO_STENCIL_PASS_Z_FAIL_MASK |
|
||||
BFO_STENCIL_PASS_Z_PASS_MASK);
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_OPS] |= BFO_STENCIL_TWO_SIDE |
|
||||
(back_ref << BFO_STENCIL_REF_SHIFT) |
|
||||
(intel_translate_compare_func(back_func) << BFO_STENCIL_TEST_SHIFT) |
|
||||
(intel_translate_stencil_op(back_fail) << BFO_STENCIL_FAIL_SHIFT) |
|
||||
(intel_translate_stencil_op(back_pass_z_fail) <<
|
||||
BFO_STENCIL_PASS_Z_FAIL_SHIFT) |
|
||||
(intel_translate_stencil_op(back_pass_z_pass) <<
|
||||
BFO_STENCIL_PASS_Z_PASS_SHIFT);
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_MASKS] &=
|
||||
~(BFM_STENCIL_TEST_MASK_MASK |
|
||||
BFM_STENCIL_WRITE_MASK_MASK);
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_MASKS] |=
|
||||
BFM_STENCIL_TEST_MASK(back_mask) |
|
||||
BFM_STENCIL_WRITE_MASK(back_writemask);
|
||||
} else {
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_OPS] &= ~BFO_STENCIL_TWO_SIDE;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
i915StencilFuncSeparate(GLcontext * ctx, GLenum face, GLenum func, GLint ref,
|
||||
GLuint mask)
|
||||
{
|
||||
struct i915_context *i915 = I915_CONTEXT(ctx);
|
||||
int test = intel_translate_compare_func(func);
|
||||
|
||||
mask = mask & 0xff;
|
||||
|
||||
DBG("%s : func: %s, ref : 0x%x, mask: 0x%x\n", __FUNCTION__,
|
||||
_mesa_lookup_enum_by_nr(func), ref, mask);
|
||||
|
||||
|
||||
I915_STATECHANGE(i915, I915_UPLOAD_CTX);
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] &= ~MODE4_ENABLE_STENCIL_TEST_MASK;
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] |= (ENABLE_STENCIL_TEST_MASK |
|
||||
STENCIL_TEST_MASK(mask));
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] &= ~(S5_STENCIL_REF_MASK |
|
||||
S5_STENCIL_TEST_FUNC_MASK);
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] |= ((ref << S5_STENCIL_REF_SHIFT) |
|
||||
(test <<
|
||||
S5_STENCIL_TEST_FUNC_SHIFT));
|
||||
}
|
||||
|
||||
static void
|
||||
i915StencilMaskSeparate(GLcontext * ctx, GLenum face, GLuint mask)
|
||||
{
|
||||
struct i915_context *i915 = I915_CONTEXT(ctx);
|
||||
|
||||
DBG("%s : mask 0x%x\n", __FUNCTION__, mask);
|
||||
|
||||
mask = mask & 0xff;
|
||||
|
||||
I915_STATECHANGE(i915, I915_UPLOAD_CTX);
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] &= ~MODE4_ENABLE_STENCIL_WRITE_MASK;
|
||||
i915->state.Ctx[I915_CTXREG_STATE4] |= (ENABLE_STENCIL_WRITE_MASK |
|
||||
STENCIL_WRITE_MASK(mask));
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
i915StencilOpSeparate(GLcontext * ctx, GLenum face, GLenum fail, GLenum zfail,
|
||||
GLenum zpass)
|
||||
{
|
||||
struct i915_context *i915 = I915_CONTEXT(ctx);
|
||||
int fop = intel_translate_stencil_op(fail);
|
||||
int dfop = intel_translate_stencil_op(zfail);
|
||||
int dpop = intel_translate_stencil_op(zpass);
|
||||
|
||||
|
||||
DBG("%s: fail : %s, zfail: %s, zpass : %s\n", __FUNCTION__,
|
||||
_mesa_lookup_enum_by_nr(fail),
|
||||
_mesa_lookup_enum_by_nr(zfail), _mesa_lookup_enum_by_nr(zpass));
|
||||
|
||||
I915_STATECHANGE(i915, I915_UPLOAD_CTX);
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] &= ~(S5_STENCIL_FAIL_MASK |
|
||||
S5_STENCIL_PASS_Z_FAIL_MASK |
|
||||
S5_STENCIL_PASS_Z_PASS_MASK);
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_LIS5] |= ((fop << S5_STENCIL_FAIL_SHIFT) |
|
||||
(dfop <<
|
||||
S5_STENCIL_PASS_Z_FAIL_SHIFT) |
|
||||
(dpop <<
|
||||
S5_STENCIL_PASS_Z_PASS_SHIFT));
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -945,6 +991,17 @@ i915_init_packets(struct i915_context *i915)
|
||||
_3DSTATE_CONST_BLEND_COLOR_CMD;
|
||||
i915->state.Ctx[I915_CTXREG_BLENDCOLOR1] = 0;
|
||||
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_MASKS] =
|
||||
_3DSTATE_BACKFACE_STENCIL_MASKS |
|
||||
BFM_ENABLE_STENCIL_TEST_MASK |
|
||||
BFM_ENABLE_STENCIL_WRITE_MASK |
|
||||
(0xff << BFM_STENCIL_WRITE_MASK_SHIFT) |
|
||||
(0xff << BFM_STENCIL_TEST_MASK_SHIFT);
|
||||
i915->state.Ctx[I915_CTXREG_BF_STENCIL_OPS] =
|
||||
_3DSTATE_BACKFACE_STENCIL_OPS |
|
||||
BFO_ENABLE_STENCIL_REF |
|
||||
BFO_ENABLE_STENCIL_FUNCS |
|
||||
BFO_ENABLE_STENCIL_TWO_SIDE;
|
||||
}
|
||||
|
||||
{
|
||||
|
@@ -176,7 +176,7 @@ i915_emit_invarient_state(struct intel_context *intel)
|
||||
{
|
||||
BATCH_LOCALS;
|
||||
|
||||
BEGIN_BATCH(20, IGNORE_CLIPRECTS);
|
||||
BEGIN_BATCH(18, IGNORE_CLIPRECTS);
|
||||
|
||||
OUT_BATCH(_3DSTATE_AA_CMD |
|
||||
AA_LINE_ECAAR_WIDTH_ENABLE |
|
||||
@@ -225,11 +225,6 @@ i915_emit_invarient_state(struct intel_context *intel)
|
||||
OUT_BATCH(_3DSTATE_LOAD_INDIRECT | 0); /* disable indirect state */
|
||||
OUT_BATCH(0);
|
||||
|
||||
|
||||
/* Don't support twosided stencil yet */
|
||||
OUT_BATCH(_3DSTATE_BACKFACE_STENCIL_OPS | BFO_ENABLE_STENCIL_TWO_SIDE | 0);
|
||||
OUT_BATCH(0);
|
||||
|
||||
ADVANCE_BATCH();
|
||||
}
|
||||
|
||||
|
@@ -120,8 +120,10 @@ static const struct dri_extension i915_extensions[] = {
|
||||
{ "GL_ARB_fragment_program", NULL },
|
||||
{ "GL_ARB_shadow", NULL },
|
||||
{ "GL_ARB_texture_non_power_of_two", NULL },
|
||||
{ "GL_ATI_separate_stencil", GL_ATI_separate_stencil_functions },
|
||||
{ "GL_ATI_texture_env_combine3", NULL },
|
||||
{ "GL_EXT_shadow_funcs", NULL },
|
||||
{ "GL_EXT_stencil_two_side", GL_EXT_stencil_two_side_functions },
|
||||
{ "GL_NV_texture_env_combine4", NULL },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
Reference in New Issue
Block a user