state_tracker: remove software handling of primitive restart

The VBO module now can handle primitive restart in software
if required. Therefore this support is no londer required.

Signed-off-by: Jordan Justen <jordan.l.justen@intel.com>
Reviewed-by: Ian Romanick <ian.d.romanick@intel.com>
This commit is contained in:
Jordan Justen
2012-05-07 16:11:55 -07:00
parent f16b39f05c
commit eef193560e

View File

@@ -638,175 +638,6 @@ check_uniforms(struct gl_context *ctx)
}
/*
* Notes on primitive restart:
* The code below is used when the gallium driver does not support primitive
* restart itself. We map the index buffer, find the restart indexes, unmap
* the index buffer then draw the sub-primitives delineated by the restarts.
* A couple possible optimizations:
* 1. Save the list of sub-primitive (start, count) values in a list attached
* to the index buffer for re-use in subsequent draws. The list would be
* invalidated when the contents of the buffer changed.
* 2. If drawing triangle strips or quad strips, create a new index buffer
* that uses duplicated vertices to render the disjoint strips as one
* long strip. We'd have to be careful to avoid using too much memory
* for this.
* Finally, some apps might perform better if they don't use primitive restart
* at all rather than this fallback path. Set MESA_EXTENSION_OVERRIDE to
* "-GL_NV_primitive_restart" to test that.
*/
struct sub_primitive
{
unsigned start, count;
};
/**
* Scan the elements array to find restart indexes. Return a list
* of primitive (start,count) pairs to indicate how to draw the sub-
* primitives delineated by the restart index.
*/
static struct sub_primitive *
find_sub_primitives(const void *elements, unsigned element_size,
unsigned start, unsigned end, unsigned restart_index,
unsigned *num_sub_prims)
{
const unsigned max_prims = end - start;
struct sub_primitive *sub_prims;
unsigned i, cur_start, cur_count, num;
sub_prims = (struct sub_primitive *)
malloc(max_prims * sizeof(struct sub_primitive));
if (!sub_prims) {
*num_sub_prims = 0;
return NULL;
}
cur_start = start;
cur_count = 0;
num = 0;
#define SCAN_ELEMENTS(TYPE) \
for (i = start; i < end; i++) { \
if (((const TYPE *) elements)[i] == restart_index) { \
if (cur_count > 0) { \
assert(num < max_prims); \
sub_prims[num].start = cur_start; \
sub_prims[num].count = cur_count; \
num++; \
} \
cur_start = i + 1; \
cur_count = 0; \
} \
else { \
cur_count++; \
} \
} \
if (cur_count > 0) { \
assert(num < max_prims); \
sub_prims[num].start = cur_start; \
sub_prims[num].count = cur_count; \
num++; \
}
switch (element_size) {
case 1:
SCAN_ELEMENTS(ubyte);
break;
case 2:
SCAN_ELEMENTS(ushort);
break;
case 4:
SCAN_ELEMENTS(uint);
break;
default:
assert(0 && "bad index_size in find_sub_primitives()");
}
#undef SCAN_ELEMENTS
*num_sub_prims = num;
return sub_prims;
}
/**
* For gallium drivers that don't support the primitive restart
* feature, handle it here by breaking up the indexed primitive into
* sub-primitives.
*/
static void
handle_fallback_primitive_restart(struct cso_context *cso,
struct pipe_context *pipe,
const struct _mesa_index_buffer *ib,
struct pipe_index_buffer *ibuffer,
struct pipe_draw_info *orig_info)
{
const unsigned start = orig_info->start;
const unsigned count = orig_info->count;
struct pipe_draw_info info = *orig_info;
struct pipe_transfer *transfer = NULL;
unsigned instance, i;
const void *ptr = NULL;
struct sub_primitive *sub_prims;
unsigned num_sub_prims;
assert(info.indexed);
assert(ibuffer->buffer || ibuffer->user_buffer);
assert(ib);
if (!ibuffer->buffer || !ibuffer->user_buffer || !ib)
return;
info.primitive_restart = FALSE;
info.instance_count = 1;
if (_mesa_is_bufferobj(ib->obj)) {
ptr = pipe_buffer_map_range(pipe, ibuffer->buffer,
start * ibuffer->index_size, /* start */
count * ibuffer->index_size, /* length */
PIPE_TRANSFER_READ, &transfer);
if (!ptr)
return;
ptr = (uint8_t*)ptr + (ibuffer->offset - start * ibuffer->index_size);
}
else {
ptr = ib->ptr;
if (!ptr)
return;
}
sub_prims = find_sub_primitives(ptr, ibuffer->index_size,
0, count, orig_info->restart_index,
&num_sub_prims);
if (transfer)
pipe_buffer_unmap(pipe, transfer);
/* Now draw the sub primitives.
* Need to loop over instances as well to preserve draw order.
*/
for (instance = 0; instance < orig_info->instance_count; instance++) {
info.start_instance = instance + orig_info->start_instance;
for (i = 0; i < num_sub_prims; i++) {
info.start = sub_prims[i].start;
info.count = sub_prims[i].count;
if (u_trim_pipe_prim(info.mode, &info.count)) {
cso_draw_vbo(cso, &info);
}
}
}
if (sub_prims)
free(sub_prims);
}
/**
* Translate OpenGL primtive type (GL_POINTS, GL_TRIANGLE_STRIP, etc) to
* the corresponding Gallium type.
@@ -994,15 +825,8 @@ st_draw_vbo(struct gl_context *ctx,
cso_draw_vbo(st->cso_context, &info);
}
else if (info.primitive_restart) {
if (st->sw_primitive_restart) {
/* Handle primitive restart for drivers that doesn't support it */
handle_fallback_primitive_restart(st->cso_context, pipe, ib,
&ibuffer, &info);
}
else {
/* don't trim, restarts might be inside index list */
cso_draw_vbo(st->cso_context, &info);
}
/* don't trim, restarts might be inside index list */
cso_draw_vbo(st->cso_context, &info);
}
else if (u_trim_pipe_prim(info.mode, &info.count))
cso_draw_vbo(st->cso_context, &info);