summaryrefslogtreecommitdiffstats
path: root/src/gallium/auxiliary/draw/draw_aaline.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/gallium/auxiliary/draw/draw_aaline.c')
-rw-r--r--src/gallium/auxiliary/draw/draw_aaline.c76
1 files changed, 55 insertions, 21 deletions
diff --git a/src/gallium/auxiliary/draw/draw_aaline.c b/src/gallium/auxiliary/draw/draw_aaline.c
index cc1873abada..e8d2a45102c 100644
--- a/src/gallium/auxiliary/draw/draw_aaline.c
+++ b/src/gallium/auxiliary/draw/draw_aaline.c
@@ -61,6 +61,8 @@ struct aaline_fragment_shader
void *aaline_fs;
void *aapoint_fs; /* not yet */
void *sprite_fs; /* not yet */
+ uint sampler_unit;
+ int generic_attrib; /**< texcoord/generic used for texture */
};
@@ -117,7 +119,8 @@ struct aa_transform_context {
struct tgsi_transform_context base;
uint tempsUsed; /**< bitmask */
int colorOutput; /**< which output is the primary color */
- int maxSampler; /**< max sampler index found */
+ uint samplersUsed; /**< bitfield of samplers used */
+ int freeSampler; /** an available sampler for the pstipple */
int maxInput, maxGeneric; /**< max input index found */
int colorTemp, texTemp; /**< temp registers */
boolean firstInstruction;
@@ -140,8 +143,11 @@ aa_transform_decl(struct tgsi_transform_context *ctx,
aactx->colorOutput = decl->u.DeclarationRange.First;
}
else if (decl->Declaration.File == TGSI_FILE_SAMPLER) {
- if ((int) decl->u.DeclarationRange.Last > aactx->maxSampler)
- aactx->maxSampler = decl->u.DeclarationRange.Last + 1;
+ uint i;
+ for (i = decl->u.DeclarationRange.First;
+ i <= decl->u.DeclarationRange.Last; i++) {
+ aactx->samplersUsed |= 1 << i;
+ }
}
else if (decl->Declaration.File == TGSI_FILE_INPUT) {
if ((int) decl->u.DeclarationRange.Last > aactx->maxInput)
@@ -164,6 +170,21 @@ aa_transform_decl(struct tgsi_transform_context *ctx,
/**
+ * Find the lowest zero bit in the given word, or -1 if bitfield is all ones.
+ */
+static int
+free_bit(uint bitfield)
+{
+ int i;
+ for (i = 0; i < 32; i++) {
+ if ((bitfield & (1 << i)) == 0)
+ return i;
+ }
+ return -1;
+}
+
+
+/**
* TGSI instruction transform callback.
* Replace writes to result.color w/ a temp reg.
* Upon END instruction, insert texture sampling code for antialiasing.
@@ -180,6 +201,11 @@ aa_transform_inst(struct tgsi_transform_context *ctx,
struct tgsi_full_declaration decl;
uint i;
+ /* find free sampler */
+ aactx->freeSampler = free_bit(aactx->samplersUsed);
+ if (aactx->freeSampler >= PIPE_MAX_SAMPLERS)
+ aactx->freeSampler = PIPE_MAX_SAMPLERS - 1;
+
/* find two free temp regs */
for (i = 0; i < 32; i++) {
if ((aactx->tempsUsed & (1 << i)) == 0) {
@@ -212,7 +238,7 @@ aa_transform_inst(struct tgsi_transform_context *ctx,
decl = tgsi_default_full_declaration();
decl.Declaration.File = TGSI_FILE_SAMPLER;
decl.u.DeclarationRange.First =
- decl.u.DeclarationRange.Last = aactx->maxSampler + 1;
+ decl.u.DeclarationRange.Last = aactx->freeSampler;
ctx->emit_declaration(ctx, &decl);
/* declare new temp regs */
@@ -246,7 +272,7 @@ aa_transform_inst(struct tgsi_transform_context *ctx,
newInst.FullSrcRegisters[0].SrcRegister.File = TGSI_FILE_INPUT;
newInst.FullSrcRegisters[0].SrcRegister.Index = aactx->maxInput + 1;
newInst.FullSrcRegisters[1].SrcRegister.File = TGSI_FILE_SAMPLER;
- newInst.FullSrcRegisters[1].SrcRegister.Index = aactx->maxSampler + 1;
+ newInst.FullSrcRegisters[1].SrcRegister.Index = aactx->freeSampler;
ctx->emit_instruction(ctx, &newInst);
@@ -311,7 +337,7 @@ static void
generate_aaline_fs(struct aaline_stage *aaline)
{
const struct pipe_shader_state *orig_fs = &aaline->fs->state;
- struct draw_context *draw = aaline->stage.draw;
+ //struct draw_context *draw = aaline->stage.draw;
struct pipe_shader_state aaline_fs;
struct aa_transform_context transform;
@@ -322,7 +348,6 @@ generate_aaline_fs(struct aaline_stage *aaline)
memset(&transform, 0, sizeof(transform));
transform.colorOutput = -1;
- transform.maxSampler = -1;
transform.maxInput = -1;
transform.maxGeneric = -1;
transform.colorTemp = -1;
@@ -340,14 +365,12 @@ generate_aaline_fs(struct aaline_stage *aaline)
tgsi_dump(aaline_fs.tokens, 0);
#endif
+ aaline->fs->sampler_unit = transform.freeSampler;
+
aaline->fs->aaline_fs
= aaline->driver_create_fs_state(aaline->pipe, &aaline_fs);
- /* advertise the extra post-transform vertex attributes which will have
- * the texcoords.
- */
- draw->extra_vp_outputs.semantic_name = TGSI_SEMANTIC_GENERIC;
- draw->extra_vp_outputs.semantic_index = transform.maxGeneric + 1;
+ aaline->fs->generic_attrib = transform.maxGeneric + 1;
}
@@ -602,7 +625,7 @@ aaline_first_line(struct draw_stage *stage, struct prim_header *header)
auto struct aaline_stage *aaline = aaline_stage(stage);
struct draw_context *draw = stage->draw;
struct pipe_context *pipe = aaline->pipe;
- uint num = MAX2(aaline->num_textures, aaline->num_samplers);
+ uint num_samplers;
assert(draw->rasterizer->line_smooth);
@@ -611,20 +634,31 @@ aaline_first_line(struct draw_stage *stage, struct prim_header *header)
else
aaline->half_line_width = 0.5f * draw->rasterizer->line_width;
+ /*
+ * Bind (generate) our fragprog, sampler and texture
+ */
+ bind_aaline_fragment_shader(aaline);
+
+ /* update vertex attrib info */
aaline->tex_slot = draw->num_vs_outputs;
assert(aaline->tex_slot > 0); /* output[0] is vertex pos */
+
+ /* advertise the extra post-transformed vertex attribute */
+ draw->extra_vp_outputs.semantic_name = TGSI_SEMANTIC_GENERIC;
+ draw->extra_vp_outputs.semantic_index = aaline->fs->generic_attrib;
draw->extra_vp_outputs.slot = aaline->tex_slot;
- /*
- * Bind our fragprog, sampler and texture
- */
- bind_aaline_fragment_shader(aaline);
+ /* how many samplers? */
+ /* we'll use sampler/texture[pstip->sampler_unit] for the stipple */
+ num_samplers = MAX2(aaline->num_textures, aaline->num_samplers);
+ num_samplers = MAX2(num_samplers, aaline->fs->sampler_unit + 1);
- aaline->state.sampler[num] = aaline->sampler_cso;
- pipe_texture_reference(&aaline->state.texture[num], aaline->texture);
+ aaline->state.sampler[aaline->fs->sampler_unit] = aaline->sampler_cso;
+ pipe_texture_reference(&aaline->state.texture[aaline->fs->sampler_unit],
+ aaline->texture);
- aaline->driver_bind_sampler_states(pipe, num + 1, aaline->state.sampler);
- aaline->driver_set_sampler_textures(pipe, num + 1, aaline->state.texture);
+ aaline->driver_bind_sampler_states(pipe, num_samplers, aaline->state.sampler);
+ aaline->driver_set_sampler_textures(pipe, num_samplers, aaline->state.texture);
/* now really draw first line */
stage->line = aaline_line;