diff options
author | Ilia Mirkin <imirkin@alum.mit.edu> | 2014-11-29 19:24:35 -0500 |
---|---|---|
committer | Ilia Mirkin <imirkin@alum.mit.edu> | 2014-11-30 13:04:28 -0500 |
commit | 82104c19f304a0e953172ad61d149640f0512fa0 (patch) | |
tree | 7a4349d42e6050bee3e8579e423b93266ba8d7b8 /src/gallium | |
parent | 8e336ef55bacae58fc099a8b8a4b7d3d007c4434 (diff) |
freedreno/a3xx: enable sampling from integer textures
We need to produce a u32 destination type on integer sampling
instructions, so keep that in a shader key set based on the
currently-bound textures.
Signed-off-by: Ilia Mirkin <imirkin@alum.mit.edu>
Diffstat (limited to 'src/gallium')
-rw-r--r-- | src/gallium/drivers/freedreno/a3xx/fd3_context.h | 3 | ||||
-rw-r--r-- | src/gallium/drivers/freedreno/a3xx/fd3_draw.c | 11 | ||||
-rw-r--r-- | src/gallium/drivers/freedreno/a3xx/fd3_texture.c | 35 | ||||
-rw-r--r-- | src/gallium/drivers/freedreno/ir3/ir3_compiler.c | 8 | ||||
-rw-r--r-- | src/gallium/drivers/freedreno/ir3/ir3_shader.h | 3 |
5 files changed, 55 insertions, 5 deletions
diff --git a/src/gallium/drivers/freedreno/a3xx/fd3_context.h b/src/gallium/drivers/freedreno/a3xx/fd3_context.h index 77e4605e550..4e3f521716e 100644 --- a/src/gallium/drivers/freedreno/a3xx/fd3_context.h +++ b/src/gallium/drivers/freedreno/a3xx/fd3_context.h @@ -105,6 +105,9 @@ struct fd3_context { */ unsigned fsaturate_s, fsaturate_t, fsaturate_r; + /* bitmask of integer texture samplers */ + uint16_t vinteger_s, finteger_s; + /* some state changes require a different shader variant. Keep * track of this so we know when we need to re-emit shader state * due to variant change. See fixup_shader_state() diff --git a/src/gallium/drivers/freedreno/a3xx/fd3_draw.c b/src/gallium/drivers/freedreno/a3xx/fd3_draw.c index 2ae4cfbcbd9..b06d4253a99 100644 --- a/src/gallium/drivers/freedreno/a3xx/fd3_draw.c +++ b/src/gallium/drivers/freedreno/a3xx/fd3_draw.c @@ -88,12 +88,14 @@ fixup_shader_state(struct fd_context *ctx, struct ir3_shader_key *key) if (last_key->has_per_samp || key->has_per_samp) { if ((last_key->vsaturate_s != key->vsaturate_s) || (last_key->vsaturate_t != key->vsaturate_t) || - (last_key->vsaturate_r != key->vsaturate_r)) + (last_key->vsaturate_r != key->vsaturate_r) || + (last_key->vinteger_s != key->vinteger_s)) ctx->prog.dirty |= FD_SHADER_DIRTY_VP; if ((last_key->fsaturate_s != key->fsaturate_s) || (last_key->fsaturate_t != key->fsaturate_t) || - (last_key->fsaturate_r != key->fsaturate_r)) + (last_key->fsaturate_r != key->fsaturate_r) || + (last_key->finteger_s != key->finteger_s)) ctx->prog.dirty |= FD_SHADER_DIRTY_FP; } @@ -127,13 +129,16 @@ fd3_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info) // TODO set .half_precision based on render target format, // ie. float16 and smaller use half, float32 use full.. .half_precision = !!(fd_mesa_debug & FD_DBG_FRAGHALF), - .has_per_samp = fd3_ctx->fsaturate || fd3_ctx->vsaturate, + .has_per_samp = (fd3_ctx->fsaturate || fd3_ctx->vsaturate || + fd3_ctx->vinteger_s || fd3_ctx->finteger_s), .vsaturate_s = fd3_ctx->vsaturate_s, .vsaturate_t = fd3_ctx->vsaturate_t, .vsaturate_r = fd3_ctx->vsaturate_r, .fsaturate_s = fd3_ctx->fsaturate_s, .fsaturate_t = fd3_ctx->fsaturate_t, .fsaturate_r = fd3_ctx->fsaturate_r, + .vinteger_s = fd3_ctx->vinteger_s, + .finteger_s = fd3_ctx->finteger_s, }, .format = pipe_surface_format(pfb->cbufs[0]), .rasterflat = ctx->rasterizer && ctx->rasterizer->flatshade, diff --git a/src/gallium/drivers/freedreno/a3xx/fd3_texture.c b/src/gallium/drivers/freedreno/a3xx/fd3_texture.c index c573c0ea9c0..c35f9b339ee 100644 --- a/src/gallium/drivers/freedreno/a3xx/fd3_texture.c +++ b/src/gallium/drivers/freedreno/a3xx/fd3_texture.c @@ -261,11 +261,44 @@ fd3_sampler_view_create(struct pipe_context *pctx, struct pipe_resource *prsc, return &so->base; } +static void +fd3_set_sampler_views(struct pipe_context *pctx, unsigned shader, + unsigned start, unsigned nr, + struct pipe_sampler_view **views) +{ + struct fd_context *ctx = fd_context(pctx); + struct fd3_context *fd3_ctx = fd3_context(ctx); + struct fd_texture_stateobj *tex; + uint16_t integer_s = 0, *ptr; + int i; + + fd_set_sampler_views(pctx, shader, start, nr, views); + + switch (shader) { + case PIPE_SHADER_FRAGMENT: + tex = &ctx->fragtex; + ptr = &fd3_ctx->finteger_s; + break; + case PIPE_SHADER_VERTEX: + tex = &ctx->verttex; + ptr = &fd3_ctx->vinteger_s; + break; + default: + return; + } + + for (i = 0; i < tex->num_textures; i++) + if (util_format_is_pure_integer(tex->textures[i]->format)) + integer_s |= 1 << i; + *ptr = integer_s; +} + + void fd3_texture_init(struct pipe_context *pctx) { pctx->create_sampler_state = fd3_sampler_state_create; pctx->bind_sampler_states = fd3_sampler_states_bind; pctx->create_sampler_view = fd3_sampler_view_create; - pctx->set_sampler_views = fd_set_sampler_views; + pctx->set_sampler_views = fd3_set_sampler_views; } diff --git a/src/gallium/drivers/freedreno/ir3/ir3_compiler.c b/src/gallium/drivers/freedreno/ir3/ir3_compiler.c index da72c5c33f7..6cc21acaf3f 100644 --- a/src/gallium/drivers/freedreno/ir3/ir3_compiler.c +++ b/src/gallium/drivers/freedreno/ir3/ir3_compiler.c @@ -53,6 +53,7 @@ struct ir3_compile_context { bool free_tokens; struct ir3 *ir; struct ir3_shader_variant *so; + uint16_t integer_s; struct ir3_block *block; struct ir3_instruction *current_instr; @@ -159,11 +160,13 @@ compile_init(struct ir3_compile_context *ctx, struct ir3_shader_variant *so, lconfig.saturate_s = so->key.fsaturate_s; lconfig.saturate_t = so->key.fsaturate_t; lconfig.saturate_r = so->key.fsaturate_r; + ctx->integer_s = so->key.finteger_s; break; case SHADER_VERTEX: lconfig.saturate_s = so->key.vsaturate_s; lconfig.saturate_t = so->key.vsaturate_t; lconfig.saturate_r = so->key.vsaturate_r; + ctx->integer_s = so->key.vinteger_s; break; } @@ -1345,7 +1348,10 @@ trans_samp(const struct instr_translater *t, } instr = instr_create(ctx, 5, t->opc); - instr->cat5.type = get_ftype(ctx); + if (ctx->integer_s & (1 << samp->Index)) + instr->cat5.type = get_utype(ctx); + else + instr->cat5.type = get_ftype(ctx); instr->cat5.samp = samp->Index; instr->cat5.tex = samp->Index; instr->flags |= tinf.flags; diff --git a/src/gallium/drivers/freedreno/ir3/ir3_shader.h b/src/gallium/drivers/freedreno/ir3/ir3_shader.h index f70886e2d3b..89442cec128 100644 --- a/src/gallium/drivers/freedreno/ir3/ir3_shader.h +++ b/src/gallium/drivers/freedreno/ir3/ir3_shader.h @@ -91,6 +91,9 @@ struct ir3_shader_key { */ uint16_t fsaturate_s, fsaturate_t, fsaturate_r; + /* bitmask of sampler which produces integer outputs: + */ + uint16_t vinteger_s, finteger_s; }; static inline bool |