diff options
author | Keith Whitwell <keithw@vmware.com> | 2009-05-18 13:15:47 +0100 |
---|---|---|
committer | Keith Whitwell <keithw@vmware.com> | 2009-06-30 14:17:51 +0100 |
commit | 3b9325f4b95f2b62920f9e570a9e07800d3bc545 (patch) | |
tree | df9a5b6464c7bad372d9307ef9866f214e36cdb6 | |
parent | 91f9882551d179677b54bd80f7e1dae4e0fbc881 (diff) |
st/vbo: wip new code for immediate vertex handling
-rw-r--r-- | src/mesa/state_tracker/st_vbo/st_vbo_exec_prims.c | 571 |
1 files changed, 571 insertions, 0 deletions
diff --git a/src/mesa/state_tracker/st_vbo/st_vbo_exec_prims.c b/src/mesa/state_tracker/st_vbo/st_vbo_exec_prims.c new file mode 100644 index 0000000000..2a304af569 --- /dev/null +++ b/src/mesa/state_tracker/st_vbo/st_vbo_exec_prims.c @@ -0,0 +1,571 @@ + +/* As long as 'upgrade' doesn't change the type of the existing + * attribute, upgrading a vertex is fairly straight-forward. + */ +static INLINE void upgrade_vertex( char *dest, + const char *src, + unsigned oldsize, + const char *inject, + unsigned inject_size + unsigned inject_offset ) +{ + memcpy(dest, + src, + inject_offset); + + memcpy(dest + inject_offset, + inject, + inject_size); + + if (inject_offset != oldsize) { + memcpy(dest + inject_offset + inject_size + src + inject_offset, + oldsize - inject_offset); + } +} + +static INLINE void upgrade_attrib( struct st_exec *exec, + unsigned attrib, + unsigned new_attrib_size ) +{ + unsigned old_attrib_size = exec->attrib[attrib].size; + unsigned extra_bytes = (new_attrib_size - old_attrib_size) * sizeof(float); + unsigned new_vertex_size = exec->vertex_size + extra_bytes; + + for (i = 0; i < 4; i++) { + char *new_vtx = MALLOC( new_vertex_size ); + + upgrade_vertex( new_vtx, + exec->slot[i].vertex, + exec->vertex_size, + (const char *)&identity[old_attrib_size], + extra_bytes, + exec->attrib[attrib].offset ); + + FREE( exec->slot[i].vertex ); + exec->slot[i].vertex = new_vtx; + } + + exec->attrib[attrib].size = new_attrib_size; + + for (i = attrib + 1; i < exec->nr_attribs; i++) + exec->attrib[i].offset += extra_bytes; + + for (i = 0; i < exec->nr_attribs; i++) + exec->attrib[i].ptr += exec->vertex + exec->attrib[i].offset; + + exec->vertex_size = new_vertex_size; +} + + +static INLINE void new_attrib( struct st_exec *exec, + unsigned attrib_name, + unsigned size ) +{ + unsigned i = exec->nr_attribs; + exec->attrib[i].name = attrib_name; + exec->attrib[i].offset = exec->vertex_size; + exec->attrib[i].size = 0; + exec->attrib[i].ptr = exec->vertex + exec->attrib[i].offset; + exec->nr_attribs++; + + upgade_attrib( exec, i, size ); +} + + +static INLINE char *new_prim( struct st_exec *exec, + GLenum mode, + unsigned verts ) +{ + + assert(exec->mode == GL_POLYGON+1); + exec->prim.mode = mode; + exec->prim.verts = 0; + exec->prim.start = + + + retval = extend_prim( exec, verts ); + assert(retval); + return retval; +} + + +static INLINE char *extend_prim( struct st_exec *exec, + unsigned verts ) +{ + unsigned bytes = verts * exec->vertex_size; + char *retval; + + assert(exec->mode != GL_POLYGON+1); + + if (exec->used + bytes > exec->total) + return NULL; + + retval = exec->ptr + exec->used; + exec->used += bytes; + exec->prim.verts += verts; + return retval; +} + + +/* POINTS + */ +static void emit_point_subsequent_slot_zero( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_POINTS, 1 ); + } + + emit_vertex( exec, dest, 0 ); + exec->slotnr = 0; +} + +static void emit_point_first_slot_zero( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_POINTS, 1 ); + emit_vertex( exec, dest, 0 ); + exec->slotnr = 0; + exec->slot[0].func = emit_point_subsequent_slot_zero; +} + + +/* LINES + */ +static void emit_line_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 2 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_LINES, 2 ); + } + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + exec->slotnr = 0; +} + +static void emit_line_first_slot_one( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_LINES, 2 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + exec->slotnr = 0; + exec->slot[1].func = emit_line_subsequent_slot_one; +} + +/* LINE_STRIP + */ +static void emit_linestrip_subsequent_slot_zero( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_LINE_STRIP, 2 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 0 ); + exec->slotnr = 1; +} + + +static void emit_linestrip_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_LINE_STRIP, 2 ); + emit_vertex( exec, dest, 0 ); + } + + emit_vertex( exec, dest, 1 ); + exec->slotnr = 0; +} + + +static void emit_linestrip_first_slot_one( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_LINE_STRIP, 2 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + exec->slotnr = 1; + exec->slot[0].func = emit_linestrip_subsequent_slot_zero; + exec->slot[1].func = emit_linestrip_subsequent_slot_one; +} + + +/* LINE_LOOP + */ +static void emit_lineloop_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_LINE_STRIP, 2 ); + emit_vertex( exec, dest, 2 ); + } + + emit_vertex( exec, dest, 1 ); + exec->slotnr = 2; +} + + +static void emit_lineloop_subsequent_slot_two( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_LINE_STRIP, 2 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 2 ); + exec->slotnr = 1; +} + + +static void emit_lineloop_first_slot_one( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_LINE_STRIP, 2 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit->slotnr = 2; + exec->slot[1].func = emit_lineloop_subsequent_slot_one; + exec->slot[2].func = emit_lineloop_subsequent_slot_two; + exec->slot[2].end = emit_lineloop_end_slot_two; + exec->slot[1].end = emit_lineloop_end_slot_one; +} + + + + +/* TRIANGLES + */ +static void emit_triangle_subsequent_slot_two( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 2 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLES, 2 ); + } + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + exec->slotnr = 0; +} + +static void emit_first_slot_two( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_TRIANGLES, 2 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + exec->slotnr = 0; + exec->slot[2].func = emit_triangle_subsequent_slot_two; +} + +/* TRIANGLE_STRIP + */ + +static void emit_tristrip_subsequent_slot_zero( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_STRIP, 3 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 3 ); + } + + emit_vertex( exec, dest, 0 ); + exec->slotnr = 1; +} + +static void emit_tristrip_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_STRIP, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 3 ); + } + + emit_vertex( exec, dest, 1 ); + exec->slotnr = 2; +} + +static void emit_tristrip_subsequent_slot_two( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_STRIP, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 2 ); + exec->slotnr = 3; +} + + +static void emit_tristrip_subsequent_slot_three( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_STRIP, 3 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 3 ); + exec->slotnr = 0; +} + + +static void emit_tristrip_first_slot_two( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_TRIANGLE_STRIP, 3 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + exec->slotnr = 3; + exec->slot[0].func = emit_tristrip_subsequent_slot_zero; + exec->slot[1].func = emit_tristrip_subsequent_slot_one; + exec->slot[2].func = emit_tristrip_subsequent_slot_two; + exec->slot[3].func = emit_tristrip_subsequent_slot_three; +} + + + +/* TRIANGLE_FAN + */ +static void emit_trifan_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_FAN, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 2 ); + } + + emit_vertex( exec, dest, 1 ); + exec->slotnr = 2; +} + +static void emit_trifan_subsequent_slot_two( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_TRIANGLE_FAN, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 2 ); + exec->slotnr = 1; +} + + +static void emit_trifan_first_slot_two( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_TRIANGLE_STRIP, 3 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + exec->slotnr = 1; + emit->slot[1].func = emit_trifan_subsequent_slot_one; + emit->slot[2].func = emit_trifan_subsequent_slot_two; +} + + + +/* QUADS + */ +static void emit_quad_subsequent_slot_three( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 4 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_QUAD_STRIP, 4 ); + } + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 4 ); + exec->slotnr = 0; +} + + +static void emit_quad_first_slot_three( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_QUAD_STRIP, 4 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 4 ); + exec->slotnr = 0; + exec->slot[3].func = emit_quad_subsequent_slot_three; +} + +/* QUADSTRIP + */ + +static void emit_quadstrip_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 2 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_QUAD_STRIP, 4 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 3 ); + } + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + exec->slotnr = 2; +} + +static void emit_quadstrip_subsequent_slot_three( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 2 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_QUAD_STRIP, 4 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 3 ); + exec->slotnr = 0; +} + + +static void emit_quadstrip_first_slot_three( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_QUAD_STRIP, 4 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + emit_vertex( exec, dest, 3 ); + exec->slotnr = 0; + exec->slot[1].func = emit_quadstrip_subsequent_slot_one; + exec->slot[3].func = emit_quadstrip_subsequent_slot_three; +} + +/* POLYGON + */ +static void emit_polygon_subsequent_slot_one( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_POLYGON, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 2 ); + } + + emit_vertex( exec, dest, 1 ); + exec->slotnr = 2; +} + +static void emit_polygon_subsequent_slot_two( struct st_exec *exec ) +{ + char *dest = extend_prim( exec, 1 ); + + if (dest == 0) { + dest = wrap_prim( exec, GL_POLYGON, 3 ); + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + } + + emit_vertex( exec, dest, 2 ); + exec->slotnr = 1; +} + + +static void emit_polygon_first_slot_two( struct st_exec *exec ) +{ + char *dest = new_prim( exec, GL_POLYGON, 3 ); + + emit_vertex( exec, dest, 0 ); + emit_vertex( exec, dest, 1 ); + emit_vertex( exec, dest, 2 ); + exec->slotnr = 1; + emit->slot[1].func = emit_polygon_subsequent_slot_one; + emit->slot[2].func = emit_polygon_subsequent_slot_two; +} + +/* Noop + */ +static void emit_noop( struct st_exec *exec ) +{ + exec->slotnr++; +} + +static emit_func[GL_POLYGON+1][4] = +{ + { emit_point_first_slot_zero, + NULL, + NULL, + NULL }, + + { emit_noop, + emit_line_first_slot_one, + NULL, + NULL }, + + { emit_noop, + emit_lineloop_first_slot_one, + NULL, + NULL }, + + { emit_noop, + emit_linestrip_first_slot_one, + NULL, + NULL }, + + { emit_noop, + emit_noop, + emit_triangle_first_slot_two, + NULL }, + + { emit_noop, + emit_noop, + emit_tristrip_first_slot_two, + NULL }, + + { emit_noop, + emit_noop, + emit_trifan_first_slot_two, + NULL }, + + { emit_noop, + emit_noop, + emit_noop, + emit_quad_first_slot_three }, + + { emit_noop, + emit_noop, + emit_noop, + emit_quadstrip_first_slot_three }, + + { emit_noop, + emit_noop, + emit_polygon_first_slot_two, + NULL } +}; |