From 7ca0ce38340144794267609646048b3820d594ab Mon Sep 17 00:00:00 2001 From: Michal Krol Date: Tue, 29 Dec 2009 23:21:01 +0100 Subject: Implement draw_arrays_instanced() in softpipe. Modify the translate module to respect instance divisors and accept instance id as a parameter to calculate input vertex offset. --- src/gallium/drivers/softpipe/sp_draw_arrays.c | 51 +++++++++++++++++++++++++++ 1 file changed, 51 insertions(+) (limited to 'src/gallium/drivers/softpipe/sp_draw_arrays.c') diff --git a/src/gallium/drivers/softpipe/sp_draw_arrays.c b/src/gallium/drivers/softpipe/sp_draw_arrays.c index 518ef8806e..6a593fb06a 100644 --- a/src/gallium/drivers/softpipe/sp_draw_arrays.c +++ b/src/gallium/drivers/softpipe/sp_draw_arrays.c @@ -184,3 +184,54 @@ softpipe_draw_elements(struct pipe_context *pipe, 0, 0xffffffff, mode, start, count ); } + +boolean +softpipe_draw_arrays_instanced(struct pipe_context *pipe, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount) +{ + struct softpipe_context *sp = softpipe_context(pipe); + struct draw_context *draw = sp->draw; + unsigned i; + + sp->reduced_api_prim = u_reduced_prim(mode); + + if (sp->dirty) { + softpipe_update_derived(sp); + } + + softpipe_map_transfers(sp); + softpipe_map_constant_buffers(sp); + + /* Map vertex buffers */ + for (i = 0; i < sp->num_vertex_buffers; i++) { + void *buf; + + buf = pipe_buffer_map(pipe->screen, + sp->vertex_buffer[i].buffer, + PIPE_BUFFER_USAGE_CPU_READ); + draw_set_mapped_vertex_buffer(draw, i, buf); + } + + draw_set_mapped_element_buffer_range(draw, 0, start, + start + count - 1, NULL); + + /* draw! */ + draw_arrays_instanced(draw, mode, start, count, startInstance, instanceCount); + + /* unmap vertex/index buffers - will cause draw module to flush */ + for (i = 0; i < sp->num_vertex_buffers; i++) { + draw_set_mapped_vertex_buffer(draw, i, NULL); + pipe_buffer_unmap(pipe->screen, sp->vertex_buffer[i].buffer); + } + + /* Note: leave drawing surfaces mapped */ + softpipe_unmap_constant_buffers(sp); + + sp->dirty_render_cache = TRUE; + + return TRUE; +} -- cgit v1.2.3 From bccdb239c700e0c7c90d27a281d5246b958581b5 Mon Sep 17 00:00:00 2001 From: Michal Krol Date: Wed, 30 Dec 2009 18:27:58 +0100 Subject: sp: Implement draw_elements_instanced(). --- src/gallium/drivers/softpipe/sp_context.c | 1 + src/gallium/drivers/softpipe/sp_draw_arrays.c | 46 +++++++++++++++++++++++++-- src/gallium/drivers/softpipe/sp_state.h | 10 ++++++ 3 files changed, 55 insertions(+), 2 deletions(-) (limited to 'src/gallium/drivers/softpipe/sp_draw_arrays.c') diff --git a/src/gallium/drivers/softpipe/sp_context.c b/src/gallium/drivers/softpipe/sp_context.c index 406414ae3d..969d69d6b4 100644 --- a/src/gallium/drivers/softpipe/sp_context.c +++ b/src/gallium/drivers/softpipe/sp_context.c @@ -239,6 +239,7 @@ softpipe_create( struct pipe_screen *screen ) softpipe->pipe.draw_elements = softpipe_draw_elements; softpipe->pipe.draw_range_elements = softpipe_draw_range_elements; softpipe->pipe.draw_arrays_instanced = softpipe_draw_arrays_instanced; + softpipe->pipe.draw_elements_instanced = softpipe_draw_elements_instanced; softpipe->pipe.clear = softpipe_clear; softpipe->pipe.flush = softpipe_flush; diff --git a/src/gallium/drivers/softpipe/sp_draw_arrays.c b/src/gallium/drivers/softpipe/sp_draw_arrays.c index 6a593fb06a..debf5bfe06 100644 --- a/src/gallium/drivers/softpipe/sp_draw_arrays.c +++ b/src/gallium/drivers/softpipe/sp_draw_arrays.c @@ -192,6 +192,26 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned count, unsigned startInstance, unsigned instanceCount) +{ + return softpipe_draw_elements_instanced(pipe, + NULL, + 0, + mode, + start, + count, + startInstance, + instanceCount); +} + +boolean +softpipe_draw_elements_instanced(struct pipe_context *pipe, + struct pipe_buffer *indexBuffer, + unsigned indexSize, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount) { struct softpipe_context *sp = softpipe_context(pipe); struct draw_context *draw = sp->draw; @@ -216,8 +236,26 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, draw_set_mapped_vertex_buffer(draw, i, buf); } - draw_set_mapped_element_buffer_range(draw, 0, start, - start + count - 1, NULL); + /* Map index buffer, if present */ + if (indexBuffer) { + void *mapped_indexes; + + mapped_indexes = pipe_buffer_map(pipe->screen, + indexBuffer, + PIPE_BUFFER_USAGE_CPU_READ); + draw_set_mapped_element_buffer_range(draw, + indexSize, + 0, + 0xffffffff, + mapped_indexes); + } else { + /* no index/element buffer */ + draw_set_mapped_element_buffer_range(draw, + 0, + start, + start + count - 1, + NULL); + } /* draw! */ draw_arrays_instanced(draw, mode, start, count, startInstance, instanceCount); @@ -227,6 +265,10 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, draw_set_mapped_vertex_buffer(draw, i, NULL); pipe_buffer_unmap(pipe->screen, sp->vertex_buffer[i].buffer); } + if (indexBuffer) { + draw_set_mapped_element_buffer(draw, 0, NULL); + pipe_buffer_unmap(pipe->screen, indexBuffer); + } /* Note: leave drawing surfaces mapped */ softpipe_unmap_constant_buffers(sp); diff --git a/src/gallium/drivers/softpipe/sp_state.h b/src/gallium/drivers/softpipe/sp_state.h index 13935fd799..00da41b985 100644 --- a/src/gallium/drivers/softpipe/sp_state.h +++ b/src/gallium/drivers/softpipe/sp_state.h @@ -197,6 +197,16 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned startInstance, unsigned instanceCount); +boolean +softpipe_draw_elements_instanced(struct pipe_context *pipe, + struct pipe_buffer *indexBuffer, + unsigned indexSize, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount); + void softpipe_map_transfers(struct softpipe_context *sp); -- cgit v1.2.3 From 230355648b647b32161124cad23be553a2c6d196 Mon Sep 17 00:00:00 2001 From: Michal Krol Date: Wed, 30 Dec 2009 18:41:05 +0100 Subject: sp: Generalise drawing code to remove dupes. Also, avoid nested draw calls from simpler versions. --- src/gallium/drivers/softpipe/sp_draw_arrays.c | 165 +++++++++++++------------- 1 file changed, 84 insertions(+), 81 deletions(-) (limited to 'src/gallium/drivers/softpipe/sp_draw_arrays.c') diff --git a/src/gallium/drivers/softpipe/sp_draw_arrays.c b/src/gallium/drivers/softpipe/sp_draw_arrays.c index debf5bfe06..14cb1322e1 100644 --- a/src/gallium/drivers/softpipe/sp_draw_arrays.c +++ b/src/gallium/drivers/softpipe/sp_draw_arrays.c @@ -88,19 +88,41 @@ softpipe_unmap_constant_buffers(struct softpipe_context *sp) } +/** + * Draw vertex arrays, with optional indexing. + * Basically, map the vertex buffers (and drawing surfaces), then hand off + * the drawing to the 'draw' module. + */ +static boolean +softpipe_draw_range_elements_instanced(struct pipe_context *pipe, + struct pipe_buffer *indexBuffer, + unsigned indexSize, + unsigned minIndex, + unsigned maxIndex, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount); + + boolean softpipe_draw_arrays(struct pipe_context *pipe, unsigned mode, unsigned start, unsigned count) { - return softpipe_draw_elements(pipe, NULL, 0, mode, start, count); + return softpipe_draw_range_elements_instanced(pipe, + NULL, + 0, + 0, + 0xffffffff, + mode, + start, + count, + 0, + 1); } -/** - * Draw vertex arrays, with optional indexing. - * Basically, map the vertex buffers (and drawing surfaces), then hand off - * the drawing to the 'draw' module. - */ boolean softpipe_draw_range_elements(struct pipe_context *pipe, struct pipe_buffer *indexBuffer, @@ -109,67 +131,16 @@ softpipe_draw_range_elements(struct pipe_context *pipe, unsigned max_index, unsigned mode, unsigned start, unsigned count) { - struct softpipe_context *sp = softpipe_context(pipe); - struct draw_context *draw = sp->draw; - unsigned i; - - sp->reduced_api_prim = u_reduced_prim(mode); - - if (sp->dirty) - softpipe_update_derived( sp ); - - softpipe_map_transfers(sp); - softpipe_map_constant_buffers(sp); - - /* - * Map vertex buffers - */ - for (i = 0; i < sp->num_vertex_buffers; i++) { - void *buf - = pipe_buffer_map(pipe->screen, - sp->vertex_buffer[i].buffer, - PIPE_BUFFER_USAGE_CPU_READ); - draw_set_mapped_vertex_buffer(draw, i, buf); - } - - /* Map index buffer, if present */ - if (indexBuffer) { - void *mapped_indexes - = pipe_buffer_map(pipe->screen, indexBuffer, - PIPE_BUFFER_USAGE_CPU_READ); - draw_set_mapped_element_buffer_range(draw, indexSize, - min_index, - max_index, - mapped_indexes); - } - else { - /* no index/element buffer */ - draw_set_mapped_element_buffer_range(draw, 0, start, - start + count - 1, NULL); - } - - /* draw! */ - draw_arrays(draw, mode, start, count); - - /* - * unmap vertex/index buffers - will cause draw module to flush - */ - for (i = 0; i < sp->num_vertex_buffers; i++) { - draw_set_mapped_vertex_buffer(draw, i, NULL); - pipe_buffer_unmap(pipe->screen, sp->vertex_buffer[i].buffer); - } - if (indexBuffer) { - draw_set_mapped_element_buffer(draw, 0, NULL); - pipe_buffer_unmap(pipe->screen, indexBuffer); - } - - - /* Note: leave drawing surfaces mapped */ - softpipe_unmap_constant_buffers(sp); - - sp->dirty_render_cache = TRUE; - - return TRUE; + return softpipe_draw_range_elements_instanced(pipe, + indexBuffer, + indexSize, + min_index, + max_index, + mode, + start, + count, + 0, + 1); } @@ -179,10 +150,16 @@ softpipe_draw_elements(struct pipe_context *pipe, unsigned indexSize, unsigned mode, unsigned start, unsigned count) { - return softpipe_draw_range_elements( pipe, indexBuffer, - indexSize, - 0, 0xffffffff, - mode, start, count ); + return softpipe_draw_range_elements_instanced(pipe, + indexBuffer, + indexSize, + 0, + 0xffffffff, + mode, + start, + count, + 0, + 1); } boolean @@ -193,14 +170,16 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned startInstance, unsigned instanceCount) { - return softpipe_draw_elements_instanced(pipe, - NULL, - 0, - mode, - start, - count, - startInstance, - instanceCount); + return softpipe_draw_range_elements_instanced(pipe, + NULL, + 0, + 0, + 0xffffffff, + mode, + start, + count, + startInstance, + instanceCount); } boolean @@ -212,6 +191,30 @@ softpipe_draw_elements_instanced(struct pipe_context *pipe, unsigned count, unsigned startInstance, unsigned instanceCount) +{ + return softpipe_draw_range_elements_instanced(pipe, + indexBuffer, + indexSize, + 0, + 0xffffffff, + mode, + start, + count, + startInstance, + instanceCount); +} + +static boolean +softpipe_draw_range_elements_instanced(struct pipe_context *pipe, + struct pipe_buffer *indexBuffer, + unsigned indexSize, + unsigned minIndex, + unsigned maxIndex, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount) { struct softpipe_context *sp = softpipe_context(pipe); struct draw_context *draw = sp->draw; @@ -245,8 +248,8 @@ softpipe_draw_elements_instanced(struct pipe_context *pipe, PIPE_BUFFER_USAGE_CPU_READ); draw_set_mapped_element_buffer_range(draw, indexSize, - 0, - 0xffffffff, + minIndex, + maxIndex, mapped_indexes); } else { /* no index/element buffer */ -- cgit v1.2.3 From 8c53a2576ec998936981c354b02979f803c0e4de Mon Sep 17 00:00:00 2001 From: Michal Krol Date: Tue, 12 Jan 2010 18:51:27 +0100 Subject: gallium: draw_arrays/elements_instanced() are of type void. --- src/gallium/drivers/softpipe/sp_draw_arrays.c | 44 +++++++++++++-------------- src/gallium/drivers/softpipe/sp_state.h | 4 +-- src/gallium/include/pipe/p_context.h | 30 +++++++++--------- 3 files changed, 39 insertions(+), 39 deletions(-) (limited to 'src/gallium/drivers/softpipe/sp_draw_arrays.c') diff --git a/src/gallium/drivers/softpipe/sp_draw_arrays.c b/src/gallium/drivers/softpipe/sp_draw_arrays.c index 87312ae151..b3ece9d8ed 100644 --- a/src/gallium/drivers/softpipe/sp_draw_arrays.c +++ b/src/gallium/drivers/softpipe/sp_draw_arrays.c @@ -172,7 +172,7 @@ softpipe_draw_elements(struct pipe_context *pipe, 1); } -boolean +void softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned mode, unsigned start, @@ -180,19 +180,19 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned startInstance, unsigned instanceCount) { - return softpipe_draw_range_elements_instanced(pipe, - NULL, - 0, - 0, - 0xffffffff, - mode, - start, - count, - startInstance, - instanceCount); + softpipe_draw_range_elements_instanced(pipe, + NULL, + 0, + 0, + 0xffffffff, + mode, + start, + count, + startInstance, + instanceCount); } -boolean +void softpipe_draw_elements_instanced(struct pipe_context *pipe, struct pipe_buffer *indexBuffer, unsigned indexSize, @@ -202,16 +202,16 @@ softpipe_draw_elements_instanced(struct pipe_context *pipe, unsigned startInstance, unsigned instanceCount) { - return softpipe_draw_range_elements_instanced(pipe, - indexBuffer, - indexSize, - 0, - 0xffffffff, - mode, - start, - count, - startInstance, - instanceCount); + softpipe_draw_range_elements_instanced(pipe, + indexBuffer, + indexSize, + 0, + 0xffffffff, + mode, + start, + count, + startInstance, + instanceCount); } static boolean diff --git a/src/gallium/drivers/softpipe/sp_state.h b/src/gallium/drivers/softpipe/sp_state.h index f8886565e9..3153d6e6a4 100644 --- a/src/gallium/drivers/softpipe/sp_state.h +++ b/src/gallium/drivers/softpipe/sp_state.h @@ -199,7 +199,7 @@ softpipe_draw_range_elements(struct pipe_context *pipe, unsigned max_index, unsigned mode, unsigned start, unsigned count); -boolean +void softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned mode, unsigned start, @@ -207,7 +207,7 @@ softpipe_draw_arrays_instanced(struct pipe_context *pipe, unsigned startInstance, unsigned instanceCount); -boolean +void softpipe_draw_elements_instanced(struct pipe_context *pipe, struct pipe_buffer *indexBuffer, unsigned indexSize, diff --git a/src/gallium/include/pipe/p_context.h b/src/gallium/include/pipe/p_context.h index 6394e095d3..f2242d2069 100644 --- a/src/gallium/include/pipe/p_context.h +++ b/src/gallium/include/pipe/p_context.h @@ -69,21 +69,21 @@ struct pipe_context { unsigned indexSize, unsigned mode, unsigned start, unsigned count); - boolean (*draw_arrays_instanced)(struct pipe_context *pipe, - unsigned mode, - unsigned start, - unsigned count, - unsigned startInstance, - unsigned instanceCount); - - boolean (*draw_elements_instanced)(struct pipe_context *pipe, - struct pipe_buffer *indexBuffer, - unsigned indexSize, - unsigned mode, - unsigned start, - unsigned count, - unsigned startInstance, - unsigned instanceCount); + void (*draw_arrays_instanced)(struct pipe_context *pipe, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount); + + void (*draw_elements_instanced)(struct pipe_context *pipe, + struct pipe_buffer *indexBuffer, + unsigned indexSize, + unsigned mode, + unsigned start, + unsigned count, + unsigned startInstance, + unsigned instanceCount); /* XXX: this is (probably) a temporary entrypoint, as the range * information should be available from the vertex_buffer state. -- cgit v1.2.3