summaryrefslogtreecommitdiff
path: root/src/mesa/vbo
diff options
context:
space:
mode:
Diffstat (limited to 'src/mesa/vbo')
-rw-r--r--src/mesa/vbo/vbo.h6
-rw-r--r--src/mesa/vbo/vbo_exec_array.c158
-rw-r--r--src/mesa/vbo/vbo_exec_draw.c1
-rw-r--r--src/mesa/vbo/vbo_rebase.c1
-rw-r--r--src/mesa/vbo/vbo_save_draw.c1
-rw-r--r--src/mesa/vbo/vbo_split_copy.c1
-rw-r--r--src/mesa/vbo/vbo_split_inplace.c1
7 files changed, 94 insertions, 75 deletions
diff --git a/src/mesa/vbo/vbo.h b/src/mesa/vbo/vbo.h
index 5362226c2f..5986e93576 100644
--- a/src/mesa/vbo/vbo.h
+++ b/src/mesa/vbo/vbo.h
@@ -69,6 +69,7 @@ typedef void (*vbo_draw_func)( GLcontext *ctx,
const struct _mesa_prim *prims,
GLuint nr_prims,
const struct _mesa_index_buffer *ib,
+ GLboolean index_bounds_valid,
GLuint min_index,
GLuint max_index );
@@ -112,7 +113,10 @@ void vbo_rebase_prims( GLcontext *ctx,
GLuint min_index,
GLuint max_index,
vbo_draw_func draw );
-
+void
+vbo_get_minmax_index(GLcontext *ctx, const struct _mesa_prim *prim,
+ const struct _mesa_index_buffer *ib,
+ GLuint *min_index, GLuint *max_index);
void vbo_use_buffer_objects(GLcontext *ctx);
diff --git a/src/mesa/vbo/vbo_exec_array.c b/src/mesa/vbo/vbo_exec_array.c
index f4b9b2f744..4fb4845f6b 100644
--- a/src/mesa/vbo/vbo_exec_array.c
+++ b/src/mesa/vbo/vbo_exec_array.c
@@ -41,15 +41,29 @@
/**
* Compute min and max elements for glDraw[Range]Elements() calls.
*/
-static void
-get_minmax_index(GLuint count, GLuint type, const GLvoid *indices,
- GLuint *min_index, GLuint *max_index)
+void
+vbo_get_minmax_index(GLcontext *ctx,
+ const struct _mesa_prim *prim,
+ const struct _mesa_index_buffer *ib,
+ GLuint *min_index, GLuint *max_index)
{
GLuint i;
+ GLsizei count = prim->count;
+ const void *indices;
+
+ if (ib->obj->Name) {
+ const GLvoid *map = ctx->Driver.MapBuffer(ctx,
+ GL_ELEMENT_ARRAY_BUFFER_ARB,
+ GL_READ_ONLY,
+ ib->obj);
+ indices = ADD_POINTERS(map, ib->ptr);
+ } else {
+ indices = ib->ptr;
+ }
- switch(type) {
+ switch (ib->type) {
case GL_UNSIGNED_INT: {
- const GLuint *ui_indices = (const GLuint *)indices;
+ const GLuint *ui_indices = (const GLuint *)ib->ptr;
GLuint max_ui = ui_indices[count-1];
GLuint min_ui = ui_indices[0];
for (i = 0; i < count; i++) {
@@ -88,6 +102,12 @@ get_minmax_index(GLuint count, GLuint type, const GLvoid *indices,
assert(0);
break;
}
+
+ if (ib->obj->Name != 0) {
+ ctx->Driver.UnmapBuffer(ctx,
+ GL_ELEMENT_ARRAY_BUFFER_ARB,
+ ib->obj);
+ }
}
@@ -500,7 +520,7 @@ vbo_exec_DrawArrays(GLenum mode, GLint start, GLsizei count)
prim[0].indexed = 0;
vbo->draw_prims( ctx, exec->array.inputs, prim, 1, NULL,
- start, start + count - 1 );
+ GL_TRUE, start, start + count - 1 );
#if 0
print_draw_arrays(ctx, exec, mode, start, count);
@@ -566,53 +586,19 @@ dump_element_buffer(GLcontext *ctx, GLenum type)
ctx->Array.ElementArrayBufferObj);
}
-
-static void GLAPIENTRY
-vbo_exec_DrawRangeElements(GLenum mode,
- GLuint start, GLuint end,
- GLsizei count, GLenum type, const GLvoid *indices)
+/* Inner support for both _mesa_DrawElements and _mesa_DrawRangeElements */
+static void
+vbo_validated_drawrangeelements(GLcontext *ctx, GLenum mode,
+ GLboolean index_bounds_valid,
+ GLuint start, GLuint end,
+ GLsizei count, GLenum type,
+ const GLvoid *indices)
{
- GET_CURRENT_CONTEXT(ctx);
struct vbo_context *vbo = vbo_context(ctx);
struct vbo_exec_context *exec = &vbo->exec;
struct _mesa_index_buffer ib;
struct _mesa_prim prim[1];
- if (!_mesa_validate_DrawRangeElements( ctx, mode, start, end, count,
- type, indices ))
- return;
-
- if (end >= ctx->Array.ArrayObj->_MaxElement) {
- /* the max element is out of bounds of one or more enabled arrays */
- _mesa_warning(ctx, "glDraw[Range]Elements(start %u, end %u, count %d, "
- "type 0x%x, indices=%p)\n"
- "\tindex=%u is out of bounds (max=%u) "
- "Element Buffer %u (size %d)",
- start, end, count, type, indices, end,
- ctx->Array.ArrayObj->_MaxElement - 1,
- ctx->Array.ElementArrayBufferObj->Name,
- ctx->Array.ElementArrayBufferObj->Size);
-
- if (0)
- dump_element_buffer(ctx, type);
-
- if (0)
- _mesa_print_arrays(ctx);
- return;
- }
- else if (0) {
- _mesa_printf("glDraw[Range]Elements"
- "(start %u, end %u, type 0x%x, count %d) ElemBuf %u\n",
- start, end, type, count,
- ctx->Array.ElementArrayBufferObj->Name);
- }
-
-#if 0
- check_draw_elements_data(ctx, count, type, indices);
-#else
- (void) check_draw_elements_data;
-#endif
-
FLUSH_CURRENT( ctx, 0 );
if (ctx->NewState)
@@ -623,13 +609,13 @@ vbo_exec_DrawRangeElements(GLenum mode,
return;
}
- bind_arrays( ctx );
-
if (ctx->NewState)
_mesa_update_state( ctx );
+ bind_arrays( ctx );
+
ib.count = count;
- ib.type = type;
+ ib.type = type;
ib.obj = ctx->Array.ElementArrayBufferObj;
ib.ptr = indices;
@@ -673,44 +659,68 @@ vbo_exec_DrawRangeElements(GLenum mode,
* for the latter case elsewhere.
*/
- vbo->draw_prims( ctx, exec->array.inputs, prim, 1, &ib, start, end );
+ vbo->draw_prims( ctx, exec->array.inputs, prim, 1, &ib,
+ index_bounds_valid, start, end );
}
-
static void GLAPIENTRY
-vbo_exec_DrawElements(GLenum mode, GLsizei count, GLenum type,
- const GLvoid *indices)
+vbo_exec_DrawRangeElements(GLenum mode,
+ GLuint start, GLuint end,
+ GLsizei count, GLenum type, const GLvoid *indices)
{
GET_CURRENT_CONTEXT(ctx);
- GLuint min_index = 0;
- GLuint max_index = 0;
- if (!_mesa_validate_DrawElements( ctx, mode, count, type, indices ))
+ if (!_mesa_validate_DrawRangeElements( ctx, mode, start, end, count,
+ type, indices ))
return;
- if (!vbo_validate_shaders(ctx)) {
- _mesa_error(ctx, GL_INVALID_OPERATION, "glDrawElements(bad shader)");
+ if (end >= ctx->Array.ArrayObj->_MaxElement) {
+ /* the max element is out of bounds of one or more enabled arrays */
+ _mesa_warning(ctx, "glDraw[Range]Elements(start %u, end %u, count %d, "
+ "type 0x%x, indices=%p)\n"
+ "\tindex=%u is out of bounds (max=%u) "
+ "Element Buffer %u (size %d)",
+ start, end, count, type, indices, end,
+ ctx->Array.ArrayObj->_MaxElement - 1,
+ ctx->Array.ElementArrayBufferObj->Name,
+ ctx->Array.ElementArrayBufferObj->Size);
+
+ if (0)
+ dump_element_buffer(ctx, type);
+
+ if (0)
+ _mesa_print_arrays(ctx);
return;
}
+ else if (0) {
+ _mesa_printf("glDraw[Range]Elements"
+ "(start %u, end %u, type 0x%x, count %d) ElemBuf %u\n",
+ start, end, type, count,
+ ctx->Array.ElementArrayBufferObj->Name);
+ }
- if (ctx->Array.ElementArrayBufferObj->Name) {
- const GLvoid *map = ctx->Driver.MapBuffer(ctx,
- GL_ELEMENT_ARRAY_BUFFER_ARB,
- GL_READ_ONLY,
- ctx->Array.ElementArrayBufferObj);
+#if 0
+ check_draw_elements_data(ctx, count, type, indices);
+#else
+ (void) check_draw_elements_data;
+#endif
+
+ vbo_validated_drawrangeelements(ctx, mode, GL_TRUE, start, end,
+ count, type, indices);
+}
- get_minmax_index(count, type, ADD_POINTERS(map, indices),
- &min_index, &max_index);
- ctx->Driver.UnmapBuffer(ctx,
- GL_ELEMENT_ARRAY_BUFFER_ARB,
- ctx->Array.ElementArrayBufferObj);
- }
- else {
- get_minmax_index(count, type, indices, &min_index, &max_index);
- }
+static void GLAPIENTRY
+vbo_exec_DrawElements(GLenum mode, GLsizei count, GLenum type,
+ const GLvoid *indices)
+{
+ GET_CURRENT_CONTEXT(ctx);
+
+ if (!_mesa_validate_DrawElements( ctx, mode, count, type, indices ))
+ return;
- vbo_exec_DrawRangeElements(mode, min_index, max_index, count, type, indices);
+ vbo_validated_drawrangeelements(ctx, mode, GL_FALSE, ~0, ~0,
+ count, type, indices);
}
diff --git a/src/mesa/vbo/vbo_exec_draw.c b/src/mesa/vbo/vbo_exec_draw.c
index 18419928b2..a988424d21 100644
--- a/src/mesa/vbo/vbo_exec_draw.c
+++ b/src/mesa/vbo/vbo_exec_draw.c
@@ -378,6 +378,7 @@ vbo_exec_vtx_flush( struct vbo_exec_context *exec, GLboolean unmap )
exec->vtx.prim,
exec->vtx.prim_count,
NULL,
+ GL_TRUE,
0,
exec->vtx.vert_count - 1);
diff --git a/src/mesa/vbo/vbo_rebase.c b/src/mesa/vbo/vbo_rebase.c
index ea87dede64..3bf7ef580f 100644
--- a/src/mesa/vbo/vbo_rebase.c
+++ b/src/mesa/vbo/vbo_rebase.c
@@ -208,6 +208,7 @@ void vbo_rebase_prims( GLcontext *ctx,
prim,
nr_prims,
ib,
+ GL_TRUE,
0,
max_index - min_index );
diff --git a/src/mesa/vbo/vbo_save_draw.c b/src/mesa/vbo/vbo_save_draw.c
index 5110648c28..d834fa1f2e 100644
--- a/src/mesa/vbo/vbo_save_draw.c
+++ b/src/mesa/vbo/vbo_save_draw.c
@@ -279,6 +279,7 @@ void vbo_save_playback_vertex_list( GLcontext *ctx, void *data )
node->prim,
node->prim_count,
NULL,
+ GL_TRUE,
0, /* Node is a VBO, so this is ok */
node->count - 1);
}
diff --git a/src/mesa/vbo/vbo_split_copy.c b/src/mesa/vbo/vbo_split_copy.c
index d7ffebf607..3f8a222805 100644
--- a/src/mesa/vbo/vbo_split_copy.c
+++ b/src/mesa/vbo/vbo_split_copy.c
@@ -194,6 +194,7 @@ flush( struct copy_context *copy )
copy->dstprim,
copy->dstprim_nr,
&copy->dstib,
+ GL_TRUE,
0,
copy->dstbuf_nr );
diff --git a/src/mesa/vbo/vbo_split_inplace.c b/src/mesa/vbo/vbo_split_inplace.c
index 9628227e7c..da84eaa6ea 100644
--- a/src/mesa/vbo/vbo_split_inplace.c
+++ b/src/mesa/vbo/vbo_split_inplace.c
@@ -85,6 +85,7 @@ static void flush_vertex( struct split_context *split )
split->dstprim,
split->dstprim_nr,
NULL,
+ GL_TRUE,
min_index,
max_index);