vrend: Associate host UBOs with the correct gallium uniform buffers

Take into account the gallium uniform buffer indices when associating
host UBOs with gallium uniform buffers.

Previously the code disregarded the gallium uniform buffer indices,
leading, under specific circumstances, to the provision of incorrect
data to the shaders. The problem manifested typically when a context
contained active UBOs which were not accessed by a particular shader,
but ended up being used instead of the correct UBOs for that shader.
This occurred, for example, when running the dEQP-GLES3.functional.ubo.*
in batch mode, in which case left over UBOs from previous tests would
cause subsequent tests to fail.

Fixes:
dEQP-GLES3.functional.ubo.* when run in batch mode

Signed-off-by: Alexandros Frantzis <alexandros.frantzis@collabora.com>
Signed-off-by: Jakob Bornecrantz <jakob@collabora.com>
Reviewed-by: Joe Kniss <djmk@chromiumos.org, djmk@google.com>
Tested-by: Elie Tournier <elie.tournier@collabora.com>
macos/master
Alexandros Frantzis 7 years ago committed by Jakob Bornecrantz
parent 704c619785
commit 78c9c237b0
  1. 22
      src/vrend_renderer.c
  2. 1
      src/vrend_shader.c
  3. 1
      src/vrend_shader.h

@ -1046,7 +1046,8 @@ static struct vrend_linked_shader_program *add_shader_program(struct vrend_conte
sprog->ubo_locs[id] = calloc(sprog->ss[id]->sel->sinfo.num_ubos, sizeof(uint32_t));
for (i = 0; i < sprog->ss[id]->sel->sinfo.num_ubos; i++) {
snprintf(name, 32, "%subo%d", prefix, i + 1);
int ubo_idx = sprog->ss[id]->sel->sinfo.ubo_idx[i];
snprintf(name, 32, "%subo%d", prefix, ubo_idx);
sprog->ubo_locs[id][i] = glGetUniformBlockIndex(prog_id, name);
}
} else
@ -2873,25 +2874,40 @@ static void vrend_draw_bind_ubo(struct vrend_context *ctx)
ubo_id = 0;
for (shader_type = PIPE_SHADER_VERTEX; shader_type <= ctx->sub->last_shader_idx; shader_type++) {
uint32_t mask;
int shader_ubo_idx = 0;
int shader_ubo_idx;
struct pipe_constant_buffer *cb;
struct vrend_resource *res;
struct vrend_shader_info* sinfo;
if (!ctx->sub->const_bufs_used_mask[shader_type])
continue;
if (!ctx->sub->prog->ubo_locs[shader_type])
continue;
sinfo = &ctx->sub->prog->ss[shader_type]->sel->sinfo;
mask = ctx->sub->const_bufs_used_mask[shader_type];
while (mask) {
/* The const_bufs_used_mask stores the gallium uniform buffer indices */
i = u_bit_scan(&mask);
/* The cbs array is indexed using the gallium uniform buffer index */
cb = &ctx->sub->cbs[shader_type][i];
res = (struct vrend_resource *)cb->buffer;
/* Find the index of the uniform buffer in the array of shader ubo data */
for (shader_ubo_idx = 0; shader_ubo_idx < sinfo->num_ubos; shader_ubo_idx++) {
if (sinfo->ubo_idx[shader_ubo_idx] == i)
break;
}
if (shader_ubo_idx == sinfo->num_ubos)
continue;
glBindBufferRange(GL_UNIFORM_BUFFER, ubo_id, res->id,
cb->buffer_offset, cb->buffer_size);
/* The ubo_locs array is indexed using the shader ubo index */
glUniformBlockBinding(ctx->sub->prog->id, ctx->sub->prog->ubo_locs[shader_type][shader_ubo_idx], ubo_id);
shader_ubo_idx++;
ubo_id++;
}
}

@ -2839,6 +2839,7 @@ char *vrend_convert_shader(struct vrend_shader_cfg *cfg,
sinfo->samplers_used_mask = ctx.samplers_used;
sinfo->num_consts = ctx.num_consts;
sinfo->num_ubos = ctx.num_ubo;
memcpy(sinfo->ubo_idx, ctx.ubo_idx, ctx.num_ubo * sizeof(*ctx.ubo_idx));
sinfo->num_inputs = ctx.num_inputs;
sinfo->num_interps = ctx.num_interps;
sinfo->num_outputs = ctx.num_outputs;

@ -41,6 +41,7 @@ struct vrend_shader_info {
int num_interps;
int num_outputs;
int num_ubos;
int ubo_idx[32];
int num_ucp;
int glsl_ver;
bool has_pervertex_out;

Loading…
Cancel
Save