mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2025-12-27 19:10:14 +01:00
Cache the i915 sampler state.
This commit is contained in:
parent
cc2629f591
commit
742e32a40b
3 changed files with 156 additions and 151 deletions
|
|
@ -141,6 +141,11 @@ struct i915_rasterizer_state {
|
|||
union { float f; unsigned u; } ds[2];
|
||||
};
|
||||
|
||||
struct i915_sampler_state {
|
||||
unsigned state[3];
|
||||
const struct pipe_sampler_state *templ;
|
||||
};
|
||||
|
||||
struct i915_context
|
||||
{
|
||||
struct pipe_context pipe;
|
||||
|
|
@ -150,7 +155,7 @@ struct i915_context
|
|||
/* The most recent drawing state as set by the driver:
|
||||
*/
|
||||
const struct i915_blend_state *blend;
|
||||
const struct pipe_sampler_state *sampler[PIPE_MAX_SAMPLERS];
|
||||
const struct i915_sampler_state *sampler[PIPE_MAX_SAMPLERS];
|
||||
const struct i915_depth_stencil_state *depth_stencil;
|
||||
const struct i915_rasterizer_state *rasterizer;
|
||||
const struct pipe_shader_state *fs;
|
||||
|
|
|
|||
|
|
@ -38,9 +38,79 @@
|
|||
#include "i915_state.h"
|
||||
#include "i915_state_inlines.h"
|
||||
|
||||
|
||||
/* The i915 (and related graphics cores) do not support GL_CLAMP. The
|
||||
* Intel drivers for "other operating systems" implement GL_CLAMP as
|
||||
* GL_CLAMP_TO_EDGE, so the same is done here.
|
||||
*/
|
||||
static unsigned
|
||||
translate_wrap_mode(unsigned wrap)
|
||||
{
|
||||
switch (wrap) {
|
||||
case PIPE_TEX_WRAP_REPEAT:
|
||||
return TEXCOORDMODE_WRAP;
|
||||
case PIPE_TEX_WRAP_CLAMP:
|
||||
return TEXCOORDMODE_CLAMP_EDGE; /* not quite correct */
|
||||
case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
|
||||
return TEXCOORDMODE_CLAMP_EDGE;
|
||||
case PIPE_TEX_WRAP_CLAMP_TO_BORDER:
|
||||
return TEXCOORDMODE_CLAMP_BORDER;
|
||||
// case PIPE_TEX_WRAP_MIRRORED_REPEAT:
|
||||
// return TEXCOORDMODE_MIRROR;
|
||||
default:
|
||||
return TEXCOORDMODE_WRAP;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_img_filter( unsigned filter )
|
||||
{
|
||||
switch (filter) {
|
||||
case PIPE_TEX_FILTER_NEAREST:
|
||||
return FILTER_NEAREST;
|
||||
case PIPE_TEX_FILTER_LINEAR:
|
||||
return FILTER_LINEAR;
|
||||
default:
|
||||
assert(0);
|
||||
return FILTER_NEAREST;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_mip_filter( unsigned filter )
|
||||
{
|
||||
switch (filter) {
|
||||
case PIPE_TEX_MIPFILTER_NONE:
|
||||
return MIPFILTER_NONE;
|
||||
case PIPE_TEX_MIPFILTER_NEAREST:
|
||||
return MIPFILTER_NEAREST;
|
||||
case PIPE_TEX_FILTER_LINEAR:
|
||||
return MIPFILTER_LINEAR;
|
||||
default:
|
||||
assert(0);
|
||||
return MIPFILTER_NONE;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_compare_func(unsigned func)
|
||||
{
|
||||
switch (func) {
|
||||
case PIPE_FUNC_NEVER:
|
||||
case PIPE_FUNC_LESS:
|
||||
case PIPE_FUNC_EQUAL:
|
||||
case PIPE_FUNC_LEQUAL:
|
||||
case PIPE_FUNC_GREATER:
|
||||
case PIPE_FUNC_NOTEQUAL:
|
||||
case PIPE_FUNC_GEQUAL:
|
||||
case PIPE_FUNC_ALWAYS:
|
||||
return 0;
|
||||
default:
|
||||
assert(0);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* None of this state is actually used for anything yet.
|
||||
*/
|
||||
|
||||
static void *
|
||||
i915_create_blend_state(struct pipe_context *pipe,
|
||||
const struct pipe_blend_state *blend)
|
||||
|
|
@ -147,7 +217,59 @@ static void *
|
|||
i915_create_sampler_state(struct pipe_context *pipe,
|
||||
const struct pipe_sampler_state *sampler)
|
||||
{
|
||||
return 0;
|
||||
struct i915_sampler_state *cso = calloc(1, sizeof(struct i915_sampler_state));
|
||||
cso->templ = sampler;
|
||||
|
||||
const unsigned ws = sampler->wrap_s;
|
||||
const unsigned wt = sampler->wrap_t;
|
||||
const unsigned wr = sampler->wrap_r;
|
||||
unsigned minFilt, magFilt;
|
||||
unsigned mipFilt;
|
||||
|
||||
mipFilt = translate_mip_filter(sampler->min_mip_filter);
|
||||
if (sampler->max_anisotropy > 1.0) {
|
||||
minFilt = FILTER_ANISOTROPIC;
|
||||
magFilt = FILTER_ANISOTROPIC;
|
||||
}
|
||||
else {
|
||||
minFilt = translate_img_filter( sampler->min_img_filter );
|
||||
magFilt = translate_img_filter( sampler->mag_img_filter );
|
||||
}
|
||||
|
||||
{
|
||||
int b = sampler->lod_bias * 16.0;
|
||||
b = CLAMP(b, -256, 255);
|
||||
cso->state[0] |= ((b << SS2_LOD_BIAS_SHIFT) & SS2_LOD_BIAS_MASK);
|
||||
}
|
||||
|
||||
/* Shadow:
|
||||
*/
|
||||
if (sampler->compare_mode == PIPE_TEX_COMPARE_R_TO_TEXTURE)
|
||||
{
|
||||
cso->state[0] |= (SS2_SHADOW_ENABLE |
|
||||
translate_compare_func(sampler->compare_func));
|
||||
|
||||
minFilt = FILTER_4X4_FLAT;
|
||||
magFilt = FILTER_4X4_FLAT;
|
||||
}
|
||||
|
||||
cso->state[0] |= ((minFilt << SS2_MIN_FILTER_SHIFT) |
|
||||
(mipFilt << SS2_MIP_FILTER_SHIFT) |
|
||||
(magFilt << SS2_MAG_FILTER_SHIFT));
|
||||
|
||||
cso->state[1] |=
|
||||
((translate_wrap_mode(ws) << SS3_TCX_ADDR_MODE_SHIFT) |
|
||||
(translate_wrap_mode(wt) << SS3_TCY_ADDR_MODE_SHIFT) |
|
||||
(translate_wrap_mode(wr) << SS3_TCZ_ADDR_MODE_SHIFT));
|
||||
|
||||
{
|
||||
ubyte r = float_to_ubyte(sampler->border_color[0]);
|
||||
ubyte g = float_to_ubyte(sampler->border_color[1]);
|
||||
ubyte b = float_to_ubyte(sampler->border_color[2]);
|
||||
ubyte a = float_to_ubyte(sampler->border_color[3]);
|
||||
cso->state[2] = I915PACKCOLOR8888(r, g, b, a);
|
||||
}
|
||||
return cso;
|
||||
}
|
||||
|
||||
static void i915_bind_sampler_state(struct pipe_context *pipe,
|
||||
|
|
@ -156,7 +278,7 @@ static void i915_bind_sampler_state(struct pipe_context *pipe,
|
|||
struct i915_context *i915 = i915_context(pipe);
|
||||
|
||||
assert(unit < PIPE_MAX_SAMPLERS);
|
||||
i915->sampler[unit] = (const struct pipe_sampler_state *)sampler;
|
||||
i915->sampler[unit] = (const struct i915_sampler_state*)sampler;
|
||||
|
||||
i915->dirty |= I915_NEW_SAMPLER;
|
||||
}
|
||||
|
|
@ -164,6 +286,7 @@ static void i915_bind_sampler_state(struct pipe_context *pipe,
|
|||
static void i915_delete_sampler_state(struct pipe_context *pipe,
|
||||
void *sampler)
|
||||
{
|
||||
free(sampler);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -42,81 +42,6 @@
|
|||
#include "i915_state.h"
|
||||
//#include "i915_cache.h"
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/* The i915 (and related graphics cores) do not support GL_CLAMP. The
|
||||
* Intel drivers for "other operating systems" implement GL_CLAMP as
|
||||
* GL_CLAMP_TO_EDGE, so the same is done here.
|
||||
*/
|
||||
static unsigned
|
||||
translate_wrap_mode(unsigned wrap)
|
||||
{
|
||||
switch (wrap) {
|
||||
case PIPE_TEX_WRAP_REPEAT:
|
||||
return TEXCOORDMODE_WRAP;
|
||||
case PIPE_TEX_WRAP_CLAMP:
|
||||
return TEXCOORDMODE_CLAMP_EDGE; /* not quite correct */
|
||||
case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
|
||||
return TEXCOORDMODE_CLAMP_EDGE;
|
||||
case PIPE_TEX_WRAP_CLAMP_TO_BORDER:
|
||||
return TEXCOORDMODE_CLAMP_BORDER;
|
||||
// case PIPE_TEX_WRAP_MIRRORED_REPEAT:
|
||||
// return TEXCOORDMODE_MIRROR;
|
||||
default:
|
||||
return TEXCOORDMODE_WRAP;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_img_filter( unsigned filter )
|
||||
{
|
||||
switch (filter) {
|
||||
case PIPE_TEX_FILTER_NEAREST:
|
||||
return FILTER_NEAREST;
|
||||
case PIPE_TEX_FILTER_LINEAR:
|
||||
return FILTER_LINEAR;
|
||||
default:
|
||||
assert(0);
|
||||
return FILTER_NEAREST;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_mip_filter( unsigned filter )
|
||||
{
|
||||
switch (filter) {
|
||||
case PIPE_TEX_MIPFILTER_NONE:
|
||||
return MIPFILTER_NONE;
|
||||
case PIPE_TEX_MIPFILTER_NEAREST:
|
||||
return MIPFILTER_NEAREST;
|
||||
case PIPE_TEX_FILTER_LINEAR:
|
||||
return MIPFILTER_LINEAR;
|
||||
default:
|
||||
assert(0);
|
||||
return MIPFILTER_NONE;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned translate_compare_func(unsigned func)
|
||||
{
|
||||
switch (func) {
|
||||
case PIPE_FUNC_NEVER:
|
||||
case PIPE_FUNC_LESS:
|
||||
case PIPE_FUNC_EQUAL:
|
||||
case PIPE_FUNC_LEQUAL:
|
||||
case PIPE_FUNC_GREATER:
|
||||
case PIPE_FUNC_NOTEQUAL:
|
||||
case PIPE_FUNC_GEQUAL:
|
||||
case PIPE_FUNC_ALWAYS:
|
||||
return 0;
|
||||
default:
|
||||
assert(0);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static uint
|
||||
bitcount(uint k)
|
||||
{
|
||||
|
|
@ -153,60 +78,21 @@ is_power_of_two_texture(const struct pipe_mipmap_tree *mt)
|
|||
*/
|
||||
static void update_sampler(struct i915_context *i915,
|
||||
uint unit,
|
||||
const struct pipe_sampler_state *sampler,
|
||||
const struct i915_sampler_state *sampler,
|
||||
const struct pipe_mipmap_tree *mt,
|
||||
unsigned state[3] )
|
||||
{
|
||||
const unsigned ws = sampler->wrap_s;
|
||||
const unsigned wt = sampler->wrap_t;
|
||||
const unsigned wr = sampler->wrap_r;
|
||||
|
||||
/* Need to do this after updating the maps, which call the
|
||||
* intel_finalize_mipmap_tree and hence can update firstLevel:
|
||||
*/
|
||||
unsigned minFilt, magFilt;
|
||||
unsigned mipFilt;
|
||||
|
||||
state[0] = state[1] = state[2] = 0;
|
||||
|
||||
mipFilt = translate_mip_filter( sampler->min_mip_filter );
|
||||
|
||||
if (sampler->max_anisotropy > 1.0) {
|
||||
minFilt = FILTER_ANISOTROPIC;
|
||||
magFilt = FILTER_ANISOTROPIC;
|
||||
}
|
||||
else {
|
||||
minFilt = translate_img_filter( sampler->min_img_filter );
|
||||
magFilt = translate_img_filter( sampler->mag_img_filter );
|
||||
}
|
||||
|
||||
{
|
||||
int b = sampler->lod_bias * 16.0;
|
||||
b = CLAMP(b, -256, 255);
|
||||
state[0] |= ((b << SS2_LOD_BIAS_SHIFT) & SS2_LOD_BIAS_MASK);
|
||||
}
|
||||
state[0] = sampler->state[0];
|
||||
state[1] = sampler->state[1];
|
||||
state[2] = sampler->state[2];
|
||||
|
||||
if (mt->format == PIPE_FORMAT_YCBCR ||
|
||||
mt->format == PIPE_FORMAT_YCBCR_REV)
|
||||
state[0] |= SS2_COLORSPACE_CONVERSION;
|
||||
|
||||
|
||||
/* Shadow:
|
||||
*/
|
||||
if (sampler->compare_mode == PIPE_TEX_COMPARE_R_TO_TEXTURE)
|
||||
{
|
||||
state[0] |= (SS2_SHADOW_ENABLE |
|
||||
translate_compare_func(sampler->compare_func));
|
||||
|
||||
minFilt = FILTER_4X4_FLAT;
|
||||
magFilt = FILTER_4X4_FLAT;
|
||||
}
|
||||
|
||||
state[0] |= ((minFilt << SS2_MIN_FILTER_SHIFT) |
|
||||
(mipFilt << SS2_MIP_FILTER_SHIFT) |
|
||||
(magFilt << SS2_MAG_FILTER_SHIFT));
|
||||
|
||||
|
||||
/* 3D textures don't seem to respect the border color.
|
||||
* Fallback if there's ever a danger that they might refer to
|
||||
* it.
|
||||
|
|
@ -217,45 +103,36 @@ static void update_sampler(struct i915_context *i915,
|
|||
* XXX: Check if this is true on i945.
|
||||
* XXX: Check if this bug got fixed in release silicon.
|
||||
*/
|
||||
if (mt->target == PIPE_TEXTURE_3D &&
|
||||
(sampler->min_img_filter != PIPE_TEX_FILTER_NEAREST ||
|
||||
sampler->mag_img_filter != PIPE_TEX_FILTER_NEAREST) &&
|
||||
(ws == PIPE_TEX_WRAP_CLAMP ||
|
||||
wt == PIPE_TEX_WRAP_CLAMP ||
|
||||
wr == PIPE_TEX_WRAP_CLAMP ||
|
||||
ws == PIPE_TEX_WRAP_CLAMP_TO_BORDER ||
|
||||
wt == PIPE_TEX_WRAP_CLAMP_TO_BORDER ||
|
||||
wr == PIPE_TEX_WRAP_CLAMP_TO_BORDER)) {
|
||||
#if 0
|
||||
if (i915->strict_conformance) {
|
||||
assert(0);
|
||||
/* sampler->fallback = true; */
|
||||
/* TODO */
|
||||
{
|
||||
const unsigned ws = sampler->templ->wrap_s;
|
||||
const unsigned wt = sampler->templ->wrap_t;
|
||||
const unsigned wr = sampler->templ->wrap_r;
|
||||
if (mt->target == PIPE_TEXTURE_3D &&
|
||||
(sampler->templ->min_img_filter != PIPE_TEX_FILTER_NEAREST ||
|
||||
sampler->templ->mag_img_filter != PIPE_TEX_FILTER_NEAREST) &&
|
||||
(ws == PIPE_TEX_WRAP_CLAMP ||
|
||||
wt == PIPE_TEX_WRAP_CLAMP ||
|
||||
wr == PIPE_TEX_WRAP_CLAMP ||
|
||||
ws == PIPE_TEX_WRAP_CLAMP_TO_BORDER ||
|
||||
wt == PIPE_TEX_WRAP_CLAMP_TO_BORDER ||
|
||||
wr == PIPE_TEX_WRAP_CLAMP_TO_BORDER)) {
|
||||
if (i915->strict_conformance) {
|
||||
assert(0);
|
||||
/* sampler->fallback = true; */
|
||||
/* TODO */
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
state[1] =
|
||||
((translate_wrap_mode(ws) << SS3_TCX_ADDR_MODE_SHIFT) |
|
||||
(translate_wrap_mode(wt) << SS3_TCY_ADDR_MODE_SHIFT) |
|
||||
(translate_wrap_mode(wr) << SS3_TCZ_ADDR_MODE_SHIFT) |
|
||||
(unit << SS3_TEXTUREMAP_INDEX_SHIFT));
|
||||
state[1] |= (unit << SS3_TEXTUREMAP_INDEX_SHIFT);
|
||||
|
||||
if (is_power_of_two_texture(mt)) {
|
||||
state[1] |= SS3_NORMALIZED_COORDS;
|
||||
}
|
||||
|
||||
{
|
||||
ubyte r = float_to_ubyte(sampler->border_color[0]);
|
||||
ubyte g = float_to_ubyte(sampler->border_color[1]);
|
||||
ubyte b = float_to_ubyte(sampler->border_color[2]);
|
||||
ubyte a = float_to_ubyte(sampler->border_color[3]);
|
||||
state[2] = I915PACKCOLOR8888(r, g, b, a);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void i915_update_samplers( struct i915_context *i915 )
|
||||
{
|
||||
uint unit;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue