[Mesa-dev] [PATCH 1/2] gallivm: split sampler and texture state
Jose Fonseca
jfonseca at vmware.com
Mon Jan 28 04:19:16 PST 2013
Reviewed-by: Jose Fonseca <jfonseca at vmware.com>
Looks good to me.
Minor nit: there is some spurious white space change (removal of trailing white-space on untouched pieces of code). Due to the wide variety of editors it's hard to enforce this (ie a recurring problem), and this can cause merge conflicts, so I'd prefer to leave these untouched (and disable editor's auto-trim feature if enabled).
Jose
----- Original Message -----
> From: Roland Scheidegger <sroland at vmware.com>
>
> Split the sampler interface to use separate sampler and texture
> (sampler_view)
> state. This is needed to support dx10-style sampling instructions.
> This is not quite complete since both draw/llvmpipe don't really
> track
> textures/samplers independently yet, as well as the gallivm code not
> quite
> using the right sampler or texture index respectively (but it should
> work
> for the sampling codes used by opengl).
> We are however losing some optimizations in the process,
> apply_max_lod will
> no longer work, and we potentially could end up with more
> (unnecessary)
> recompiles (if switching textures with/without mipmaps only so it
> shouldn't
> be too bad).
>
> v2: don't use different callback structs for sampler/sampler view
> functions
> (which just complicates things), fix up sampling code to actually use
> the
> right texture or sampler index, and similar for llvmpipe/draw
> actually
> distinguish between samplers and sampler views.
>
> v3: fix more of PIPE_MAX_SAMPLER / PIPE_MAX_SHADER_SAMPLER_VIEWS
> mismatches
> (both in draw and llvmpipe), based on feedback from José get rid of
> unneeded
> static sampler derived state.(which also fixes the only 2 piglit
> regressions
> due to a forgotten assignment), fix comments based on Brian's
> feedback.
> ---
> src/gallium/auxiliary/draw/draw_context.c | 4 +-
> src/gallium/auxiliary/draw/draw_llvm.c | 131
> ++++++++++-----
> src/gallium/auxiliary/draw/draw_llvm.h | 66 ++++++--
> src/gallium/auxiliary/draw/draw_llvm_sample.c | 96 +++++++++--
> src/gallium/auxiliary/draw/draw_private.h | 2 +-
> src/gallium/auxiliary/gallivm/lp_bld_sample.c | 108
> +++++++-----
> src/gallium/auxiliary/gallivm/lp_bld_sample.h | 58 +++++--
> src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c | 104
> ++++++------
> src/gallium/auxiliary/gallivm/lp_bld_sample_soa.c | 185
> +++++++++++----------
> src/gallium/auxiliary/gallivm/lp_bld_tgsi.h | 3 +-
> src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c | 6 +-
> src/gallium/drivers/llvmpipe/lp_context.h | 4 +-
> src/gallium/drivers/llvmpipe/lp_jit.c | 54 ++++--
> src/gallium/drivers/llvmpipe/lp_jit.h | 24 ++-
> src/gallium/drivers/llvmpipe/lp_setup.c | 16 +-
> src/gallium/drivers/llvmpipe/lp_setup_context.h | 2 +-
> src/gallium/drivers/llvmpipe/lp_state_fs.c | 84 +++++++---
> src/gallium/drivers/llvmpipe/lp_state_fs.h | 17 +-
> src/gallium/drivers/llvmpipe/lp_state_sampler.c | 6 +-
> src/gallium/drivers/llvmpipe/lp_state_setup.c | 16 +-
> src/gallium/drivers/llvmpipe/lp_tex_sample.c | 102
> +++++++++---
> 21 files changed, 720 insertions(+), 368 deletions(-)
>
> diff --git a/src/gallium/auxiliary/draw/draw_context.c
> b/src/gallium/auxiliary/draw/draw_context.c
> index bc2f0e1..dfa8927 100644
> --- a/src/gallium/auxiliary/draw/draw_context.c
> +++ b/src/gallium/auxiliary/draw/draw_context.c
> @@ -762,11 +762,11 @@ draw_set_sampler_views(struct draw_context
> *draw,
> unsigned i;
>
> debug_assert(shader_stage < PIPE_SHADER_TYPES);
> - debug_assert(num <= PIPE_MAX_SAMPLERS);
> + debug_assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> for (i = 0; i < num; ++i)
> draw->sampler_views[shader_stage][i] = views[i];
> - for (i = num; i < PIPE_MAX_SAMPLERS; ++i)
> + for (i = num; i < PIPE_MAX_SHADER_SAMPLER_VIEWS; ++i)
> draw->sampler_views[shader_stage][i] = NULL;
>
> draw->num_sampler_views[shader_stage] = num;
> diff --git a/src/gallium/auxiliary/draw/draw_llvm.c
> b/src/gallium/auxiliary/draw/draw_llvm.c
> index a3a3bbf..7a2418a 100644
> --- a/src/gallium/auxiliary/draw/draw_llvm.c
> +++ b/src/gallium/auxiliary/draw/draw_llvm.c
> @@ -85,11 +85,6 @@ create_jit_texture_type(struct gallivm_state
> *gallivm, const char *struct_name)
> elem_types[DRAW_JIT_TEXTURE_IMG_STRIDE] =
> elem_types[DRAW_JIT_TEXTURE_MIP_OFFSETS] =
> LLVMArrayType(int32_type, PIPE_MAX_TEXTURE_LEVELS);
> - elem_types[DRAW_JIT_TEXTURE_MIN_LOD] =
> - elem_types[DRAW_JIT_TEXTURE_MAX_LOD] =
> - elem_types[DRAW_JIT_TEXTURE_LOD_BIAS] =
> LLVMFloatTypeInContext(gallivm->context);
> - elem_types[DRAW_JIT_TEXTURE_BORDER_COLOR] =
> - LLVMArrayType(LLVMFloatTypeInContext(gallivm->context), 4);
>
> texture_type = LLVMStructTypeInContext(gallivm->context,
> elem_types,
> Elements(elem_types), 0);
> @@ -130,18 +125,6 @@ create_jit_texture_type(struct gallivm_state
> *gallivm, const char *struct_name)
> LP_CHECK_MEMBER_OFFSET(struct draw_jit_texture, mip_offsets,
> target, texture_type,
> DRAW_JIT_TEXTURE_MIP_OFFSETS);
> - LP_CHECK_MEMBER_OFFSET(struct draw_jit_texture, min_lod,
> - target, texture_type,
> - DRAW_JIT_TEXTURE_MIN_LOD);
> - LP_CHECK_MEMBER_OFFSET(struct draw_jit_texture, max_lod,
> - target, texture_type,
> - DRAW_JIT_TEXTURE_MAX_LOD);
> - LP_CHECK_MEMBER_OFFSET(struct draw_jit_texture, lod_bias,
> - target, texture_type,
> - DRAW_JIT_TEXTURE_LOD_BIAS);
> - LP_CHECK_MEMBER_OFFSET(struct draw_jit_texture, border_color,
> - target, texture_type,
> - DRAW_JIT_TEXTURE_BORDER_COLOR);
>
> LP_CHECK_STRUCT_SIZE(struct draw_jit_texture, target,
> texture_type);
>
> @@ -150,15 +133,63 @@ create_jit_texture_type(struct gallivm_state
> *gallivm, const char *struct_name)
>
>
> /**
> - * Create LLVM type for struct draw_jit_texture
> + * Create LLVM type for struct draw_jit_sampler
> + */
> +static LLVMTypeRef
> +create_jit_sampler_type(struct gallivm_state *gallivm, const char
> *struct_name)
> +{
> + LLVMTargetDataRef target = gallivm->target;
> + LLVMTypeRef sampler_type;
> + LLVMTypeRef elem_types[DRAW_JIT_SAMPLER_NUM_FIELDS];
> +
> + elem_types[DRAW_JIT_SAMPLER_MIN_LOD] =
> + elem_types[DRAW_JIT_SAMPLER_MAX_LOD] =
> + elem_types[DRAW_JIT_SAMPLER_LOD_BIAS] =
> LLVMFloatTypeInContext(gallivm->context);
> + elem_types[DRAW_JIT_SAMPLER_BORDER_COLOR] =
> + LLVMArrayType(LLVMFloatTypeInContext(gallivm->context), 4);
> +
> + sampler_type = LLVMStructTypeInContext(gallivm->context,
> elem_types,
> + Elements(elem_types), 0);
> +
> +#if HAVE_LLVM < 0x0300
> + LLVMAddTypeName(gallivm->module, struct_name, sampler_type);
> +
> + /* Make sure the target's struct layout cache doesn't return
> + * stale/invalid data.
> + */
> + LLVMInvalidateStructLayout(gallivm->target, sampler_type);
> +#endif
> +
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_sampler, min_lod,
> + target, sampler_type,
> + DRAW_JIT_SAMPLER_MIN_LOD);
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_sampler, max_lod,
> + target, sampler_type,
> + DRAW_JIT_SAMPLER_MAX_LOD);
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_sampler, lod_bias,
> + target, sampler_type,
> + DRAW_JIT_SAMPLER_LOD_BIAS);
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_sampler, border_color,
> + target, sampler_type,
> + DRAW_JIT_SAMPLER_BORDER_COLOR);
> +
> + LP_CHECK_STRUCT_SIZE(struct draw_jit_sampler, target,
> sampler_type);
> +
> + return sampler_type;
> +}
> +
> +
> +/**
> + * Create LLVM type for struct draw_jit_context
> */
> static LLVMTypeRef
> create_jit_context_type(struct gallivm_state *gallivm,
> - LLVMTypeRef texture_type, const char
> *struct_name)
> + LLVMTypeRef texture_type, LLVMTypeRef
> sampler_type,
> + const char *struct_name)
> {
> LLVMTargetDataRef target = gallivm->target;
> LLVMTypeRef float_type =
> LLVMFloatTypeInContext(gallivm->context);
> - LLVMTypeRef elem_types[5];
> + LLVMTypeRef elem_types[6];
> LLVMTypeRef context_type;
>
> elem_types[0] = LLVMArrayType(LLVMPointerType(float_type, 0), /*
> vs_constants */
> @@ -168,7 +199,9 @@ create_jit_context_type(struct gallivm_state
> *gallivm,
> DRAW_TOTAL_CLIP_PLANES),
> 0);
> elem_types[3] = LLVMPointerType(float_type, 0); /* viewport */
> elem_types[4] = LLVMArrayType(texture_type,
> - PIPE_MAX_SAMPLERS); /* textures */
> + PIPE_MAX_SHADER_SAMPLER_VIEWS); /*
> textures */
> + elem_types[5] = LLVMArrayType(sampler_type,
> + PIPE_MAX_SAMPLERS); /* samplers */
> context_type = LLVMStructTypeInContext(gallivm->context,
> elem_types,
> Elements(elem_types), 0);
> #if HAVE_LLVM < 0x0300
> @@ -183,9 +216,14 @@ create_jit_context_type(struct gallivm_state
> *gallivm,
> target, context_type, 1);
> LP_CHECK_MEMBER_OFFSET(struct draw_jit_context, planes,
> target, context_type, 2);
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_context, viewport,
> + target, context_type, 3);
> LP_CHECK_MEMBER_OFFSET(struct draw_jit_context, textures,
> target, context_type,
> DRAW_JIT_CTX_TEXTURES);
> + LP_CHECK_MEMBER_OFFSET(struct draw_jit_context, samplers,
> + target, context_type,
> + DRAW_JIT_CTX_SAMPLERS);
> LP_CHECK_STRUCT_SIZE(struct draw_jit_context,
> target, context_type);
>
> @@ -291,11 +329,13 @@ static void
> create_jit_types(struct draw_llvm_variant *variant)
> {
> struct gallivm_state *gallivm = variant->gallivm;
> - LLVMTypeRef texture_type, context_type, buffer_type, vb_type;
> + LLVMTypeRef texture_type, sampler_type, context_type,
> buffer_type, vb_type;
>
> texture_type = create_jit_texture_type(gallivm, "texture");
> + sampler_type = create_jit_sampler_type(gallivm, "sampler");
>
> - context_type = create_jit_context_type(gallivm, texture_type,
> "draw_jit_context");
> + context_type = create_jit_context_type(gallivm, texture_type,
> sampler_type,
> + "draw_jit_context");
> variant->context_ptr_type = LLVMPointerType(context_type, 0);
>
> buffer_type =
> LLVMPointerType(LLVMIntTypeInContext(gallivm->context, 8), 0);
> @@ -1182,8 +1222,8 @@ draw_llvm_generate(struct draw_llvm *llvm,
> struct draw_llvm_variant *variant,
>
> /* code generated texture sampling */
> sampler = draw_llvm_sampler_soa_create(
> - draw_llvm_variant_key_samplers(&variant->key),
> - context_ptr);
> + draw_llvm_variant_key_samplers(&variant->key),
> + context_ptr);
>
> if (elts) {
> start = zero;
> @@ -1319,7 +1359,7 @@ draw_llvm_make_variant_key(struct draw_llvm
> *llvm, char *store)
> {
> unsigned i;
> struct draw_llvm_variant_key *key;
> - struct lp_sampler_static_state *sampler;
> + struct draw_sampler_static_state *draw_sampler;
>
> key = (struct draw_llvm_variant_key *)store;
>
> @@ -1345,19 +1385,29 @@ draw_llvm_make_variant_key(struct draw_llvm
> *llvm, char *store)
> * sampler array.
> */
> key->nr_samplers =
> llvm->draw->vs.vertex_shader->info.file_max[TGSI_FILE_SAMPLER] +
> 1;
> + if
> (llvm->draw->vs.vertex_shader->info.file_max[TGSI_FILE_SAMPLER_VIEW]
> != -1) {
> + key->nr_sampler_views =
> +
> llvm->draw->vs.vertex_shader->info.file_max[TGSI_FILE_SAMPLER_VIEW]
> + 1;
> + }
> + else {
> + key->nr_sampler_views = key->nr_samplers;
> + }
>
> - sampler = draw_llvm_variant_key_samplers(key);
> + draw_sampler = draw_llvm_variant_key_samplers(key);
>
> memcpy(key->vertex_element,
> llvm->draw->pt.vertex_element,
> sizeof(struct pipe_vertex_element) *
> key->nr_vertex_elements);
> -
> - memset(sampler, 0, key->nr_samplers * sizeof *sampler);
> +
> + memset(draw_sampler, 0, MAX2(key->nr_samplers,
> key->nr_sampler_views) * sizeof *draw_sampler);
>
> for (i = 0 ; i < key->nr_samplers; i++) {
> - lp_sampler_static_state(&sampler[i],
> - llvm->draw->sampler_views[PIPE_SHADER_VERTEX][i],
> - llvm->draw->samplers[PIPE_SHADER_VERTEX][i]);
> +
> lp_sampler_static_sampler_state(&draw_sampler[i].sampler_state,
> +
> llvm->draw->samplers[PIPE_SHADER_VERTEX][i]);
> + }
> + for (i = 0 ; i < key->nr_sampler_views; i++) {
> +
> lp_sampler_static_texture_state(&draw_sampler[i].texture_state,
> +
> llvm->draw->sampler_views[PIPE_SHADER_VERTEX][i]);
> }
>
> return key;
> @@ -1368,7 +1418,7 @@ void
> draw_llvm_dump_variant_key(struct draw_llvm_variant_key *key)
> {
> unsigned i;
> - struct lp_sampler_static_state *sampler =
> draw_llvm_variant_key_samplers(key);
> + struct draw_sampler_static_state *sampler =
> draw_llvm_variant_key_samplers(key);
>
> debug_printf("clamp_vertex_color = %u\n",
> key->clamp_vertex_color);
> debug_printf("clip_xy = %u\n", key->clip_xy);
> @@ -1386,8 +1436,8 @@ draw_llvm_dump_variant_key(struct
> draw_llvm_variant_key *key)
> debug_printf("vertex_element[%i].src_format = %s\n", i,
> util_format_name(key->vertex_element[i].src_format));
> }
>
> - for (i = 0 ; i < key->nr_samplers; i++) {
> - debug_printf("sampler[%i].src_format = %s\n", i,
> util_format_name(sampler[i].format));
> + for (i = 0 ; i < key->nr_sampler_views; i++) {
> + debug_printf("sampler[%i].src_format = %s\n", i,
> util_format_name(sampler[i].texture_state.format));
> }
> }
>
> @@ -1428,17 +1478,16 @@ void
> draw_llvm_set_sampler_state(struct draw_context *draw)
> {
> unsigned i;
> -
> for (i = 0; i < draw->num_samplers[PIPE_SHADER_VERTEX]; i++) {
> - struct draw_jit_texture *jit_tex =
> &draw->llvm->jit_context.textures[i];
> + struct draw_jit_sampler *jit_sam =
> &draw->llvm->jit_context.samplers[i];
>
> if (draw->samplers[i]) {
> const struct pipe_sampler_state *s
> = draw->samplers[PIPE_SHADER_VERTEX][i];
> - jit_tex->min_lod = s->min_lod;
> - jit_tex->max_lod = s->max_lod;
> - jit_tex->lod_bias = s->lod_bias;
> - COPY_4V(jit_tex->border_color, s->border_color.f);
> + jit_sam->min_lod = s->min_lod;
> + jit_sam->max_lod = s->max_lod;
> + jit_sam->lod_bias = s->lod_bias;
> + COPY_4V(jit_sam->border_color, s->border_color.f);
> }
> }
> }
> diff --git a/src/gallium/auxiliary/draw/draw_llvm.h
> b/src/gallium/auxiliary/draw/draw_llvm.h
> index 892973c..a664857 100644
> --- a/src/gallium/auxiliary/draw/draw_llvm.h
> +++ b/src/gallium/auxiliary/draw/draw_llvm.h
> @@ -52,12 +52,30 @@ struct draw_jit_texture
> uint32_t row_stride[PIPE_MAX_TEXTURE_LEVELS];
> uint32_t img_stride[PIPE_MAX_TEXTURE_LEVELS];
> uint32_t mip_offsets[PIPE_MAX_TEXTURE_LEVELS];
> +};
> +
> +
> +struct draw_sampler_static_state
> +{
> + /*
> + * These attributes are effectively interleaved for more sane key
> handling.
> + * However, there might be lots of null space if the amount of
> samplers and
> + * textures isn't the same.
> + */
> + struct lp_static_sampler_state sampler_state;
> + struct lp_static_texture_state texture_state;
> +};
> +
> +
> +struct draw_jit_sampler
> +{
> float min_lod;
> float max_lod;
> float lod_bias;
> float border_color[4];
> };
>
> +
> enum {
> DRAW_JIT_TEXTURE_WIDTH = 0,
> DRAW_JIT_TEXTURE_HEIGHT,
> @@ -68,13 +86,19 @@ enum {
> DRAW_JIT_TEXTURE_ROW_STRIDE,
> DRAW_JIT_TEXTURE_IMG_STRIDE,
> DRAW_JIT_TEXTURE_MIP_OFFSETS,
> - DRAW_JIT_TEXTURE_MIN_LOD,
> - DRAW_JIT_TEXTURE_MAX_LOD,
> - DRAW_JIT_TEXTURE_LOD_BIAS,
> - DRAW_JIT_TEXTURE_BORDER_COLOR,
> DRAW_JIT_TEXTURE_NUM_FIELDS /* number of fields above */
> };
>
> +
> +enum {
> + DRAW_JIT_SAMPLER_MIN_LOD,
> + DRAW_JIT_SAMPLER_MAX_LOD,
> + DRAW_JIT_SAMPLER_LOD_BIAS,
> + DRAW_JIT_SAMPLER_BORDER_COLOR,
> + DRAW_JIT_SAMPLER_NUM_FIELDS /* number of fields above */
> +};
> +
> +
> enum {
> DRAW_JIT_VERTEX_VERTEX_ID = 0,
> DRAW_JIT_VERTEX_CLIP,
> @@ -82,6 +106,9 @@ enum {
> DRAW_JIT_VERTEX_DATA
> };
>
> +#define DRAW_JIT_CTX_TEXTURES 4
> +#define DRAW_JIT_CTX_SAMPLERS 5
> +
> /**
> * This structure is passed directly to the generated vertex shader.
> *
> @@ -100,7 +127,8 @@ struct draw_jit_context
> float (*planes) [DRAW_TOTAL_CLIP_PLANES][4];
> float *viewport;
>
> - struct draw_jit_texture textures[PIPE_MAX_SAMPLERS];
> + struct draw_jit_texture textures[PIPE_MAX_SHADER_SAMPLER_VIEWS];
> + struct draw_jit_sampler samplers[PIPE_MAX_SAMPLERS];
> };
>
>
> @@ -117,10 +145,14 @@ struct draw_jit_context
> lp_build_struct_get(_gallivm, _ptr, 3, "viewport")
>
> #define DRAW_JIT_CTX_TEXTURES 4
> +#define DRAW_JIT_CTX_SAMPLERS 5
>
> #define draw_jit_context_textures(_gallivm, _ptr) \
> lp_build_struct_get_ptr(_gallivm, _ptr, DRAW_JIT_CTX_TEXTURES,
> "textures")
>
> +#define draw_jit_context_samplers(_gallivm, _ptr) \
> + lp_build_struct_get_ptr(_gallivm, _ptr, DRAW_JIT_CTX_SAMPLERS,
> "samplers")
> +
> #define draw_jit_header_id(_gallivm, _ptr) \
> lp_build_struct_get_ptr(_gallivm, _ptr,
> DRAW_JIT_VERTEX_VERTEX_ID, "id")
>
> @@ -166,6 +198,7 @@ struct draw_llvm_variant_key
> {
> unsigned nr_vertex_elements:8;
> unsigned nr_samplers:8;
> + unsigned nr_sampler_views:8;
> unsigned clamp_vertex_color:1;
> unsigned clip_xy:1;
> unsigned clip_z:1;
> @@ -174,7 +207,7 @@ struct draw_llvm_variant_key
> unsigned bypass_viewport:1;
> unsigned need_edgeflags:1;
> unsigned ucp_enable:PIPE_MAX_CLIP_PLANES;
> - unsigned pad:9-PIPE_MAX_CLIP_PLANES;
> + unsigned pad:33-PIPE_MAX_CLIP_PLANES;
>
> /* Variable number of vertex elements:
> */
> @@ -182,34 +215,33 @@ struct draw_llvm_variant_key
>
> /* Followed by variable number of samplers:
> */
> -/* struct lp_sampler_static_state sampler; */
> +/* struct draw_sampler_static_state sampler; */
> };
>
> #define DRAW_LLVM_MAX_VARIANT_KEY_SIZE \
> (sizeof(struct draw_llvm_variant_key) + \
> - PIPE_MAX_SAMPLERS * sizeof(struct lp_sampler_static_state) + \
> + PIPE_MAX_SHADER_SAMPLER_VIEWS * sizeof(struct
> draw_sampler_static_state) + \
> (PIPE_MAX_ATTRIBS-1) * sizeof(struct pipe_vertex_element))
>
>
> static INLINE size_t
> draw_llvm_variant_key_size(unsigned nr_vertex_elements,
> - unsigned nr_samplers)
> + unsigned nr_samplers)
> {
> return (sizeof(struct draw_llvm_variant_key) +
> - nr_samplers * sizeof(struct lp_sampler_static_state) +
> - (nr_vertex_elements - 1) * sizeof(struct pipe_vertex_element));
> + nr_samplers * sizeof(struct draw_sampler_static_state) +
> + (nr_vertex_elements - 1) * sizeof(struct
> pipe_vertex_element));
> }
>
>
> -static INLINE struct lp_sampler_static_state *
> +static INLINE struct draw_sampler_static_state *
> draw_llvm_variant_key_samplers(struct draw_llvm_variant_key *key)
> {
> - return (struct lp_sampler_static_state *)
> + return (struct draw_sampler_static_state *)
> &key->vertex_element[key->nr_vertex_elements];
> }
>
>
> -
> struct draw_llvm_variant_list_item
> {
> struct draw_llvm_variant *base;
> @@ -275,8 +307,8 @@ draw_llvm_destroy(struct draw_llvm *llvm);
>
> struct draw_llvm_variant *
> draw_llvm_create_variant(struct draw_llvm *llvm,
> - unsigned num_vertex_header_attribs,
> - const struct draw_llvm_variant_key *key);
> + unsigned num_vertex_header_attribs,
> + const struct draw_llvm_variant_key *key);
>
> void
> draw_llvm_destroy_variant(struct draw_llvm_variant *variant);
> @@ -288,7 +320,7 @@ void
> draw_llvm_dump_variant_key(struct draw_llvm_variant_key *key);
>
> struct lp_build_sampler_soa *
> -draw_llvm_sampler_soa_create(const struct lp_sampler_static_state
> *static_state,
> +draw_llvm_sampler_soa_create(const struct draw_sampler_static_state
> *static_state,
> LLVMValueRef context_ptr);
>
> void
> diff --git a/src/gallium/auxiliary/draw/draw_llvm_sample.c
> b/src/gallium/auxiliary/draw/draw_llvm_sample.c
> index 67d4e93..ac1c031 100644
> --- a/src/gallium/auxiliary/draw/draw_llvm_sample.c
> +++ b/src/gallium/auxiliary/draw/draw_llvm_sample.c
> @@ -58,7 +58,7 @@ struct draw_llvm_sampler_dynamic_state
> {
> struct lp_sampler_dynamic_state base;
>
> - const struct lp_sampler_static_state *static_state;
> + const struct draw_sampler_static_state *static_state;
>
> LLVMValueRef context_ptr;
> };
> @@ -98,7 +98,7 @@ draw_llvm_texture_member(const struct
> lp_sampler_dynamic_state *base,
> LLVMValueRef ptr;
> LLVMValueRef res;
>
> - debug_assert(unit < PIPE_MAX_SAMPLERS);
> + debug_assert(unit < PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> /* context[0] */
> indices[0] = lp_build_const_int32(gallivm, 0);
> @@ -123,6 +123,53 @@ draw_llvm_texture_member(const struct
> lp_sampler_dynamic_state *base,
>
>
> /**
> + * Fetch the specified member of the lp_jit_sampler structure.
> + * \param emit_load if TRUE, emit the LLVM load instruction to
> actually
> + * fetch the field's value. Otherwise, just emit
> the
> + * GEP code to address the field.
> + *
> + * @sa http://llvm.org/docs/GetElementPtr.html
> + */
> +static LLVMValueRef
> +draw_llvm_sampler_member(const struct lp_sampler_dynamic_state
> *base,
> + struct gallivm_state *gallivm,
> + unsigned unit,
> + unsigned member_index,
> + const char *member_name,
> + boolean emit_load)
> +{
> + LLVMBuilderRef builder = gallivm->builder;
> + struct draw_llvm_sampler_dynamic_state *state =
> + (struct draw_llvm_sampler_dynamic_state *)base;
> + LLVMValueRef indices[4];
> + LLVMValueRef ptr;
> + LLVMValueRef res;
> +
> + debug_assert(unit < PIPE_MAX_SAMPLERS);
> +
> + /* context[0] */
> + indices[0] = lp_build_const_int32(gallivm, 0);
> + /* context[0].samplers */
> + indices[1] = lp_build_const_int32(gallivm,
> DRAW_JIT_CTX_SAMPLERS);
> + /* context[0].samplers[unit] */
> + indices[2] = lp_build_const_int32(gallivm, unit);
> + /* context[0].samplers[unit].member */
> + indices[3] = lp_build_const_int32(gallivm, member_index);
> +
> + ptr = LLVMBuildGEP(builder, state->context_ptr, indices,
> Elements(indices), "");
> +
> + if (emit_load)
> + res = LLVMBuildLoad(builder, ptr, "");
> + else
> + res = ptr;
> +
> + lp_build_name(res, "context.sampler%u.%s", unit, member_name);
> +
> + return res;
> +}
> +
> +
> +/**
> * Helper macro to instantiate the functions that generate the code
> to
> * fetch the members of lp_jit_texture to fulfill the sampler code
> * generator requests.
> @@ -150,10 +197,23 @@ DRAW_LLVM_TEXTURE_MEMBER(base_ptr,
> DRAW_JIT_TEXTURE_BASE, TRUE)
> DRAW_LLVM_TEXTURE_MEMBER(row_stride, DRAW_JIT_TEXTURE_ROW_STRIDE,
> FALSE)
> DRAW_LLVM_TEXTURE_MEMBER(img_stride, DRAW_JIT_TEXTURE_IMG_STRIDE,
> FALSE)
> DRAW_LLVM_TEXTURE_MEMBER(mip_offsets, DRAW_JIT_TEXTURE_MIP_OFFSETS,
> FALSE)
> -DRAW_LLVM_TEXTURE_MEMBER(min_lod, DRAW_JIT_TEXTURE_MIN_LOD, TRUE)
> -DRAW_LLVM_TEXTURE_MEMBER(max_lod, DRAW_JIT_TEXTURE_MAX_LOD, TRUE)
> -DRAW_LLVM_TEXTURE_MEMBER(lod_bias, DRAW_JIT_TEXTURE_LOD_BIAS,
> TRUE)
> -DRAW_LLVM_TEXTURE_MEMBER(border_color,
> DRAW_JIT_TEXTURE_BORDER_COLOR, FALSE)
> +
> +
> +#define DRAW_LLVM_SAMPLER_MEMBER(_name, _index, _emit_load) \
> + static LLVMValueRef \
> + draw_llvm_sampler_##_name( const struct lp_sampler_dynamic_state
> *base, \
> + struct gallivm_state *gallivm,
> \
> + unsigned unit)
> \
> + { \
> + return draw_llvm_sampler_member(base, gallivm, unit, _index,
> #_name, _emit_load ); \
> + }
> +
> +
> +DRAW_LLVM_SAMPLER_MEMBER(min_lod, DRAW_JIT_SAMPLER_MIN_LOD, TRUE)
> +DRAW_LLVM_SAMPLER_MEMBER(max_lod, DRAW_JIT_SAMPLER_MAX_LOD, TRUE)
> +DRAW_LLVM_SAMPLER_MEMBER(lod_bias, DRAW_JIT_SAMPLER_LOD_BIAS,
> TRUE)
> +DRAW_LLVM_SAMPLER_MEMBER(border_color,
> DRAW_JIT_SAMPLER_BORDER_COLOR, FALSE)
> +
>
>
> static void
> @@ -172,7 +232,8 @@ draw_llvm_sampler_soa_emit_fetch_texel(const
> struct lp_build_sampler_soa *base,
> struct gallivm_state
> *gallivm,
> struct lp_type type,
> boolean is_fetch,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const LLVMValueRef *coords,
> const LLVMValueRef *offsets,
> const struct lp_derivatives
> *derivs,
> @@ -182,14 +243,17 @@ draw_llvm_sampler_soa_emit_fetch_texel(const
> struct lp_build_sampler_soa *base,
> {
> struct draw_llvm_sampler_soa *sampler = (struct
> draw_llvm_sampler_soa *)base;
>
> - assert(unit < PIPE_MAX_SAMPLERS);
> + assert(texture_index < PIPE_MAX_SHADER_SAMPLER_VIEWS);
> + assert(sampler_index < PIPE_MAX_SAMPLERS);
>
> lp_build_sample_soa(gallivm,
> - &sampler->dynamic_state.static_state[unit],
> +
> &sampler->dynamic_state.static_state[texture_index].texture_state,
> +
> &sampler->dynamic_state.static_state[sampler_index].sampler_state,
> &sampler->dynamic_state.base,
> type,
> is_fetch,
> - unit,
> + texture_index,
> + sampler_index,
> coords,
> offsets,
> derivs,
> @@ -214,7 +278,7 @@ draw_llvm_sampler_soa_emit_size_query(const
> struct lp_build_sampler_soa *base,
> assert(unit < PIPE_MAX_SAMPLERS);
>
> lp_build_size_query_soa(gallivm,
> -
> &sampler->dynamic_state.static_state[unit],
> +
> &sampler->dynamic_state.static_state[unit].texture_state,
> &sampler->dynamic_state.base,
> type,
> unit,
> @@ -223,7 +287,7 @@ draw_llvm_sampler_soa_emit_size_query(const
> struct lp_build_sampler_soa *base,
> }
>
> struct lp_build_sampler_soa *
> -draw_llvm_sampler_soa_create(const struct lp_sampler_static_state
> *static_state,
> +draw_llvm_sampler_soa_create(const struct draw_sampler_static_state
> *static_state,
> LLVMValueRef context_ptr)
> {
> struct draw_llvm_sampler_soa *sampler;
> @@ -244,10 +308,10 @@ draw_llvm_sampler_soa_create(const struct
> lp_sampler_static_state *static_state,
> sampler->dynamic_state.base.img_stride =
> draw_llvm_texture_img_stride;
> sampler->dynamic_state.base.base_ptr =
> draw_llvm_texture_base_ptr;
> sampler->dynamic_state.base.mip_offsets =
> draw_llvm_texture_mip_offsets;
> - sampler->dynamic_state.base.min_lod = draw_llvm_texture_min_lod;
> - sampler->dynamic_state.base.max_lod = draw_llvm_texture_max_lod;
> - sampler->dynamic_state.base.lod_bias =
> draw_llvm_texture_lod_bias;
> - sampler->dynamic_state.base.border_color =
> draw_llvm_texture_border_color;
> + sampler->dynamic_state.base.min_lod = draw_llvm_sampler_min_lod;
> + sampler->dynamic_state.base.max_lod = draw_llvm_sampler_max_lod;
> + sampler->dynamic_state.base.lod_bias =
> draw_llvm_sampler_lod_bias;
> + sampler->dynamic_state.base.border_color =
> draw_llvm_sampler_border_color;
> sampler->dynamic_state.static_state = static_state;
> sampler->dynamic_state.context_ptr = context_ptr;
>
> diff --git a/src/gallium/auxiliary/draw/draw_private.h
> b/src/gallium/auxiliary/draw/draw_private.h
> index 2223fcb..ec5791c 100644
> --- a/src/gallium/auxiliary/draw/draw_private.h
> +++ b/src/gallium/auxiliary/draw/draw_private.h
> @@ -310,7 +310,7 @@ struct draw_context
> * we only handle vertex and geometry shaders in the draw module,
> but
> * there may be more in the future (ex: hull and tessellation).
> */
> - struct pipe_sampler_view
> *sampler_views[PIPE_SHADER_TYPES][PIPE_MAX_SAMPLERS];
> + struct pipe_sampler_view
> *sampler_views[PIPE_SHADER_TYPES][PIPE_MAX_SHADER_SAMPLER_VIEWS];
> unsigned num_sampler_views[PIPE_SHADER_TYPES];
> const struct pipe_sampler_state
> *samplers[PIPE_SHADER_TYPES][PIPE_MAX_SAMPLERS];
> unsigned num_samplers[PIPE_SHADER_TYPES];
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_sample.c
> b/src/gallium/auxiliary/gallivm/lp_bld_sample.c
> index 04f4135..4e4bca3 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_sample.c
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_sample.c
> @@ -87,24 +87,54 @@ lp_sampler_wrap_mode_uses_border_color(unsigned
> mode,
>
>
> /**
> - * Initialize lp_sampler_static_state object with the gallium
> sampler
> - * and texture state.
> - * The former is considered to be static and the later dynamic.
> + * Initialize lp_sampler_static_texture_state object with the
> gallium
> + * texture/sampler_view state (this contains the parts which are
> + * considered static).
> */
> void
> -lp_sampler_static_state(struct lp_sampler_static_state *state,
> - const struct pipe_sampler_view *view,
> - const struct pipe_sampler_state *sampler)
> +lp_sampler_static_texture_state(struct lp_static_texture_state
> *state,
> + const struct pipe_sampler_view
> *view)
> {
> const struct pipe_resource *texture;
>
> memset(state, 0, sizeof *state);
>
> - if (!sampler || !view || !view->texture)
> + if (!view || !view->texture)
> return;
>
> texture = view->texture;
>
> + state->format = view->format;
> + state->swizzle_r = view->swizzle_r;
> + state->swizzle_g = view->swizzle_g;
> + state->swizzle_b = view->swizzle_b;
> + state->swizzle_a = view->swizzle_a;
> +
> + state->target = texture->target;
> + state->pot_width = util_is_power_of_two(texture->width0);
> + state->pot_height =
> util_is_power_of_two(texture->height0);
> + state->pot_depth = util_is_power_of_two(texture->depth0);
> + state->level_zero_only = !view->u.tex.last_level;
> +
> + /*
> + * FIXME: Handle the remainder of pipe_sampler_view.
> + */
> +}
> +
> +
> +/**
> + * Initialize lp_sampler_static_sampler_state object with the
> gallium sampler
> + * state (this contains the parts which are considered static).
> + */
> +void
> +lp_sampler_static_sampler_state(struct lp_static_sampler_state
> *state,
> + const struct pipe_sampler_state
> *sampler)
> +{
> + memset(state, 0, sizeof *state);
> +
> + if (!sampler)
> + return;
> +
> /*
> * We don't copy sampler state over unless it is actually
> enabled, to avoid
> * spurious recompiles, as the sampler static state is part of
> the shader
> @@ -117,24 +147,13 @@ lp_sampler_static_state(struct
> lp_sampler_static_state *state,
> * regarding 1D/2D/3D/CUBE textures, wrap modes, etc.
> */
>
> - state->format = view->format;
> - state->swizzle_r = view->swizzle_r;
> - state->swizzle_g = view->swizzle_g;
> - state->swizzle_b = view->swizzle_b;
> - state->swizzle_a = view->swizzle_a;
> -
> - state->target = texture->target;
> - state->pot_width = util_is_power_of_two(texture->width0);
> - state->pot_height =
> util_is_power_of_two(texture->height0);
> - state->pot_depth = util_is_power_of_two(texture->depth0);
> -
> state->wrap_s = sampler->wrap_s;
> state->wrap_t = sampler->wrap_t;
> state->wrap_r = sampler->wrap_r;
> state->min_img_filter = sampler->min_img_filter;
> state->mag_img_filter = sampler->mag_img_filter;
>
> - if (view->u.tex.last_level && sampler->max_lod > 0.0f) {
> + if (sampler->max_lod > 0.0f) {
> state->min_mip_filter = sampler->min_mip_filter;
> } else {
> state->min_mip_filter = PIPE_TEX_MIPFILTER_NONE;
> @@ -155,7 +174,11 @@ lp_sampler_static_state(struct
> lp_sampler_static_state *state,
> state->apply_min_lod = 1;
> }
>
> - if (sampler->max_lod < (float)view->u.tex.last_level) {
> + /*
> + * XXX this won't do anything with the mesa state tracker
> which always
> + * sets max_lod to not more than actually present mip
> maps...
> + */
> + if (sampler->max_lod < (PIPE_MAX_TEXTURE_LEVELS - 1)) {
> state->apply_max_lod = 1;
> }
> }
> @@ -167,10 +190,6 @@ lp_sampler_static_state(struct
> lp_sampler_static_state *state,
> }
>
> state->normalized_coords = sampler->normalized_coords;
> -
> - /*
> - * FIXME: Handle the remainder of pipe_sampler_view.
> - */
> }
>
>
> @@ -182,7 +201,7 @@ lp_sampler_static_state(struct
> lp_sampler_static_state *state,
> */
> static LLVMValueRef
> lp_build_rho(struct lp_build_sample_context *bld,
> - unsigned unit,
> + unsigned texture_unit,
> const struct lp_derivatives *derivs)
> {
> struct gallivm_state *gallivm = bld->gallivm;
> @@ -264,7 +283,7 @@ lp_build_rho(struct lp_build_sample_context *bld,
> rho_vec = lp_build_max(coord_bld, rho_xvec, rho_yvec);
>
> first_level = bld->dynamic_state->first_level(bld->dynamic_state,
> - bld->gallivm,
> unit);
> + bld->gallivm,
> texture_unit);
> first_level_vec = lp_build_broadcast_scalar(int_size_bld,
> first_level);
> int_size = lp_build_minify(int_size_bld, bld->int_size,
> first_level_vec);
> float_size = lp_build_int_to_float(float_size_bld, int_size);
> @@ -489,7 +508,8 @@ lp_build_brilinear_rho(struct lp_build_context
> *bld,
> */
> void
> lp_build_lod_selector(struct lp_build_sample_context *bld,
> - unsigned unit,
> + unsigned texture_unit,
> + unsigned sampler_unit,
> const struct lp_derivatives *derivs,
> LLVMValueRef lod_bias, /* optional */
> LLVMValueRef explicit_lod, /* optional */
> @@ -505,12 +525,13 @@ lp_build_lod_selector(struct
> lp_build_sample_context *bld,
> *out_lod_ipart = bld->perquadi_bld.zero;
> *out_lod_fpart = perquadf_bld->zero;
>
> - if (bld->static_state->min_max_lod_equal) {
> + if (bld->static_sampler_state->min_max_lod_equal) {
> /* User is forcing sampling from a particular mipmap level.
> * This is hit during mipmap generation.
> */
> LLVMValueRef min_lod =
> - bld->dynamic_state->min_lod(bld->dynamic_state,
> bld->gallivm, unit);
> + bld->dynamic_state->min_lod(bld->dynamic_state,
> + bld->gallivm, sampler_unit);
>
> lod = lp_build_broadcast_scalar(perquadf_bld, min_lod);
> }
> @@ -522,16 +543,16 @@ lp_build_lod_selector(struct
> lp_build_sample_context *bld,
> else {
> LLVMValueRef rho;
>
> - rho = lp_build_rho(bld, unit, derivs);
> + rho = lp_build_rho(bld, texture_unit, derivs);
>
> /*
> * Compute lod = log2(rho)
> */
>
> if (!lod_bias &&
> - !bld->static_state->lod_bias_non_zero &&
> - !bld->static_state->apply_max_lod &&
> - !bld->static_state->apply_min_lod) {
> + !bld->static_sampler_state->lod_bias_non_zero &&
> + !bld->static_sampler_state->apply_max_lod &&
> + !bld->static_sampler_state->apply_min_lod) {
> /*
> * Special case when there are no post-log2 adjustments,
> which
> * saves instructions but keeping the integer and
> fractional lod
> @@ -568,25 +589,28 @@ lp_build_lod_selector(struct
> lp_build_sample_context *bld,
> }
>
> /* add sampler lod bias */
> - if (bld->static_state->lod_bias_non_zero) {
> + if (bld->static_sampler_state->lod_bias_non_zero) {
> LLVMValueRef sampler_lod_bias =
> - bld->dynamic_state->lod_bias(bld->dynamic_state,
> bld->gallivm, unit);
> + bld->dynamic_state->lod_bias(bld->dynamic_state,
> + bld->gallivm,
> sampler_unit);
> sampler_lod_bias = lp_build_broadcast_scalar(perquadf_bld,
> sampler_lod_bias);
> lod = LLVMBuildFAdd(builder, lod, sampler_lod_bias,
> "sampler_lod_bias");
> }
>
> /* clamp lod */
> - if (bld->static_state->apply_max_lod) {
> + if (bld->static_sampler_state->apply_max_lod) {
> LLVMValueRef max_lod =
> - bld->dynamic_state->max_lod(bld->dynamic_state,
> bld->gallivm, unit);
> + bld->dynamic_state->max_lod(bld->dynamic_state,
> + bld->gallivm, sampler_unit);
> max_lod = lp_build_broadcast_scalar(perquadf_bld, max_lod);
>
> lod = lp_build_min(perquadf_bld, lod, max_lod);
> }
> - if (bld->static_state->apply_min_lod) {
> + if (bld->static_sampler_state->apply_min_lod) {
> LLVMValueRef min_lod =
> - bld->dynamic_state->min_lod(bld->dynamic_state,
> bld->gallivm, unit);
> + bld->dynamic_state->min_lod(bld->dynamic_state,
> + bld->gallivm, sampler_unit);
> min_lod = lp_build_broadcast_scalar(perquadf_bld, min_lod);
>
> lod = lp_build_max(perquadf_bld, lod, min_lod);
> @@ -988,9 +1012,9 @@ lp_build_mipmap_level_sizes(struct
> lp_build_sample_context *bld,
> ilevel);
> }
> if (dims == 3 ||
> - bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> *img_stride_vec = lp_build_get_level_stride_vec(bld,
> bld->img_stride_array,
> ilevel);
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_sample.h
> b/src/gallium/auxiliary/gallivm/lp_bld_sample.h
> index 87bf556..d0207aa 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_sample.h
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_sample.h
> @@ -61,12 +61,12 @@ struct lp_derivatives
>
>
> /**
> - * Sampler static state.
> + * Texture static state.
> *
> - * These are the bits of state from pipe_resource and
> pipe_sampler_state that
> + * These are the bits of state from pipe_resource/pipe_sampler_view
> that
> * are embedded in the generated code.
> */
> -struct lp_sampler_static_state
> +struct lp_static_texture_state
> {
> /* pipe_sampler_view's state */
> enum pipe_format format;
> @@ -80,7 +80,18 @@ struct lp_sampler_static_state
> unsigned pot_width:1; /**< is the width a power of two? */
> unsigned pot_height:1;
> unsigned pot_depth:1;
> + unsigned level_zero_only:1;
> +};
>
> +
> +/**
> + * Sampler static state.
> + *
> + * These are the bits of state from pipe_sampler_state that
> + * are embedded in the generated code.
> + */
> +struct lp_static_sampler_state
> +{
> /* pipe_sampler_state's state */
> unsigned wrap_s:3;
> unsigned wrap_t:3;
> @@ -105,8 +116,8 @@ struct lp_sampler_static_state
> /**
> * Sampler dynamic state.
> *
> - * These are the bits of state from pipe_resource and
> pipe_sampler_state that
> - * are computed in runtime.
> + * These are the bits of state from pipe_resource/pipe_sampler_view
> + * as well as from sampler state that are computed at runtime.
> *
> * There are obtained through callbacks, as we don't want to tie the
> texture
> * sampling code generation logic to any particular texture layout
> or pipe
> @@ -114,6 +125,7 @@ struct lp_sampler_static_state
> */
> struct lp_sampler_dynamic_state
> {
> + /* First callbacks for sampler view state */
>
> /** Obtain the base texture width (returns int32) */
> LLVMValueRef
> @@ -169,6 +181,8 @@ struct lp_sampler_dynamic_state
> struct gallivm_state *gallivm,
> unsigned unit);
>
> + /* These are callbacks for sampler state */
> +
> /** Obtain texture min lod (returns float) */
> LLVMValueRef
> (*min_lod)(const struct lp_sampler_dynamic_state *state,
> @@ -198,7 +212,8 @@ struct lp_build_sample_context
> {
> struct gallivm_state *gallivm;
>
> - const struct lp_sampler_static_state *static_state;
> + const struct lp_static_texture_state *static_texture_state;
> + const struct lp_static_sampler_state *static_sampler_state;
>
> struct lp_sampler_dynamic_state *dynamic_state;
>
> @@ -295,10 +310,10 @@ apply_sampler_swizzle(struct
> lp_build_sample_context *bld,
> {
> unsigned char swizzles[4];
>
> - swizzles[0] = bld->static_state->swizzle_r;
> - swizzles[1] = bld->static_state->swizzle_g;
> - swizzles[2] = bld->static_state->swizzle_b;
> - swizzles[3] = bld->static_state->swizzle_a;
> + swizzles[0] = bld->static_texture_state->swizzle_r;
> + swizzles[1] = bld->static_texture_state->swizzle_g;
> + swizzles[2] = bld->static_texture_state->swizzle_b;
> + swizzles[3] = bld->static_texture_state->swizzle_a;
>
> lp_build_swizzle_soa_inplace(&bld->texel_bld, texel, swizzles);
> }
> @@ -338,14 +353,19 @@ lp_sampler_wrap_mode_uses_border_color(unsigned
> mode,
> * Derive the sampler static state.
> */
> void
> -lp_sampler_static_state(struct lp_sampler_static_state *state,
> - const struct pipe_sampler_view *view,
> - const struct pipe_sampler_state *sampler);
> +lp_sampler_static_sampler_state(struct lp_static_sampler_state
> *state,
> + const struct pipe_sampler_state
> *sampler);
> +
> +
> +void
> +lp_sampler_static_texture_state(struct lp_static_texture_state
> *state,
> + const struct pipe_sampler_view
> *view);
>
>
> void
> lp_build_lod_selector(struct lp_build_sample_context *bld,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const struct lp_derivatives *derivs,
> LLVMValueRef lod_bias, /* optional */
> LLVMValueRef explicit_lod, /* optional */
> @@ -437,11 +457,13 @@ lp_build_sample_offset(struct lp_build_context
> *bld,
>
> void
> lp_build_sample_soa(struct gallivm_state *gallivm,
> - const struct lp_sampler_static_state
> *static_state,
> - struct lp_sampler_dynamic_state *dynamic_state,
> + const struct lp_static_texture_state
> *static_texture_state,
> + const struct lp_static_sampler_state
> *static_sampler_state,
> + struct lp_sampler_dynamic_state
> *dynamic_texture_state,
> struct lp_type fp_type,
> boolean is_fetch,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const LLVMValueRef *coords,
> const LLVMValueRef *offsets,
> const struct lp_derivatives *derivs,
> @@ -461,7 +483,7 @@ lp_build_coord_repeat_npot_linear(struct
> lp_build_sample_context *bld,
>
> void
> lp_build_size_query_soa(struct gallivm_state *gallivm,
> - const struct lp_sampler_static_state
> *static_state,
> + const struct lp_static_texture_state
> *static_state,
> struct lp_sampler_dynamic_state
> *dynamic_state,
> struct lp_type int_type,
> unsigned unit,
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c
> b/src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c
> index 9371e1c..b9c8446 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_sample_aos.c
> @@ -152,7 +152,7 @@ lp_build_sample_wrap_nearest_float(struct
> lp_build_sample_context *bld,
> break;
> case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
> length_minus_one = lp_build_sub(coord_bld, length,
> coord_bld->one);
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length);
> }
> @@ -407,7 +407,7 @@ lp_build_sample_wrap_linear_float(struct
> lp_build_sample_context *bld,
> }
> break;
> case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* mul by tex size */
> coord = lp_build_mul(coord_bld, coord, length);
> }
> @@ -549,7 +549,7 @@ lp_build_sample_image_nearest(struct
> lp_build_sample_context *bld,
>
> s_float = s; t_float = t; r_float = r;
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> LLVMValueRef scaled_size;
> LLVMValueRef flt_size;
>
> @@ -594,8 +594,8 @@ lp_build_sample_image_nearest(struct
> lp_build_sample_context *bld,
> bld->format_desc->block.width,
> s_ipart, s_float,
> width_vec, x_stride,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s,
> +
> bld->static_texture_state->pot_width,
> +
> bld->static_sampler_state->wrap_s,
> &x_offset, &x_subcoord);
> offset = x_offset;
> if (dims >= 2) {
> @@ -604,8 +604,8 @@ lp_build_sample_image_nearest(struct
> lp_build_sample_context *bld,
> bld->format_desc->block.height,
> t_ipart, t_float,
> height_vec, row_stride_vec,
> -
> bld->static_state->pot_height,
> - bld->static_state->wrap_t,
> +
> bld->static_texture_state->pot_height,
> +
> bld->static_sampler_state->wrap_t,
> &y_offset, &y_subcoord);
> offset = lp_build_add(&bld->int_coord_bld, offset, y_offset);
> if (dims >= 3) {
> @@ -614,15 +614,15 @@ lp_build_sample_image_nearest(struct
> lp_build_sample_context *bld,
> 1, /* block length (depth)
> */
> r_ipart, r_float,
> depth_vec, img_stride_vec,
> -
> bld->static_state->pot_depth,
> - bld->static_state->wrap_r,
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r,
> &z_offset, &z_subcoord);
> offset = lp_build_add(&bld->int_coord_bld, offset,
> z_offset);
> }
> }
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> LLVMValueRef z_offset;
> /* The r coord is the cube face in [0,5] or array layer */
> z_offset = lp_build_mul(&bld->int_coord_bld, r,
> img_stride_vec);
> @@ -678,28 +678,28 @@ lp_build_sample_image_nearest_afloat(struct
> lp_build_sample_context *bld,
> /* Do texcoord wrapping */
> lp_build_sample_wrap_nearest_float(bld,
> s, width_vec,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s,
> +
> bld->static_texture_state->pot_width,
> +
> bld->static_sampler_state->wrap_s,
> &x_icoord);
>
> if (dims >= 2) {
> lp_build_sample_wrap_nearest_float(bld,
> t, height_vec,
> -
> bld->static_state->pot_height,
> - bld->static_state->wrap_t,
> +
> bld->static_texture_state->pot_height,
> +
> bld->static_sampler_state->wrap_t,
> &y_icoord);
>
> if (dims >= 3) {
> lp_build_sample_wrap_nearest_float(bld,
> r, depth_vec,
> -
> bld->static_state->pot_depth,
> -
> bld->static_state->wrap_r,
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r,
> &z_icoord);
> }
> }
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> z_icoord = r;
> }
>
> @@ -885,7 +885,7 @@ lp_build_sample_fetch_image_linear(struct
> lp_build_sample_context *bld,
> /*
> * Linear interpolation with 8.8 fixed point.
> */
> - if (bld->static_state->force_nearest_s) {
> + if (bld->static_sampler_state->force_nearest_s) {
> /* special case 1-D lerp */
> packed_lo = lp_build_lerp(&h16,
> t_fpart_lo,
> @@ -897,7 +897,7 @@ lp_build_sample_fetch_image_linear(struct
> lp_build_sample_context *bld,
> neighbors_hi[0][1][0],
> neighbors_hi[0][1][0]);
> }
> - else if (bld->static_state->force_nearest_t) {
> + else if (bld->static_sampler_state->force_nearest_t) {
> /* special case 1-D lerp */
> packed_lo = lp_build_lerp(&h16,
> s_fpart_lo,
> @@ -1016,7 +1016,7 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
>
> s_float = s; t_float = t; r_float = r;
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> LLVMValueRef scaled_size;
> LLVMValueRef flt_size;
>
> @@ -1045,10 +1045,10 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
>
> /* subtract 0.5 (add -128) */
> i32_c128 = lp_build_const_int_vec(bld->gallivm, i32.type, -128);
> - if (!bld->static_state->force_nearest_s) {
> + if (!bld->static_sampler_state->force_nearest_s) {
> s = LLVMBuildAdd(builder, s, i32_c128, "");
> }
> - if (dims >= 2 && !bld->static_state->force_nearest_t) {
> + if (dims >= 2 && !bld->static_sampler_state->force_nearest_t) {
> t = LLVMBuildAdd(builder, t, i32_c128, "");
> }
> if (dims >= 3) {
> @@ -1082,15 +1082,15 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
> bld->format_desc->block.width,
> s_ipart, &s_fpart, s_float,
> width_vec, x_stride,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s,
> +
> bld->static_texture_state->pot_width,
> +
> bld->static_sampler_state->wrap_s,
> &x_offset0, &x_offset1,
> &x_subcoord[0], &x_subcoord[1]);
>
> /* add potential cube/array/mip offsets now as they are constant
> per pixel */
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> LLVMValueRef z_offset;
> z_offset = lp_build_mul(&bld->int_coord_bld, r,
> img_stride_vec);
> /* The r coord is the cube face in [0,5] or array layer */
> @@ -1114,8 +1114,8 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
> bld->format_desc->block.height,
> t_ipart, &t_fpart, t_float,
> height_vec, y_stride,
> - bld->static_state->pot_height,
> - bld->static_state->wrap_t,
> +
> bld->static_texture_state->pot_height,
> +
> bld->static_sampler_state->wrap_t,
> &y_offset0, &y_offset1,
> &y_subcoord[0],
> &y_subcoord[1]);
>
> @@ -1134,8 +1134,8 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
> bld->format_desc->block.height,
> r_ipart, &r_fpart, r_float,
> depth_vec, z_stride,
> - bld->static_state->pot_depth,
> - bld->static_state->wrap_r,
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r,
> &z_offset0, &z_offset1,
> &z_subcoord[0],
> &z_subcoord[1]);
> for (y = 0; y < 2; y++) {
> @@ -1205,28 +1205,28 @@ lp_build_sample_image_linear_afloat(struct
> lp_build_sample_context *bld,
> lp_build_sample_wrap_linear_float(bld,
> bld->format_desc->block.width,
> s, width_vec,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s,
> +
> bld->static_texture_state->pot_width,
> +
> bld->static_sampler_state->wrap_s,
> &x_icoord0, &x_icoord1,
> &s_fpart,
> -
> bld->static_state->force_nearest_s);
> +
> bld->static_sampler_state->force_nearest_s);
>
> if (dims >= 2) {
> lp_build_sample_wrap_linear_float(bld,
> bld->format_desc->block.height,
> t, height_vec,
> -
> bld->static_state->pot_height,
> - bld->static_state->wrap_t,
> +
> bld->static_texture_state->pot_height,
> +
> bld->static_sampler_state->wrap_t,
> &y_icoord0, &y_icoord1,
> &t_fpart,
> -
> bld->static_state->force_nearest_t);
> +
> bld->static_sampler_state->force_nearest_t);
>
> if (dims >= 3) {
> lp_build_sample_wrap_linear_float(bld,
> bld->format_desc->block.height,
> r, depth_vec,
> -
> bld->static_state->pot_depth,
> -
> bld->static_state->wrap_r,
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r,
> &z_icoord0, &z_icoord1,
> &r_fpart, 0);
> }
> @@ -1259,9 +1259,9 @@ lp_build_sample_image_linear_afloat(struct
> lp_build_sample_context *bld,
> &x_offset1, &x_subcoord[1]);
>
> /* add potential cube/array/mip offsets now as they are constant
> per pixel */
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> LLVMValueRef z_offset;
> z_offset = lp_build_mul(&bld->int_coord_bld, r,
> img_stride_vec);
> /* The r coord is the cube face in [0,5] or array layer */
> @@ -1582,20 +1582,20 @@ lp_build_sample_aos(struct
> lp_build_sample_context *bld,
> {
> struct lp_build_context *int_bld = &bld->int_bld;
> LLVMBuilderRef builder = bld->gallivm->builder;
> - const unsigned mip_filter = bld->static_state->min_mip_filter;
> - const unsigned min_filter = bld->static_state->min_img_filter;
> - const unsigned mag_filter = bld->static_state->mag_img_filter;
> + const unsigned mip_filter =
> bld->static_sampler_state->min_mip_filter;
> + const unsigned min_filter =
> bld->static_sampler_state->min_img_filter;
> + const unsigned mag_filter =
> bld->static_sampler_state->mag_img_filter;
> const unsigned dims = bld->dims;
> LLVMValueRef packed, packed_lo, packed_hi;
> LLVMValueRef unswizzled[4];
> struct lp_build_context h16_bld;
>
> /* we only support the common/simple wrap modes at this time */
> - assert(lp_is_simple_wrap_mode(bld->static_state->wrap_s));
> +
> assert(lp_is_simple_wrap_mode(bld->static_sampler_state->wrap_s));
> if (dims >= 2)
> - assert(lp_is_simple_wrap_mode(bld->static_state->wrap_t));
> +
> assert(lp_is_simple_wrap_mode(bld->static_sampler_state->wrap_t));
> if (dims >= 3)
> - assert(lp_is_simple_wrap_mode(bld->static_state->wrap_r));
> +
> assert(lp_is_simple_wrap_mode(bld->static_sampler_state->wrap_r));
>
>
> /* make 16-bit fixed-pt builder context */
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_sample_soa.c
> b/src/gallium/auxiliary/gallivm/lp_bld_sample_soa.c
> index 918dd36..0e90194 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_sample_soa.c
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_sample_soa.c
> @@ -85,7 +85,7 @@ lp_build_sample_texel_soa(struct
> lp_build_sample_context *bld,
> LLVMValueRef mipoffsets,
> LLVMValueRef texel_out[4])
> {
> - const struct lp_sampler_static_state *static_state =
> bld->static_state;
> + const struct lp_static_sampler_state *static_state =
> bld->static_sampler_state;
> const unsigned dims = bld->dims;
> struct lp_build_context *int_coord_bld = &bld->int_coord_bld;
> LLVMBuilderRef builder = bld->gallivm->builder;
> @@ -317,7 +317,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> break;
>
> case PIPE_TEX_WRAP_CLAMP:
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -337,7 +337,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> struct lp_build_context abs_coord_bld = bld->coord_bld;
> abs_coord_bld.type.sign = FALSE;
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* mul by tex size */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -356,7 +356,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> }
>
> case PIPE_TEX_WRAP_CLAMP_TO_BORDER:
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -389,7 +389,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> case PIPE_TEX_WRAP_MIRROR_CLAMP:
> coord = lp_build_abs(coord_bld, coord);
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -411,7 +411,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> abs_coord_bld.type.sign = FALSE;
> coord = lp_build_abs(coord_bld, coord);
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -433,7 +433,7 @@ lp_build_sample_wrap_linear(struct
> lp_build_sample_context *bld,
> {
> coord = lp_build_abs(coord_bld, coord);
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -500,7 +500,7 @@ lp_build_sample_wrap_nearest(struct
> lp_build_sample_context *bld,
>
> case PIPE_TEX_WRAP_CLAMP:
> case PIPE_TEX_WRAP_CLAMP_TO_EDGE:
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -515,7 +515,7 @@ lp_build_sample_wrap_nearest(struct
> lp_build_sample_context *bld,
> break;
>
> case PIPE_TEX_WRAP_CLAMP_TO_BORDER:
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -528,7 +528,7 @@ lp_build_sample_wrap_nearest(struct
> lp_build_sample_context *bld,
> coord = lp_build_coord_mirror(bld, coord);
>
> /* scale coord to length */
> - assert(bld->static_state->normalized_coords);
> + assert(bld->static_sampler_state->normalized_coords);
> coord = lp_build_mul(coord_bld, coord, length_f);
>
> /* itrunc == ifloor here */
> @@ -542,7 +542,7 @@ lp_build_sample_wrap_nearest(struct
> lp_build_sample_context *bld,
> case PIPE_TEX_WRAP_MIRROR_CLAMP_TO_EDGE:
> coord = lp_build_abs(coord_bld, coord);
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -557,7 +557,7 @@ lp_build_sample_wrap_nearest(struct
> lp_build_sample_context *bld,
> case PIPE_TEX_WRAP_MIRROR_CLAMP_TO_BORDER:
> coord = lp_build_abs(coord_bld, coord);
>
> - if (bld->static_state->normalized_coords) {
> + if (bld->static_sampler_state->normalized_coords) {
> /* scale coord to length */
> coord = lp_build_mul(coord_bld, coord, length_f);
> }
> @@ -620,26 +620,26 @@ lp_build_sample_image_nearest(struct
> lp_build_sample_context *bld,
> * Compute integer texcoords.
> */
> x = lp_build_sample_wrap_nearest(bld, s, width_vec,
> flt_width_vec,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s);
> +
> bld->static_texture_state->pot_width,
> +
> bld->static_sampler_state->wrap_s);
> lp_build_name(x, "tex.x.wrapped");
>
> if (dims >= 2) {
> y = lp_build_sample_wrap_nearest(bld, t, height_vec,
> flt_height_vec,
> -
> bld->static_state->pot_height,
> - bld->static_state->wrap_t);
> +
> bld->static_texture_state->pot_height,
> +
> bld->static_sampler_state->wrap_t);
> lp_build_name(y, "tex.y.wrapped");
>
> if (dims == 3) {
> z = lp_build_sample_wrap_nearest(bld, r, depth_vec,
> flt_depth_vec,
> -
> bld->static_state->pot_depth,
> -
> bld->static_state->wrap_r);
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r);
> lp_build_name(z, "tex.z.wrapped");
> }
> }
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> z = r;
> lp_build_name(z, "tex.z.layer");
> }
> @@ -703,32 +703,32 @@ lp_build_sample_image_linear(struct
> lp_build_sample_context *bld,
> * Compute integer texcoords.
> */
> lp_build_sample_wrap_linear(bld, s, width_vec, flt_width_vec,
> - bld->static_state->pot_width,
> - bld->static_state->wrap_s,
> + bld->static_texture_state->pot_width,
> + bld->static_sampler_state->wrap_s,
> &x0, &x1, &s_fpart);
> lp_build_name(x0, "tex.x0.wrapped");
> lp_build_name(x1, "tex.x1.wrapped");
>
> if (dims >= 2) {
> lp_build_sample_wrap_linear(bld, t, height_vec,
> flt_height_vec,
> - bld->static_state->pot_height,
> - bld->static_state->wrap_t,
> +
> bld->static_texture_state->pot_height,
> + bld->static_sampler_state->wrap_t,
> &y0, &y1, &t_fpart);
> lp_build_name(y0, "tex.y0.wrapped");
> lp_build_name(y1, "tex.y1.wrapped");
>
> if (dims == 3) {
> lp_build_sample_wrap_linear(bld, r, depth_vec,
> flt_depth_vec,
> - bld->static_state->pot_depth,
> - bld->static_state->wrap_r,
> +
> bld->static_texture_state->pot_depth,
> +
> bld->static_sampler_state->wrap_r,
> &z0, &z1, &r_fpart);
> lp_build_name(z0, "tex.z0.wrapped");
> lp_build_name(z1, "tex.z1.wrapped");
> }
> }
> - if (bld->static_state->target == PIPE_TEXTURE_CUBE ||
> - bld->static_state->target == PIPE_TEXTURE_1D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_2D_ARRAY) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_CUBE ||
> + bld->static_texture_state->target == PIPE_TEXTURE_1D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY) {
> z0 = z1 = r; /* cube face or array layer */
> lp_build_name(z0, "tex.z0.layer");
> lp_build_name(z1, "tex.z1.layer");
> @@ -1004,7 +1004,8 @@ lp_build_layer_coord(struct
> lp_build_sample_context *bld,
> */
> static void
> lp_build_sample_common(struct lp_build_sample_context *bld,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> LLVMValueRef *s,
> LLVMValueRef *t,
> LLVMValueRef *r,
> @@ -1016,10 +1017,10 @@ lp_build_sample_common(struct
> lp_build_sample_context *bld,
> LLVMValueRef *ilevel0,
> LLVMValueRef *ilevel1)
> {
> - const unsigned mip_filter = bld->static_state->min_mip_filter;
> - const unsigned min_filter = bld->static_state->min_img_filter;
> - const unsigned mag_filter = bld->static_state->mag_img_filter;
> - const unsigned target = bld->static_state->target;
> + const unsigned mip_filter =
> bld->static_sampler_state->min_mip_filter;
> + const unsigned min_filter =
> bld->static_sampler_state->min_img_filter;
> + const unsigned mag_filter =
> bld->static_sampler_state->mag_img_filter;
> + const unsigned target = bld->static_texture_state->target;
> LLVMValueRef first_level;
> struct lp_derivatives face_derivs;
>
> @@ -1046,11 +1047,11 @@ lp_build_sample_common(struct
> lp_build_sample_context *bld,
> }
> else if (target == PIPE_TEXTURE_1D_ARRAY) {
> *r = lp_build_iround(&bld->coord_bld, *t);
> - *r = lp_build_layer_coord(bld, unit, *r);
> + *r = lp_build_layer_coord(bld, texture_index, *r);
> }
> else if (target == PIPE_TEXTURE_2D_ARRAY) {
> *r = lp_build_iround(&bld->coord_bld, *r);
> - *r = lp_build_layer_coord(bld, unit, *r);
> + *r = lp_build_layer_coord(bld, texture_index, *r);
> }
>
> /*
> @@ -1061,8 +1062,8 @@ lp_build_sample_common(struct
> lp_build_sample_context *bld,
> /* Need to compute lod either to choose mipmap levels or to
> * distinguish between minification/magnification with one
> mipmap level.
> */
> - lp_build_lod_selector(bld, unit, derivs,
> - lod_bias, explicit_lod,
> + lp_build_lod_selector(bld, texture_index, sampler_index,
> + derivs, lod_bias, explicit_lod,
> mip_filter,
> lod_ipart, lod_fpart);
> } else {
> @@ -1085,23 +1086,23 @@ lp_build_sample_common(struct
> lp_build_sample_context *bld,
> * XXX should probably disable that on other llvm versions.
> */
> assert(*lod_ipart);
> - lp_build_nearest_mip_level(bld, unit, *lod_ipart, ilevel0);
> + lp_build_nearest_mip_level(bld, texture_index, *lod_ipart,
> ilevel0);
> }
> else {
> first_level =
> bld->dynamic_state->first_level(bld->dynamic_state,
> - bld->gallivm,
> unit);
> + bld->gallivm,
> texture_index);
> first_level = lp_build_broadcast_scalar(&bld->perquadi_bld,
> first_level);
> *ilevel0 = first_level;
> }
> break;
> case PIPE_TEX_MIPFILTER_NEAREST:
> assert(*lod_ipart);
> - lp_build_nearest_mip_level(bld, unit, *lod_ipart, ilevel0);
> + lp_build_nearest_mip_level(bld, texture_index, *lod_ipart,
> ilevel0);
> break;
> case PIPE_TEX_MIPFILTER_LINEAR:
> assert(*lod_ipart);
> assert(*lod_fpart);
> - lp_build_linear_mip_levels(bld, unit,
> + lp_build_linear_mip_levels(bld, texture_index,
> *lod_ipart, lod_fpart,
> ilevel0, ilevel1);
> break;
> @@ -1127,9 +1128,9 @@ lp_build_sample_general(struct
> lp_build_sample_context *bld,
> {
> struct lp_build_context *int_bld = &bld->int_bld;
> LLVMBuilderRef builder = bld->gallivm->builder;
> - const unsigned mip_filter = bld->static_state->min_mip_filter;
> - const unsigned min_filter = bld->static_state->min_img_filter;
> - const unsigned mag_filter = bld->static_state->mag_img_filter;
> + const unsigned mip_filter =
> bld->static_sampler_state->min_mip_filter;
> + const unsigned min_filter =
> bld->static_sampler_state->min_img_filter;
> + const unsigned mag_filter =
> bld->static_sampler_state->mag_img_filter;
> LLVMValueRef texels[4];
> unsigned chan;
>
> @@ -1221,7 +1222,7 @@ lp_build_fetch_texel(struct
> lp_build_sample_context *bld,
> struct lp_build_context *perquadi_bld = &bld->perquadi_bld;
> struct lp_build_context *int_coord_bld = &bld->int_coord_bld;
> unsigned dims = bld->dims, chan;
> - unsigned target = bld->static_state->target;
> + unsigned target = bld->static_texture_state->target;
> LLVMValueRef size, ilevel;
> LLVMValueRef row_stride_vec = NULL, img_stride_vec = NULL;
> LLVMValueRef x = coords[0], y = coords[1], z = coords[2];
> @@ -1229,7 +1230,7 @@ lp_build_fetch_texel(struct
> lp_build_sample_context *bld,
> LLVMValueRef offset, out_of_bounds, out1;
>
> /* XXX just like ordinary sampling, we don't handle per-pixel lod
> (yet). */
> - if (explicit_lod && bld->static_state->target != PIPE_BUFFER) {
> + if (explicit_lod && bld->static_texture_state->target !=
> PIPE_BUFFER) {
> ilevel = lp_build_pack_aos_scalars(bld->gallivm,
> int_coord_bld->type,
> perquadi_bld->type,
> explicit_lod, 0);
> lp_build_nearest_mip_level(bld, unit, ilevel, &ilevel);
> @@ -1288,7 +1289,7 @@ lp_build_fetch_texel(struct
> lp_build_sample_context *bld,
> x, y, z, row_stride_vec, img_stride_vec,
> &offset, &i, &j);
>
> - if (bld->static_state->target != PIPE_BUFFER) {
> + if (bld->static_texture_state->target != PIPE_BUFFER) {
> offset = lp_build_add(int_coord_bld, offset,
> lp_build_get_mip_offsets(bld, ilevel));
> }
> @@ -1333,11 +1334,11 @@ lp_build_sample_compare(struct
> lp_build_sample_context *bld,
> LLVMValueRef res, p;
> const unsigned chan = 0;
>
> - if (bld->static_state->compare_mode == PIPE_TEX_COMPARE_NONE)
> + if (bld->static_sampler_state->compare_mode ==
> PIPE_TEX_COMPARE_NONE)
> return;
>
> - if (bld->static_state->target == PIPE_TEXTURE_2D_ARRAY ||
> - bld->static_state->target == PIPE_TEXTURE_CUBE) {
> + if (bld->static_texture_state->target == PIPE_TEXTURE_2D_ARRAY ||
> + bld->static_texture_state->target == PIPE_TEXTURE_CUBE) {
> p = coords[3];
> }
> else {
> @@ -1359,7 +1360,7 @@ lp_build_sample_compare(struct
> lp_build_sample_context *bld,
> bld->coord_bld.one);
>
> /* result = (p FUNC texel) ? 1 : 0 */
> - res = lp_build_cmp(texel_bld, bld->static_state->compare_func,
> + res = lp_build_cmp(texel_bld,
> bld->static_sampler_state->compare_func,
> p, texel[chan]);
> res = lp_build_select(texel_bld, res, texel_bld->one,
> texel_bld->zero);
>
> @@ -1400,11 +1401,13 @@ lp_build_sample_nop(struct gallivm_state
> *gallivm,
> */
> void
> lp_build_sample_soa(struct gallivm_state *gallivm,
> - const struct lp_sampler_static_state
> *static_state,
> + const struct lp_static_texture_state
> *static_texture_state,
> + const struct lp_static_sampler_state
> *static_sampler_state,
> struct lp_sampler_dynamic_state *dynamic_state,
> struct lp_type type,
> boolean is_fetch,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const LLVMValueRef *coords,
> const LLVMValueRef *offsets,
> const struct lp_derivatives *derivs,
> @@ -1412,10 +1415,11 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> LLVMValueRef explicit_lod, /* optional */
> LLVMValueRef texel_out[4])
> {
> - unsigned dims = texture_dims(static_state->target);
> + unsigned dims = texture_dims(static_texture_state->target);
> unsigned num_quads = type.length / 4;
> - unsigned mip_filter = static_state->min_mip_filter;
> + unsigned mip_filter;
> struct lp_build_sample_context bld;
> + struct lp_static_sampler_state derived_sampler_state =
> *static_sampler_state;
> LLVMTypeRef i32t = LLVMInt32TypeInContext(gallivm->context);
> LLVMBuilderRef builder = gallivm->builder;
> LLVMValueRef tex_width, tex_height, tex_depth;
> @@ -1424,7 +1428,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> LLVMValueRef r;
>
> if (0) {
> - enum pipe_format fmt = static_state->format;
> + enum pipe_format fmt = static_texture_state->format;
> debug_printf("Sample from %s\n", util_format_name(fmt));
> }
>
> @@ -1433,9 +1437,10 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> /* Setup our build context */
> memset(&bld, 0, sizeof bld);
> bld.gallivm = gallivm;
> - bld.static_state = static_state;
> + bld.static_sampler_state = &derived_sampler_state;
> + bld.static_texture_state = static_texture_state;
> bld.dynamic_state = dynamic_state;
> - bld.format_desc = util_format_description(static_state->format);
> + bld.format_desc =
> util_format_description(static_texture_state->format);
> bld.dims = dims;
>
> bld.vector_width = lp_type_width(type);
> @@ -1466,11 +1471,22 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> }
> }
>
> + if (!static_texture_state->level_zero_only) {
> + derived_sampler_state.min_mip_filter =
> static_sampler_state->min_mip_filter;
> + } else {
> + derived_sampler_state.min_mip_filter =
> PIPE_TEX_MIPFILTER_NONE;
> + }
> + mip_filter = derived_sampler_state.min_mip_filter;
> +
> + if (0) {
> + debug_printf(" .min_mip_filter = %u\n",
> derived_sampler_state.min_mip_filter);
> + }
> +
> /*
> * There are other situations where at least the multiple int
> lods could be
> * avoided like min and max lod being equal.
> */
> - if ((is_fetch && explicit_lod && bld.static_state->target !=
> PIPE_BUFFER) ||
> + if ((is_fetch && explicit_lod && bld.static_texture_state->target
> != PIPE_BUFFER) ||
> (!is_fetch && mip_filter != PIPE_TEX_MIPFILTER_NONE)) {
> bld.num_lods = num_quads;
> }
> @@ -1497,13 +1513,13 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> lp_build_context_init(&bld.perquadi_bld, gallivm,
> bld.perquadi_type);
>
> /* Get the dynamic state */
> - tex_width = dynamic_state->width(dynamic_state, gallivm, unit);
> - tex_height = dynamic_state->height(dynamic_state, gallivm, unit);
> - tex_depth = dynamic_state->depth(dynamic_state, gallivm, unit);
> - bld.row_stride_array = dynamic_state->row_stride(dynamic_state,
> gallivm, unit);
> - bld.img_stride_array = dynamic_state->img_stride(dynamic_state,
> gallivm, unit);
> - bld.base_ptr = dynamic_state->base_ptr(dynamic_state, gallivm,
> unit);
> - bld.mip_offsets = dynamic_state->mip_offsets(dynamic_state,
> gallivm, unit);
> + tex_width = dynamic_state->width(dynamic_state, gallivm,
> texture_index);
> + tex_height = dynamic_state->height(dynamic_state, gallivm,
> texture_index);
> + tex_depth = dynamic_state->depth(dynamic_state, gallivm,
> texture_index);
> + bld.row_stride_array = dynamic_state->row_stride(dynamic_state,
> gallivm, texture_index);
> + bld.img_stride_array = dynamic_state->img_stride(dynamic_state,
> gallivm, texture_index);
> + bld.base_ptr = dynamic_state->base_ptr(dynamic_state, gallivm,
> texture_index);
> + bld.mip_offsets = dynamic_state->mip_offsets(dynamic_state,
> gallivm, texture_index);
> /* Note that mip_offsets is an array[level] of offsets to texture
> images */
>
> s = coords[0];
> @@ -1536,7 +1552,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> }
>
> else if (is_fetch) {
> - lp_build_fetch_texel(&bld, unit, coords,
> + lp_build_fetch_texel(&bld, texture_index, coords,
> explicit_lod, offsets,
> texel_out);
> }
> @@ -1545,22 +1561,22 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> LLVMValueRef lod_ipart = NULL, lod_fpart = NULL;
> LLVMValueRef ilevel0 = NULL, ilevel1 = NULL;
> boolean use_aos = util_format_fits_8unorm(bld.format_desc) &&
> - lp_is_simple_wrap_mode(static_state->wrap_s)
> &&
> -
> lp_is_simple_wrap_mode(static_state->wrap_t);
> +
> lp_is_simple_wrap_mode(static_sampler_state->wrap_s)
> &&
> +
> lp_is_simple_wrap_mode(static_sampler_state->wrap_t);
>
> if ((gallivm_debug & GALLIVM_DEBUG_PERF) &&
> !use_aos && util_format_fits_8unorm(bld.format_desc)) {
> debug_printf("%s: using floating point linear filtering for
> %s\n",
> __FUNCTION__, bld.format_desc->short_name);
> debug_printf(" min_img %d mag_img %d mip %d wraps %d
> wrapt %d\n",
> - static_state->min_img_filter,
> - static_state->mag_img_filter,
> - static_state->min_mip_filter,
> - static_state->wrap_s,
> - static_state->wrap_t);
> + static_sampler_state->min_img_filter,
> + static_sampler_state->mag_img_filter,
> + static_sampler_state->min_mip_filter,
> + static_sampler_state->wrap_s,
> + static_sampler_state->wrap_t);
> }
>
> - lp_build_sample_common(&bld, unit,
> + lp_build_sample_common(&bld, texture_index, sampler_index,
> &s, &t, &r,
> derivs, lod_bias, explicit_lod,
> &lod_ipart, &lod_fpart,
> @@ -1586,7 +1602,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> }
> if (use_aos) {
> /* do sampling/filtering with fixed pt arithmetic */
> - lp_build_sample_aos(&bld, unit,
> + lp_build_sample_aos(&bld, sampler_index,
> s, t, r,
> lod_ipart, lod_fpart,
> ilevel0, ilevel1,
> @@ -1594,7 +1610,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> }
>
> else {
> - lp_build_sample_general(&bld, unit,
> + lp_build_sample_general(&bld, sampler_index,
> s, t, r,
> lod_ipart, lod_fpart,
> ilevel0, ilevel1,
> @@ -1614,7 +1630,8 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> /* Setup our build context */
> memset(&bld4, 0, sizeof bld4);
> bld4.gallivm = bld.gallivm;
> - bld4.static_state = bld.static_state;
> + bld4.static_texture_state = bld.static_texture_state;
> + bld4.static_sampler_state = bld.static_sampler_state;
> bld4.dynamic_state = bld.dynamic_state;
> bld4.format_desc = bld.format_desc;
> bld4.dims = bld.dims;
> @@ -1675,7 +1692,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
>
> if (use_aos) {
> /* do sampling/filtering with fixed pt arithmetic */
> - lp_build_sample_aos(&bld4, unit,
> + lp_build_sample_aos(&bld4, sampler_index,
> s4, t4, r4,
> lod_iparts, lod_fparts,
> ilevel0s, ilevel1s,
> @@ -1683,7 +1700,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> }
>
> else {
> - lp_build_sample_general(&bld4, unit,
> + lp_build_sample_general(&bld4, sampler_index,
> s4, t4, r4,
> lod_iparts, lod_fparts,
> ilevel0s, ilevel1s,
> @@ -1702,7 +1719,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
> lp_build_sample_compare(&bld, coords, texel_out);
> }
>
> - if (static_state->target != PIPE_BUFFER) {
> + if (static_texture_state->target != PIPE_BUFFER) {
> apply_sampler_swizzle(&bld, texel_out);
> }
>
> @@ -1721,7 +1738,7 @@ lp_build_sample_soa(struct gallivm_state
> *gallivm,
>
> void
> lp_build_size_query_soa(struct gallivm_state *gallivm,
> - const struct lp_sampler_static_state
> *static_state,
> + const struct lp_static_texture_state
> *static_state,
> struct lp_sampler_dynamic_state
> *dynamic_state,
> struct lp_type int_type,
> unsigned unit,
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_tgsi.h
> b/src/gallium/auxiliary/gallivm/lp_bld_tgsi.h
> index 16d2ed9..4898849 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_tgsi.h
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_tgsi.h
> @@ -173,7 +173,8 @@ struct lp_build_sampler_soa
> struct gallivm_state *gallivm,
> struct lp_type type,
> boolean is_fetch,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const LLVMValueRef *coords,
> const LLVMValueRef *offsets,
> const struct lp_derivatives *derivs,
> diff --git a/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
> b/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
> index fbeb805..0621fb4 100644
> --- a/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
> +++ b/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
> @@ -1331,7 +1331,8 @@ emit_tex( struct lp_build_tgsi_soa_context
> *bld,
> bld->bld_base.base.gallivm,
> bld->bld_base.base.type,
> FALSE,
> - unit, coords,
> + unit, unit,
> + coords,
> offsets,
> &derivs,
> lod_bias, explicit_lod,
> @@ -1417,7 +1418,8 @@ emit_txf( struct lp_build_tgsi_soa_context
> *bld,
> bld->bld_base.base.gallivm,
> bld->bld_base.base.type,
> TRUE,
> - unit, coords,
> + unit, unit,
> + coords,
> offsets,
> &derivs,
> NULL, explicit_lod,
> diff --git a/src/gallium/drivers/llvmpipe/lp_context.h
> b/src/gallium/drivers/llvmpipe/lp_context.h
> index b11a3d8..9ccb67b 100644
> --- a/src/gallium/drivers/llvmpipe/lp_context.h
> +++ b/src/gallium/drivers/llvmpipe/lp_context.h
> @@ -76,12 +76,12 @@ struct llvmpipe_context {
> struct pipe_framebuffer_state framebuffer;
> struct pipe_poly_stipple poly_stipple;
> struct pipe_scissor_state scissor;
> - struct pipe_sampler_view
> *sampler_views[PIPE_SHADER_TYPES][PIPE_MAX_SAMPLERS];
> + struct pipe_sampler_view
> *sampler_views[PIPE_SHADER_TYPES][PIPE_MAX_SHADER_SAMPLER_VIEWS];
>
> struct pipe_viewport_state viewport;
> struct pipe_vertex_buffer vertex_buffer[PIPE_MAX_ATTRIBS];
> struct pipe_index_buffer index_buffer;
> - struct pipe_resource *mapped_vs_tex[PIPE_MAX_SAMPLERS];
> + struct pipe_resource
> *mapped_vs_tex[PIPE_MAX_SHADER_SAMPLER_VIEWS];
>
> unsigned num_samplers[PIPE_SHADER_TYPES];
> unsigned num_sampler_views[PIPE_SHADER_TYPES];
> diff --git a/src/gallium/drivers/llvmpipe/lp_jit.c
> b/src/gallium/drivers/llvmpipe/lp_jit.c
> index ea7c805..d0a7916 100644
> --- a/src/gallium/drivers/llvmpipe/lp_jit.c
> +++ b/src/gallium/drivers/llvmpipe/lp_jit.c
> @@ -45,7 +45,7 @@ lp_jit_create_types(struct
> lp_fragment_shader_variant *lp)
> {
> struct gallivm_state *gallivm = lp->gallivm;
> LLVMContextRef lc = gallivm->context;
> - LLVMTypeRef texture_type;
> + LLVMTypeRef texture_type, sampler_type;
>
> /* struct lp_jit_texture */
> {
> @@ -61,11 +61,6 @@ lp_jit_create_types(struct
> lp_fragment_shader_variant *lp)
> elem_types[LP_JIT_TEXTURE_IMG_STRIDE] =
> elem_types[LP_JIT_TEXTURE_MIP_OFFSETS] =
> LLVMArrayType(LLVMInt32TypeInContext(lc),
> LP_MAX_TEXTURE_LEVELS);
> - elem_types[LP_JIT_TEXTURE_MIN_LOD] =
> - elem_types[LP_JIT_TEXTURE_MAX_LOD] =
> - elem_types[LP_JIT_TEXTURE_LOD_BIAS] =
> LLVMFloatTypeInContext(lc);
> - elem_types[LP_JIT_TEXTURE_BORDER_COLOR] =
> - LLVMArrayType(LLVMFloatTypeInContext(lc), 4);
>
> texture_type = LLVMStructTypeInContext(lc, elem_types,
> Elements(elem_types),
> 0);
> @@ -102,21 +97,41 @@ lp_jit_create_types(struct
> lp_fragment_shader_variant *lp)
> LP_CHECK_MEMBER_OFFSET(struct lp_jit_texture, mip_offsets,
> gallivm->target, texture_type,
> LP_JIT_TEXTURE_MIP_OFFSETS);
> - LP_CHECK_MEMBER_OFFSET(struct lp_jit_texture, min_lod,
> + LP_CHECK_STRUCT_SIZE(struct lp_jit_texture,
> + gallivm->target, texture_type);
> + }
> +
> + {
> + /* struct lp_jit_sampler */
> + LLVMTypeRef elem_types[LP_JIT_SAMPLER_NUM_FIELDS];
> + elem_types[LP_JIT_SAMPLER_MIN_LOD] =
> + elem_types[LP_JIT_SAMPLER_MAX_LOD] =
> + elem_types[LP_JIT_SAMPLER_LOD_BIAS] =
> LLVMFloatTypeInContext(lc);
> + elem_types[LP_JIT_SAMPLER_BORDER_COLOR] =
> + LLVMArrayType(LLVMFloatTypeInContext(lc), 4);
> +
> + sampler_type = LLVMStructTypeInContext(lc, elem_types,
> + Elements(elem_types),
> 0);
> +#if HAVE_LLVM < 0x0300
> + LLVMAddTypeName(gallivm->module, "texture", texture_type);
> +
> + LLVMInvalidateStructLayout(gallivm->target, texture_type);
> +#endif
> +
> + LP_CHECK_MEMBER_OFFSET(struct lp_jit_sampler, min_lod,
> gallivm->target, texture_type,
> - LP_JIT_TEXTURE_MIN_LOD);
> - LP_CHECK_MEMBER_OFFSET(struct lp_jit_texture, max_lod,
> + LP_JIT_SAMPLER_MIN_LOD);
> + LP_CHECK_MEMBER_OFFSET(struct lp_jit_sampler, max_lod,
> gallivm->target, texture_type,
> - LP_JIT_TEXTURE_MAX_LOD);
> - LP_CHECK_MEMBER_OFFSET(struct lp_jit_texture, lod_bias,
> + LP_JIT_SAMPLER_MAX_LOD);
> + LP_CHECK_MEMBER_OFFSET(struct lp_jit_sampler, lod_bias,
> gallivm->target, texture_type,
> - LP_JIT_TEXTURE_LOD_BIAS);
> - LP_CHECK_MEMBER_OFFSET(struct lp_jit_texture, border_color,
> + LP_JIT_SAMPLER_LOD_BIAS);
> + LP_CHECK_MEMBER_OFFSET(struct lp_jit_sampler, border_color,
> gallivm->target, texture_type,
> - LP_JIT_TEXTURE_BORDER_COLOR);
> -
> - LP_CHECK_STRUCT_SIZE(struct lp_jit_texture,
> - gallivm->target, texture_type);
> + LP_JIT_SAMPLER_BORDER_COLOR);
> + LP_CHECK_STRUCT_SIZE(struct lp_jit_sampler,
> + gallivm->target, sampler_type);
> }
>
> /* struct lp_jit_context */
> @@ -132,6 +147,8 @@ lp_jit_create_types(struct
> lp_fragment_shader_variant *lp)
> elem_types[LP_JIT_CTX_U8_BLEND_COLOR] =
> LLVMPointerType(LLVMInt8TypeInContext(lc), 0);
> elem_types[LP_JIT_CTX_F_BLEND_COLOR] =
> LLVMPointerType(LLVMFloatTypeInContext(lc), 0);
> elem_types[LP_JIT_CTX_TEXTURES] = LLVMArrayType(texture_type,
> +
> PIPE_MAX_SHADER_SAMPLER_VIEWS);
> + elem_types[LP_JIT_CTX_SAMPLERS] = LLVMArrayType(sampler_type,
> PIPE_MAX_SAMPLERS);
>
> context_type = LLVMStructTypeInContext(lc, elem_types,
> @@ -164,6 +181,9 @@ lp_jit_create_types(struct
> lp_fragment_shader_variant *lp)
> LP_CHECK_MEMBER_OFFSET(struct lp_jit_context, textures,
> gallivm->target, context_type,
> LP_JIT_CTX_TEXTURES);
> + LP_CHECK_MEMBER_OFFSET(struct lp_jit_context, samplers,
> + gallivm->target, context_type,
> + LP_JIT_CTX_SAMPLERS);
> LP_CHECK_STRUCT_SIZE(struct lp_jit_context,
> gallivm->target, context_type);
>
> diff --git a/src/gallium/drivers/llvmpipe/lp_jit.h
> b/src/gallium/drivers/llvmpipe/lp_jit.h
> index 5dc5bc4..3057c0d 100644
> --- a/src/gallium/drivers/llvmpipe/lp_jit.h
> +++ b/src/gallium/drivers/llvmpipe/lp_jit.h
> @@ -58,7 +58,11 @@ struct lp_jit_texture
> uint32_t row_stride[LP_MAX_TEXTURE_LEVELS];
> uint32_t img_stride[LP_MAX_TEXTURE_LEVELS];
> uint32_t mip_offsets[LP_MAX_TEXTURE_LEVELS];
> - /* sampler state, actually */
> +};
> +
> +
> +struct lp_jit_sampler
> +{
> float min_lod;
> float max_lod;
> float lod_bias;
> @@ -76,14 +80,18 @@ enum {
> LP_JIT_TEXTURE_ROW_STRIDE,
> LP_JIT_TEXTURE_IMG_STRIDE,
> LP_JIT_TEXTURE_MIP_OFFSETS,
> - LP_JIT_TEXTURE_MIN_LOD,
> - LP_JIT_TEXTURE_MAX_LOD,
> - LP_JIT_TEXTURE_LOD_BIAS,
> - LP_JIT_TEXTURE_BORDER_COLOR,
> LP_JIT_TEXTURE_NUM_FIELDS /* number of fields above */
> };
>
>
> +enum {
> + LP_JIT_SAMPLER_MIN_LOD,
> + LP_JIT_SAMPLER_MAX_LOD,
> + LP_JIT_SAMPLER_LOD_BIAS,
> + LP_JIT_SAMPLER_BORDER_COLOR,
> + LP_JIT_SAMPLER_NUM_FIELDS /* number of fields above */
> +};
> +
>
> /**
> * This structure is passed directly to the generated fragment
> shader.
> @@ -107,7 +115,8 @@ struct lp_jit_context
> uint8_t *u8_blend_color;
> float *f_blend_color;
>
> - struct lp_jit_texture textures[PIPE_MAX_SAMPLERS];
> + struct lp_jit_texture textures[PIPE_MAX_SHADER_SAMPLER_VIEWS];
> + struct lp_jit_sampler samplers[PIPE_MAX_SAMPLERS];
> };
>
>
> @@ -123,6 +132,7 @@ enum {
> LP_JIT_CTX_U8_BLEND_COLOR,
> LP_JIT_CTX_F_BLEND_COLOR,
> LP_JIT_CTX_TEXTURES,
> + LP_JIT_CTX_SAMPLERS,
> LP_JIT_CTX_COUNT
> };
>
> @@ -148,6 +158,8 @@ enum {
> #define lp_jit_context_textures(_gallivm, _ptr) \
> lp_build_struct_get_ptr(_gallivm, _ptr, LP_JIT_CTX_TEXTURES,
> "textures")
>
> +#define lp_jit_context_samplers(_gallivm, _ptr) \
> + lp_build_struct_get_ptr(_gallivm, _ptr, LP_JIT_CTX_SAMPLERS,
> "samplers")
>
>
> /**
> diff --git a/src/gallium/drivers/llvmpipe/lp_setup.c
> b/src/gallium/drivers/llvmpipe/lp_setup.c
> index ffa0fe6..b0bc4a8 100644
> --- a/src/gallium/drivers/llvmpipe/lp_setup.c
> +++ b/src/gallium/drivers/llvmpipe/lp_setup.c
> @@ -668,9 +668,9 @@ lp_setup_set_fragment_sampler_views(struct
> lp_setup_context *setup,
>
> LP_DBG(DEBUG_SETUP, "%s\n", __FUNCTION__);
>
> - assert(num <= PIPE_MAX_SAMPLERS);
> + assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> - for (i = 0; i < PIPE_MAX_SAMPLERS; i++) {
> + for (i = 0; i < PIPE_MAX_SHADER_SAMPLER_VIEWS; i++) {
> struct pipe_sampler_view *view = i < num ? views[i] : NULL;
>
> if (view) {
> @@ -780,13 +780,13 @@ lp_setup_set_fragment_sampler_state(struct
> lp_setup_context *setup,
> const struct pipe_sampler_state *sampler = i < num ?
> samplers[i] : NULL;
>
> if (sampler) {
> - struct lp_jit_texture *jit_tex;
> - jit_tex = &setup->fs.current.jit_context.textures[i];
> + struct lp_jit_sampler *jit_sam;
> + jit_sam = &setup->fs.current.jit_context.samplers[i];
>
> - jit_tex->min_lod = sampler->min_lod;
> - jit_tex->max_lod = sampler->max_lod;
> - jit_tex->lod_bias = sampler->lod_bias;
> - COPY_4V(jit_tex->border_color, sampler->border_color.f);
> + jit_sam->min_lod = sampler->min_lod;
> + jit_sam->max_lod = sampler->max_lod;
> + jit_sam->lod_bias = sampler->lod_bias;
> + COPY_4V(jit_sam->border_color, sampler->border_color.f);
> }
> }
>
> diff --git a/src/gallium/drivers/llvmpipe/lp_setup_context.h
> b/src/gallium/drivers/llvmpipe/lp_setup_context.h
> index 4d20dd3..0e2de64 100644
> --- a/src/gallium/drivers/llvmpipe/lp_setup_context.h
> +++ b/src/gallium/drivers/llvmpipe/lp_setup_context.h
> @@ -123,7 +123,7 @@ struct lp_setup_context
> struct {
> const struct lp_rast_state *stored; /**< what's in the scene
> */
> struct lp_rast_state current; /**< currently set state */
> - struct pipe_resource *current_tex[PIPE_MAX_SAMPLERS];
> + struct pipe_resource
> *current_tex[PIPE_MAX_SHADER_SAMPLER_VIEWS];
> } fs;
>
> /** fragment shader constants */
> diff --git a/src/gallium/drivers/llvmpipe/lp_state_fs.c
> b/src/gallium/drivers/llvmpipe/lp_state_fs.c
> index cf936d0..09f37e0 100644
> --- a/src/gallium/drivers/llvmpipe/lp_state_fs.c
> +++ b/src/gallium/drivers/llvmpipe/lp_state_fs.c
> @@ -1904,7 +1904,7 @@ generate_fragment(struct llvmpipe_context *lp,
> LLVMPositionBuilderAtEnd(builder, block);
>
> /* code generated texture sampling */
> - sampler = lp_llvm_sampler_soa_create(key->sampler, context_ptr);
> + sampler = lp_llvm_sampler_soa_create(key->state, context_ptr);
>
> zs_format_desc = util_format_description(key->zsbuf_format);
>
> @@ -2113,32 +2113,39 @@ dump_fs_variant_key(const struct
> lp_fragment_shader_variant_key *key)
> }
> debug_printf("blend.colormask = 0x%x\n",
> key->blend.rt[0].colormask);
> for (i = 0; i < key->nr_samplers; ++i) {
> + const struct lp_static_sampler_state *sampler =
> &key->state[i].sampler_state;
> debug_printf("sampler[%u] = \n", i);
> - debug_printf(" .format = %s\n",
> - util_format_name(key->sampler[i].format));
> - debug_printf(" .target = %s\n",
> - util_dump_tex_target(key->sampler[i].target,
> TRUE));
> - debug_printf(" .pot = %u %u %u\n",
> - key->sampler[i].pot_width,
> - key->sampler[i].pot_height,
> - key->sampler[i].pot_depth);
> debug_printf(" .wrap = %s %s %s\n",
> - util_dump_tex_wrap(key->sampler[i].wrap_s, TRUE),
> - util_dump_tex_wrap(key->sampler[i].wrap_t, TRUE),
> - util_dump_tex_wrap(key->sampler[i].wrap_r,
> TRUE));
> + util_dump_tex_wrap(sampler->wrap_s, TRUE),
> + util_dump_tex_wrap(sampler->wrap_t, TRUE),
> + util_dump_tex_wrap(sampler->wrap_r, TRUE));
> debug_printf(" .min_img_filter = %s\n",
> -
> util_dump_tex_filter(key->sampler[i].min_img_filter,
> TRUE));
> + util_dump_tex_filter(sampler->min_img_filter,
> TRUE));
> debug_printf(" .min_mip_filter = %s\n",
> -
> util_dump_tex_mipfilter(key->sampler[i].min_mip_filter,
> TRUE));
> + util_dump_tex_mipfilter(sampler->min_mip_filter,
> TRUE));
> debug_printf(" .mag_img_filter = %s\n",
> -
> util_dump_tex_filter(key->sampler[i].mag_img_filter,
> TRUE));
> - if (key->sampler[i].compare_mode != PIPE_TEX_COMPARE_NONE)
> - debug_printf(" .compare_func = %s\n",
> util_dump_func(key->sampler[i].compare_func, TRUE));
> - debug_printf(" .normalized_coords = %u\n",
> key->sampler[i].normalized_coords);
> - debug_printf(" .min_max_lod_equal = %u\n",
> key->sampler[i].min_max_lod_equal);
> - debug_printf(" .lod_bias_non_zero = %u\n",
> key->sampler[i].lod_bias_non_zero);
> - debug_printf(" .apply_min_lod = %u\n",
> key->sampler[i].apply_min_lod);
> - debug_printf(" .apply_max_lod = %u\n",
> key->sampler[i].apply_max_lod);
> + util_dump_tex_filter(sampler->mag_img_filter,
> TRUE));
> + if (sampler->compare_mode != PIPE_TEX_COMPARE_NONE)
> + debug_printf(" .compare_func = %s\n",
> util_dump_func(sampler->compare_func, TRUE));
> + debug_printf(" .normalized_coords = %u\n",
> sampler->normalized_coords);
> + debug_printf(" .min_max_lod_equal = %u\n",
> sampler->min_max_lod_equal);
> + debug_printf(" .lod_bias_non_zero = %u\n",
> sampler->lod_bias_non_zero);
> + debug_printf(" .apply_min_lod = %u\n",
> sampler->apply_min_lod);
> + debug_printf(" .apply_max_lod = %u\n",
> sampler->apply_max_lod);
> + }
> + for (i = 0; i < key->nr_sampler_views; ++i) {
> + const struct lp_static_texture_state *texture =
> &key->state[i].texture_state;
> + debug_printf("texture[%u] = \n", i);
> + debug_printf(" .format = %s\n",
> + util_format_name(texture->format));
> + debug_printf(" .target = %s\n",
> + util_dump_tex_target(texture->target, TRUE));
> + debug_printf(" .level_zero_only = %u\n",
> + texture->level_zero_only);
> + debug_printf(" .pot = %u %u %u\n",
> + texture->pot_width,
> + texture->pot_height,
> + texture->pot_depth);
> }
> }
>
> @@ -2251,6 +2258,7 @@ llvmpipe_create_fs_state(struct pipe_context
> *pipe,
> struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
> struct lp_fragment_shader *shader;
> int nr_samplers;
> + int nr_sampler_views;
> int i;
>
> shader = CALLOC_STRUCT(lp_fragment_shader);
> @@ -2274,9 +2282,10 @@ llvmpipe_create_fs_state(struct pipe_context
> *pipe,
> }
>
> nr_samplers = shader->info.base.file_max[TGSI_FILE_SAMPLER] + 1;
> + nr_sampler_views =
> shader->info.base.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
>
> shader->variant_key_size = Offset(struct
> lp_fragment_shader_variant_key,
> - sampler[nr_samplers]);
> + state[MAX2(nr_samplers,
> nr_sampler_views)]);
>
> for (i = 0; i < shader->info.base.num_inputs; i++) {
> shader->inputs[i].usage_mask =
> shader->info.base.input_usage_mask[i];
> @@ -2605,9 +2614,32 @@ make_variant_key(struct llvmpipe_context *lp,
>
> for(i = 0; i < key->nr_samplers; ++i) {
> if(shader->info.base.file_mask[TGSI_FILE_SAMPLER] & (1 << i))
> {
> - lp_sampler_static_state(&key->sampler[i],
> - lp->sampler_views[PIPE_SHADER_FRAGMENT][i],
> - lp->samplers[PIPE_SHADER_FRAGMENT][i]);
> +
> lp_sampler_static_sampler_state(&key->state[i].sampler_state,
> +
> lp->samplers[PIPE_SHADER_FRAGMENT][i]);
> + }
> + }
> +
> + /*
> + * XXX If TGSI_FILE_SAMPLER_VIEW exists assume all texture
> opcodes
> + * are dx10-style? Can't really have mixed opcodes, at least not
> + * if we want to skip the holes here (without rescanning tgsi).
> + */
> + if (shader->info.base.file_max[TGSI_FILE_SAMPLER_VIEW] != -1) {
> + key->nr_sampler_views =
> shader->info.base.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
> + for(i = 0; i < key->nr_sampler_views; ++i) {
> + if(shader->info.base.file_mask[TGSI_FILE_SAMPLER_VIEW] & (1
> << i)) {
> +
> lp_sampler_static_texture_state(&key->state[i].texture_state,
> +
> lp->sampler_views[PIPE_SHADER_FRAGMENT][i]);
> + }
> + }
> + }
> + else {
> + key->nr_sampler_views = key->nr_samplers;
> + for(i = 0; i < key->nr_sampler_views; ++i) {
> + if(shader->info.base.file_mask[TGSI_FILE_SAMPLER] & (1 <<
> i)) {
> +
> lp_sampler_static_texture_state(&key->state[i].texture_state,
> +
> lp->sampler_views[PIPE_SHADER_FRAGMENT][i]);
> + }
> }
> }
> }
> diff --git a/src/gallium/drivers/llvmpipe/lp_state_fs.h
> b/src/gallium/drivers/llvmpipe/lp_state_fs.h
> index 306f5f9..dbe657c 100644
> --- a/src/gallium/drivers/llvmpipe/lp_state_fs.h
> +++ b/src/gallium/drivers/llvmpipe/lp_state_fs.h
> @@ -46,6 +46,18 @@ struct lp_fragment_shader;
> #define RAST_WHOLE 0
> #define RAST_EDGE_TEST 1
>
> +struct lp_sampler_static_state
> +{
> + /*
> + * These attributes are effectively interleaved for more sane key
> handling.
> + * However, there might be lots of null space if the amount of
> samplers and
> + * textures isn't the same.
> + */
> + struct lp_static_sampler_state sampler_state;
> + struct lp_static_texture_state texture_state;
> +};
> +
> +
>
> struct lp_fragment_shader_variant_key
> {
> @@ -59,14 +71,15 @@ struct lp_fragment_shader_variant_key
> } alpha;
>
> unsigned nr_cbufs:8;
> - unsigned nr_samplers:8; /* actually derivable from just the
> shader */
> + unsigned nr_samplers:8; /* actually derivable from just the
> shader */
> + unsigned nr_sampler_views:8; /* actually derivable from just the
> shader */
> unsigned flatshade:1;
> unsigned occlusion_count:1;
>
> enum pipe_format zsbuf_format;
> enum pipe_format cbuf_format[PIPE_MAX_COLOR_BUFS];
>
> - struct lp_sampler_static_state sampler[PIPE_MAX_SAMPLERS];
> + struct lp_sampler_static_state
> state[PIPE_MAX_SHADER_SAMPLER_VIEWS];
> };
>
>
> diff --git a/src/gallium/drivers/llvmpipe/lp_state_sampler.c
> b/src/gallium/drivers/llvmpipe/lp_state_sampler.c
> index e7429cc..9736ca9 100644
> --- a/src/gallium/drivers/llvmpipe/lp_state_sampler.c
> +++ b/src/gallium/drivers/llvmpipe/lp_state_sampler.c
> @@ -143,7 +143,7 @@ llvmpipe_set_sampler_views(struct pipe_context
> *pipe,
> struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
> uint i;
>
> - assert(num <= PIPE_MAX_SAMPLERS);
> + assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> assert(shader < PIPE_SHADER_TYPES);
> assert(start + num <= Elements(llvmpipe->sampler_views[shader]));
> @@ -258,11 +258,11 @@ llvmpipe_prepare_vertex_sampling(struct
> llvmpipe_context *lp,
> uint32_t mip_offsets[PIPE_MAX_TEXTURE_LEVELS];
> const void *addr;
>
> - assert(num <= PIPE_MAX_SAMPLERS);
> + assert(num <= PIPE_MAX_SHADER_SAMPLER_VIEWS);
> if (!num)
> return;
>
> - for (i = 0; i < PIPE_MAX_SAMPLERS; i++) {
> + for (i = 0; i < PIPE_MAX_SHADER_SAMPLER_VIEWS; i++) {
> struct pipe_sampler_view *view = i < num ? views[i] : NULL;
>
> if (view) {
> diff --git a/src/gallium/drivers/llvmpipe/lp_state_setup.c
> b/src/gallium/drivers/llvmpipe/lp_state_setup.c
> index f44eed4..9dd337a 100644
> --- a/src/gallium/drivers/llvmpipe/lp_state_setup.c
> +++ b/src/gallium/drivers/llvmpipe/lp_state_setup.c
> @@ -795,19 +795,19 @@ fail:
>
> static void
> lp_make_setup_variant_key(struct llvmpipe_context *lp,
> - struct lp_setup_variant_key *key)
> + struct lp_setup_variant_key *key)
> {
> struct lp_fragment_shader *fs = lp->fs;
> unsigned i;
>
> assert(sizeof key->inputs[0] == sizeof(uint));
> -
> +
> key->num_inputs = fs->info.base.num_inputs;
> key->flatshade_first = lp->rasterizer->flatshade_first;
> key->pixel_center_half = lp->rasterizer->gl_rasterization_rules;
> key->twoside = lp->rasterizer->light_twoside;
> key->size = Offset(struct lp_setup_variant_key,
> - inputs[key->num_inputs]);
> + inputs[key->num_inputs]);
>
> key->color_slot = lp->color_slot [0];
> key->bcolor_slot = lp->bcolor_slot[0];
> @@ -825,9 +825,9 @@ lp_make_setup_variant_key(struct llvmpipe_context
> *lp,
> for (i = 0; i < key->num_inputs; i++) {
> if (key->inputs[i].interp == LP_INTERP_COLOR) {
> if (lp->rasterizer->flatshade)
> - key->inputs[i].interp = LP_INTERP_CONSTANT;
> - else
> - key->inputs[i].interp = LP_INTERP_PERSPECTIVE;
> + key->inputs[i].interp = LP_INTERP_CONSTANT;
> + else
> + key->inputs[i].interp = LP_INTERP_PERSPECTIVE;
> }
> }
>
> @@ -836,11 +836,11 @@ lp_make_setup_variant_key(struct
> llvmpipe_context *lp,
>
> static void
> remove_setup_variant(struct llvmpipe_context *lp,
> - struct lp_setup_variant *variant)
> + struct lp_setup_variant *variant)
> {
> if (gallivm_debug & GALLIVM_DEBUG_IR) {
> debug_printf("llvmpipe: del setup_variant #%u total %u\n",
> - variant->no, lp->nr_setup_variants);
> + variant->no, lp->nr_setup_variants);
> }
>
> if (variant->function) {
> diff --git a/src/gallium/drivers/llvmpipe/lp_tex_sample.c
> b/src/gallium/drivers/llvmpipe/lp_tex_sample.c
> index 0bd5c4a..25125a0 100644
> --- a/src/gallium/drivers/llvmpipe/lp_tex_sample.c
> +++ b/src/gallium/drivers/llvmpipe/lp_tex_sample.c
> @@ -49,6 +49,7 @@
> #include "gallivm/lp_bld_tgsi.h"
> #include "lp_jit.h"
> #include "lp_tex_sample.h"
> +#include "lp_state_fs.h"
> #include "lp_debug.h"
>
>
> @@ -103,7 +104,7 @@ lp_llvm_texture_member(const struct
> lp_sampler_dynamic_state *base,
> LLVMValueRef ptr;
> LLVMValueRef res;
>
> - assert(unit < PIPE_MAX_SAMPLERS);
> + assert(unit < PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> /* context[0] */
> indices[0] = lp_build_const_int32(gallivm, 0);
> @@ -155,10 +156,69 @@ LP_LLVM_TEXTURE_MEMBER(base_ptr,
> LP_JIT_TEXTURE_BASE, TRUE)
> LP_LLVM_TEXTURE_MEMBER(row_stride, LP_JIT_TEXTURE_ROW_STRIDE, FALSE)
> LP_LLVM_TEXTURE_MEMBER(img_stride, LP_JIT_TEXTURE_IMG_STRIDE, FALSE)
> LP_LLVM_TEXTURE_MEMBER(mip_offsets, LP_JIT_TEXTURE_MIP_OFFSETS,
> FALSE)
> -LP_LLVM_TEXTURE_MEMBER(min_lod, LP_JIT_TEXTURE_MIN_LOD, TRUE)
> -LP_LLVM_TEXTURE_MEMBER(max_lod, LP_JIT_TEXTURE_MAX_LOD, TRUE)
> -LP_LLVM_TEXTURE_MEMBER(lod_bias, LP_JIT_TEXTURE_LOD_BIAS, TRUE)
> -LP_LLVM_TEXTURE_MEMBER(border_color, LP_JIT_TEXTURE_BORDER_COLOR,
> FALSE)
> +
> +
> +/**
> + * Fetch the specified member of the lp_jit_sampler structure.
> + * \param emit_load if TRUE, emit the LLVM load instruction to
> actually
> + * fetch the field's value. Otherwise, just emit
> the
> + * GEP code to address the field.
> + *
> + * @sa http://llvm.org/docs/GetElementPtr.html
> + */
> +static LLVMValueRef
> +lp_llvm_sampler_member(const struct lp_sampler_dynamic_state *base,
> + struct gallivm_state *gallivm,
> + unsigned unit,
> + unsigned member_index,
> + const char *member_name,
> + boolean emit_load)
> +{
> + struct llvmpipe_sampler_dynamic_state *state =
> + (struct llvmpipe_sampler_dynamic_state *)base;
> + LLVMBuilderRef builder = gallivm->builder;
> + LLVMValueRef indices[4];
> + LLVMValueRef ptr;
> + LLVMValueRef res;
> +
> + assert(unit < PIPE_MAX_SAMPLERS);
> +
> + /* context[0] */
> + indices[0] = lp_build_const_int32(gallivm, 0);
> + /* context[0].samplers */
> + indices[1] = lp_build_const_int32(gallivm, LP_JIT_CTX_SAMPLERS);
> + /* context[0].samplers[unit] */
> + indices[2] = lp_build_const_int32(gallivm, unit);
> + /* context[0].samplers[unit].member */
> + indices[3] = lp_build_const_int32(gallivm, member_index);
> +
> + ptr = LLVMBuildGEP(builder, state->context_ptr, indices,
> Elements(indices), "");
> +
> + if (emit_load)
> + res = LLVMBuildLoad(builder, ptr, "");
> + else
> + res = ptr;
> +
> + lp_build_name(res, "context.sampler%u.%s", unit, member_name);
> +
> + return res;
> +}
> +
> +
> +#define LP_LLVM_SAMPLER_MEMBER(_name, _index, _emit_load) \
> + static LLVMValueRef \
> + lp_llvm_sampler_##_name( const struct lp_sampler_dynamic_state
> *base, \
> + struct gallivm_state *gallivm, \
> + unsigned unit) \
> + { \
> + return lp_llvm_sampler_member(base, gallivm, unit, _index,
> #_name, _emit_load ); \
> + }
> +
> +
> +LP_LLVM_SAMPLER_MEMBER(min_lod, LP_JIT_SAMPLER_MIN_LOD, TRUE)
> +LP_LLVM_SAMPLER_MEMBER(max_lod, LP_JIT_SAMPLER_MAX_LOD, TRUE)
> +LP_LLVM_SAMPLER_MEMBER(lod_bias, LP_JIT_SAMPLER_LOD_BIAS, TRUE)
> +LP_LLVM_SAMPLER_MEMBER(border_color, LP_JIT_SAMPLER_BORDER_COLOR,
> FALSE)
>
>
> static void
> @@ -177,7 +237,8 @@ lp_llvm_sampler_soa_emit_fetch_texel(const struct
> lp_build_sampler_soa *base,
> struct gallivm_state *gallivm,
> struct lp_type type,
> boolean is_fetch,
> - unsigned unit,
> + unsigned texture_index,
> + unsigned sampler_index,
> const LLVMValueRef *coords,
> const LLVMValueRef *offsets,
> const struct lp_derivatives
> *derivs,
> @@ -187,7 +248,8 @@ lp_llvm_sampler_soa_emit_fetch_texel(const struct
> lp_build_sampler_soa *base,
> {
> struct lp_llvm_sampler_soa *sampler = (struct lp_llvm_sampler_soa
> *)base;
>
> - assert(unit < PIPE_MAX_SAMPLERS);
> + assert(sampler_index < PIPE_MAX_SAMPLERS);
> + assert(texture_index < PIPE_MAX_SHADER_SAMPLER_VIEWS);
>
> if (LP_PERF & PERF_NO_TEX) {
> lp_build_sample_nop(gallivm, type, coords, texel);
> @@ -195,11 +257,13 @@ lp_llvm_sampler_soa_emit_fetch_texel(const
> struct lp_build_sampler_soa *base,
> }
>
> lp_build_sample_soa(gallivm,
> - &sampler->dynamic_state.static_state[unit],
> +
> &sampler->dynamic_state.static_state[texture_index].texture_state,
> +
> &sampler->dynamic_state.static_state[sampler_index].sampler_state,
> &sampler->dynamic_state.base,
> type,
> is_fetch,
> - unit,
> + texture_index,
> + sampler_index,
> coords,
> offsets,
> derivs,
> @@ -221,14 +285,14 @@ lp_llvm_sampler_soa_emit_size_query(const
> struct lp_build_sampler_soa *base,
> struct lp_llvm_sampler_soa *sampler = (struct lp_llvm_sampler_soa
> *)base;
>
> assert(unit < PIPE_MAX_SAMPLERS);
> -
> +
> lp_build_size_query_soa(gallivm,
> - &sampler->dynamic_state.static_state[unit],
> - &sampler->dynamic_state.base,
> +
> &sampler->dynamic_state.static_state[unit].texture_state,
> + &sampler->dynamic_state.base,
> type,
> - unit,
> - explicit_lod,
> - sizes_out);
> + unit,
> + explicit_lod,
> + sizes_out);
> }
>
>
> @@ -254,10 +318,10 @@ lp_llvm_sampler_soa_create(const struct
> lp_sampler_static_state *static_state,
> sampler->dynamic_state.base.row_stride =
> lp_llvm_texture_row_stride;
> sampler->dynamic_state.base.img_stride =
> lp_llvm_texture_img_stride;
> sampler->dynamic_state.base.mip_offsets =
> lp_llvm_texture_mip_offsets;
> - sampler->dynamic_state.base.min_lod = lp_llvm_texture_min_lod;
> - sampler->dynamic_state.base.max_lod = lp_llvm_texture_max_lod;
> - sampler->dynamic_state.base.lod_bias = lp_llvm_texture_lod_bias;
> - sampler->dynamic_state.base.border_color =
> lp_llvm_texture_border_color;
> + sampler->dynamic_state.base.min_lod = lp_llvm_sampler_min_lod;
> + sampler->dynamic_state.base.max_lod = lp_llvm_sampler_max_lod;
> + sampler->dynamic_state.base.lod_bias = lp_llvm_sampler_lod_bias;
> + sampler->dynamic_state.base.border_color =
> lp_llvm_sampler_border_color;
>
> sampler->dynamic_state.static_state = static_state;
> sampler->dynamic_state.context_ptr = context_ptr;
> --
> 1.7.9.5
>
More information about the mesa-dev
mailing list