gallium: make pipe_draw_indirect_info * a draw_vbo parameter

This removes 8 bytes from pipe_draw_info (think u_threaded_context)
and a lot of info->indirect pointer indirections.

Reviewed-by: Pierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer@amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/7441>
This commit is contained in:
Marek Olšák 2020-11-01 06:38:32 -05:00 committed by Marge Bot
parent 1a717dca04
commit abe8ef862f
84 changed files with 514 additions and 402 deletions

View File

@ -1722,25 +1722,26 @@ cso_restore_state(struct cso_context *cso)
void
cso_draw_vbo(struct cso_context *cso,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct u_vbuf *vbuf = cso->vbuf_current;
/* We can't have both indirect drawing and SO-vertex-count drawing */
assert(!info->indirect ||
info->indirect->buffer == NULL ||
info->indirect->count_from_stream_output == NULL);
assert(!indirect ||
indirect->buffer == NULL ||
indirect->count_from_stream_output == NULL);
/* We can't have SO-vertex-count drawing with an index buffer */
assert(info->index_size == 0 ||
!info->indirect ||
info->indirect->count_from_stream_output == NULL);
!indirect ||
indirect->count_from_stream_output == NULL);
if (vbuf) {
u_vbuf_draw_vbo(vbuf, info);
u_vbuf_draw_vbo(vbuf, info, indirect);
} else {
struct pipe_context *pipe = cso->pipe;
pipe->draw_vbo(pipe, info);
pipe->draw_vbo(pipe, info, indirect);
}
}
@ -1757,7 +1758,7 @@ cso_draw_arrays(struct cso_context *cso, uint mode, uint start, uint count)
info.min_index = start;
info.max_index = start + count - 1;
cso_draw_vbo(cso, &info);
cso_draw_vbo(cso, &info, NULL);
}
void
@ -1777,5 +1778,5 @@ cso_draw_arrays_instanced(struct cso_context *cso, uint mode,
info.start_instance = start_instance;
info.instance_count = instance_count;
cso_draw_vbo(cso, &info);
cso_draw_vbo(cso, &info, NULL);
}

View File

@ -217,7 +217,8 @@ cso_set_vertex_buffers_and_elements(struct cso_context *ctx,
void
cso_draw_vbo(struct cso_context *cso,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
void
cso_draw_arrays_instanced(struct cso_context *cso, uint mode,

View File

@ -323,7 +323,8 @@ draw_set_mapped_so_targets(struct draw_context *draw,
*/
void draw_vbo(struct draw_context *draw,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
/*******************************************************************************

View File

@ -440,14 +440,15 @@ draw_pt_arrays_restart(struct draw_context *draw,
*/
static void
resolve_draw_info(const struct pipe_draw_info *raw_info,
const struct pipe_draw_indirect_info *indirect,
struct pipe_draw_info *info,
struct pipe_vertex_buffer *vertex_buffer)
{
memcpy(info, raw_info, sizeof(struct pipe_draw_info));
if (raw_info->indirect && raw_info->indirect->count_from_stream_output) {
if (indirect && indirect->count_from_stream_output) {
struct draw_so_target *target =
(struct draw_so_target *)info->indirect->count_from_stream_output;
(struct draw_so_target *)indirect->count_from_stream_output;
assert(vertex_buffer != NULL);
info->count = vertex_buffer->stride == 0 ? 0 :
target->internal_offset / vertex_buffer->stride;
@ -455,7 +456,6 @@ resolve_draw_info(const struct pipe_draw_info *raw_info,
/* Stream output draw can not be indexed */
debug_assert(!info->index_size);
info->max_index = info->count - 1;
info->indirect = NULL;
}
}
@ -467,7 +467,8 @@ resolve_draw_info(const struct pipe_draw_info *raw_info,
*/
void
draw_vbo(struct draw_context *draw,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
unsigned instance;
unsigned index_limit;
@ -483,7 +484,7 @@ draw_vbo(struct draw_context *draw,
*/
util_fpstate_set_denorms_to_zero(fpstate);
resolve_draw_info(info, &resolved_info, &(draw->pt.vertex_buffer[0]));
resolve_draw_info(info, indirect, &resolved_info, &(draw->pt.vertex_buffer[0]));
info = &resolved_info;
if (info->index_size)

View File

@ -351,19 +351,19 @@ dd_dump_flush(struct dd_draw_state *dstate, struct call_flush *info, FILE *f)
}
static void
dd_dump_draw_vbo(struct dd_draw_state *dstate, struct pipe_draw_info *info, FILE *f)
dd_dump_draw_vbo(struct dd_draw_state *dstate, struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect, FILE *f)
{
int sh, i;
DUMP(draw_info, info);
if (info->indirect) {
if (info->indirect->buffer)
DUMP_M(resource, info, indirect->buffer);
if (info->indirect->indirect_draw_count)
DUMP_M(resource, info, indirect->indirect_draw_count);
if (info->indirect->count_from_stream_output)
DUMP_M(stream_output_target, info,
indirect->count_from_stream_output);
if (indirect) {
if (indirect->buffer)
DUMP_M(resource, indirect, buffer);
if (indirect->indirect_draw_count)
DUMP_M(resource, indirect, indirect_draw_count);
if (indirect->count_from_stream_output)
DUMP_M(stream_output_target, indirect, count_from_stream_output);
}
fprintf(f, "\n");
@ -633,7 +633,8 @@ dd_dump_call(FILE *f, struct dd_draw_state *state, struct dd_call *call)
dd_dump_flush(state, &call->info.flush, f);
break;
case CALL_DRAW_VBO:
dd_dump_draw_vbo(state, &call->info.draw_vbo.draw, f);
dd_dump_draw_vbo(state, &call->info.draw_vbo.draw,
&call->info.draw_vbo.indirect, f);
break;
case CALL_LAUNCH_GRID:
dd_dump_launch_grid(state, &call->info.launch_grid, f);
@ -1298,7 +1299,8 @@ dd_context_flush(struct pipe_context *_pipe,
static void
dd_context_draw_vbo(struct pipe_context *_pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct dd_context *dctx = dd_context(_pipe);
struct pipe_context *pipe = dctx->pipe;
@ -1312,25 +1314,23 @@ dd_context_draw_vbo(struct pipe_context *_pipe,
info->index.resource);
}
if (info->indirect) {
record->call.info.draw_vbo.indirect = *info->indirect;
record->call.info.draw_vbo.draw.indirect = &record->call.info.draw_vbo.indirect;
if (indirect) {
record->call.info.draw_vbo.indirect = *indirect;
record->call.info.draw_vbo.indirect.buffer = NULL;
pipe_resource_reference(&record->call.info.draw_vbo.indirect.buffer,
info->indirect->buffer);
indirect->buffer);
record->call.info.draw_vbo.indirect.indirect_draw_count = NULL;
pipe_resource_reference(&record->call.info.draw_vbo.indirect.indirect_draw_count,
info->indirect->indirect_draw_count);
indirect->indirect_draw_count);
record->call.info.draw_vbo.indirect.count_from_stream_output = NULL;
pipe_so_target_reference(&record->call.info.draw_vbo.indirect.count_from_stream_output,
info->indirect->count_from_stream_output);
indirect->count_from_stream_output);
} else {
memset(&record->call.info.draw_vbo.indirect, 0, sizeof(*info->indirect));
memset(&record->call.info.draw_vbo.indirect, 0, sizeof(*indirect));
}
dd_before_draw(dctx, record);
pipe->draw_vbo(pipe, info);
pipe->draw_vbo(pipe, info, indirect);
dd_after_draw(dctx, record);
}

View File

@ -30,7 +30,8 @@
#include "util/u_inlines.h"
#include "util/u_transfer.h"
static void noop_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
static void noop_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
}

View File

@ -114,7 +114,8 @@ rbug_draw_block_locked(struct rbug_context *rb_pipe, int flag)
}
static void
rbug_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *_info)
rbug_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *_info,
const struct pipe_draw_indirect_info *_indirect)
{
struct rbug_context *rb_pipe = rbug_context(_pipe);
struct pipe_context *pipe = rb_pipe->pipe;
@ -132,7 +133,7 @@ rbug_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *_info)
if (!(rb_pipe->curr.shader[PIPE_SHADER_FRAGMENT] && rb_pipe->curr.shader[PIPE_SHADER_FRAGMENT]->disabled) &&
!(rb_pipe->curr.shader[PIPE_SHADER_GEOMETRY] && rb_pipe->curr.shader[PIPE_SHADER_GEOMETRY]->disabled) &&
!(rb_pipe->curr.shader[PIPE_SHADER_VERTEX] && rb_pipe->curr.shader[PIPE_SHADER_VERTEX]->disabled))
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, _indirect);
mtx_unlock(&rb_pipe->call_mutex);
rbug_draw_block_locked(rb_pipe, RBUG_BLOCK_AFTER);

View File

@ -89,7 +89,8 @@ trace_surface_unwrap(struct trace_context *tr_ctx,
static void
trace_context_draw_vbo(struct pipe_context *_pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct trace_context *tr_ctx = trace_context(_pipe);
struct pipe_context *pipe = tr_ctx->pipe;
@ -98,10 +99,11 @@ trace_context_draw_vbo(struct pipe_context *_pipe,
trace_dump_arg(ptr, pipe);
trace_dump_arg(draw_info, info);
trace_dump_arg(draw_indirect_info, indirect);
trace_dump_trace_flush();
pipe->draw_vbo(pipe, info);
pipe->draw_vbo(pipe, info, indirect);
trace_dump_call_end();
}

View File

@ -793,19 +793,27 @@ void trace_dump_draw_info(const struct pipe_draw_info *state)
trace_dump_member(uint, state, restart_index);
trace_dump_member(ptr, state, index.resource);
trace_dump_struct_end();
}
if (!state->indirect) {
trace_dump_member(ptr, state, indirect);
} else {
trace_dump_member(uint, state, indirect->offset);
trace_dump_member(uint, state, indirect->stride);
trace_dump_member(uint, state, indirect->draw_count);
trace_dump_member(uint, state, indirect->indirect_draw_count_offset);
trace_dump_member(ptr, state, indirect->buffer);
trace_dump_member(ptr, state, indirect->indirect_draw_count);
trace_dump_member(ptr, state, indirect->count_from_stream_output);
void trace_dump_draw_indirect_info(const struct pipe_draw_indirect_info *state)
{
if (!trace_dumping_enabled_locked())
return;
if (!state) {
trace_dump_null();
return;
}
trace_dump_struct_begin("pipe_draw_indirect_info");
trace_dump_member(uint, state, offset);
trace_dump_member(uint, state, stride);
trace_dump_member(uint, state, draw_count);
trace_dump_member(uint, state, indirect_draw_count_offset);
trace_dump_member(ptr, state, buffer);
trace_dump_member(ptr, state, indirect_draw_count);
trace_dump_member(ptr, state, count_from_stream_output);
trace_dump_struct_end();
}

View File

@ -82,6 +82,8 @@ void trace_dump_shader_buffer(const struct pipe_shader_buffer *buffer);
void trace_dump_draw_info(const struct pipe_draw_info *state);
void trace_dump_draw_indirect_info(const struct pipe_draw_indirect_info *state);
void trace_dump_blit_info(const struct pipe_blit_info *);
void trace_dump_query_result(unsigned query_type,

View File

@ -172,7 +172,7 @@ util_primconvert_draw_vbo(struct primconvert_context *pc,
u_upload_unmap(pc->pipe->stream_uploader);
/* to the translated draw: */
pc->pipe->draw_vbo(pc->pipe, &new_info);
pc->pipe->draw_vbo(pc->pipe, &new_info, NULL);
pipe_resource_reference(&new_info.index.resource, NULL);
}

View File

@ -126,30 +126,31 @@ util_draw_max_index(
}
/* This extracts the draw arguments from the info_in->indirect resource,
/* This extracts the draw arguments from the indirect resource,
* puts them into a new instance of pipe_draw_info, and calls draw_vbo on it.
*/
void
util_draw_indirect(struct pipe_context *pipe,
const struct pipe_draw_info *info_in)
const struct pipe_draw_info *info_in,
const struct pipe_draw_indirect_info *indirect)
{
struct pipe_draw_info info;
struct pipe_transfer *transfer;
uint32_t *params;
unsigned num_params = info_in->index_size ? 5 : 4;
assert(info_in->indirect);
assert(!info_in->indirect->count_from_stream_output);
assert(indirect);
assert(!indirect->count_from_stream_output);
memcpy(&info, info_in, sizeof(info));
uint32_t draw_count = info_in->indirect->draw_count;
uint32_t draw_count = indirect->draw_count;
if (info_in->indirect->indirect_draw_count) {
if (indirect->indirect_draw_count) {
struct pipe_transfer *dc_transfer;
uint32_t *dc_param = pipe_buffer_map_range(pipe,
info_in->indirect->indirect_draw_count,
info_in->indirect->indirect_draw_count_offset,
indirect->indirect_draw_count,
indirect->indirect_draw_count_offset,
4, PIPE_MAP_READ, &dc_transfer);
if (!dc_transfer) {
debug_printf("%s: failed to map indirect draw count buffer\n", __FUNCTION__);
@ -160,13 +161,13 @@ util_draw_indirect(struct pipe_context *pipe,
pipe_buffer_unmap(pipe, dc_transfer);
}
if (info_in->indirect->stride)
num_params = MIN2(info_in->indirect->stride / 4, num_params);
if (indirect->stride)
num_params = MIN2(indirect->stride / 4, num_params);
params = (uint32_t *)
pipe_buffer_map_range(pipe,
info_in->indirect->buffer,
info_in->indirect->offset,
(num_params * info_in->indirect->draw_count) * sizeof(uint32_t),
indirect->buffer,
indirect->offset,
(num_params * indirect->draw_count) * sizeof(uint32_t),
PIPE_MAP_READ,
&transfer);
if (!transfer) {
@ -181,11 +182,10 @@ util_draw_indirect(struct pipe_context *pipe,
info.index_bias = info_in->index_size ? params[3] : 0;
info.start_instance = info_in->index_size ? params[4] : params[3];
info.drawid = i;
info.indirect = NULL;
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, NULL);
params += info_in->indirect->stride / 4;
params += indirect->stride / 4;
}
pipe_buffer_unmap(pipe, transfer);
}

View File

@ -63,7 +63,7 @@ util_draw_arrays(struct pipe_context *pipe,
info.min_index = start;
info.max_index = start + count - 1;
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, NULL);
}
static inline void
@ -85,7 +85,7 @@ util_draw_elements(struct pipe_context *pipe,
info.count = count;
info.index_bias = index_bias;
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, NULL);
}
static inline void
@ -107,7 +107,7 @@ util_draw_arrays_instanced(struct pipe_context *pipe,
info.min_index = start;
info.max_index = start + count - 1;
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, NULL);
}
static inline void
@ -134,7 +134,7 @@ util_draw_elements_instanced(struct pipe_context *pipe,
info.start_instance = start_instance;
info.instance_count = instance_count;
pipe->draw_vbo(pipe, &info);
pipe->draw_vbo(pipe, &info, NULL);
}
@ -143,7 +143,8 @@ util_draw_elements_instanced(struct pipe_context *pipe,
*/
void
util_draw_indirect(struct pipe_context *pipe,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
unsigned

View File

@ -200,6 +200,10 @@ util_dump_stream_output_target(FILE *stream,
void
util_dump_draw_info(FILE *stream, const struct pipe_draw_info *state);
void
util_dump_draw_indirect_info(FILE *stream,
const struct pipe_draw_indirect_info *indirect);
void
util_dump_grid_info(FILE *stream, const struct pipe_grid_info *state);

View File

@ -941,19 +941,26 @@ util_dump_draw_info(FILE *stream, const struct pipe_draw_info *state)
else
util_dump_member(stream, ptr, state, index.resource);
}
util_dump_struct_end(stream);
}
if (!state->indirect) {
util_dump_member(stream, ptr, state, indirect);
} else {
util_dump_member(stream, uint, state, indirect->offset);
util_dump_member(stream, uint, state, indirect->stride);
util_dump_member(stream, uint, state, indirect->draw_count);
util_dump_member(stream, uint, state, indirect->indirect_draw_count_offset);
util_dump_member(stream, ptr, state, indirect->buffer);
util_dump_member(stream, ptr, state, indirect->indirect_draw_count);
util_dump_member(stream, ptr, state, indirect->count_from_stream_output);
void
util_dump_draw_indirect_info(FILE *stream,
const struct pipe_draw_indirect_info *state)
{
if (!state) {
util_dump_null(stream);
return;
}
util_dump_struct_begin(stream, "pipe_draw_indirect_info");
util_dump_member(stream, uint, state, offset);
util_dump_member(stream, uint, state, stride);
util_dump_member(stream, uint, state, draw_count);
util_dump_member(stream, uint, state, indirect_draw_count_offset);
util_dump_member(stream, ptr, state, buffer);
util_dump_member(stream, ptr, state, indirect_draw_count);
util_dump_member(stream, ptr, state, count_from_stream_output);
util_dump_struct_end(stream);
}

View File

@ -38,7 +38,7 @@ typedef struct {
} DrawElementsIndirectCommand;
static DrawElementsIndirectCommand
read_indirect_elements(struct pipe_context *context, struct pipe_draw_indirect_info *indirect)
read_indirect_elements(struct pipe_context *context, const struct pipe_draw_indirect_info *indirect)
{
DrawElementsIndirectCommand ret;
struct pipe_transfer *transfer = NULL;
@ -99,6 +99,7 @@ util_translate_prim_restart_data(unsigned index_size,
enum pipe_error
util_translate_prim_restart_ib(struct pipe_context *context,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect_info,
struct pipe_resource **dst_buffer)
{
struct pipe_screen *screen = context->screen;
@ -114,8 +115,8 @@ util_translate_prim_restart_ib(struct pipe_context *context,
dst_index_size = MAX2(2, info->index_size);
assert(dst_index_size == 2 || dst_index_size == 4);
if (info->indirect && info->indirect->buffer) {
indirect = read_indirect_elements(context, info->indirect);
if (indirect_info && indirect_info->buffer) {
indirect = read_indirect_elements(context, indirect_info);
count = indirect.count;
start = indirect.firstIndex;
}
@ -220,7 +221,8 @@ add_range(struct range_info *info, unsigned start, unsigned count)
*/
enum pipe_error
util_draw_vbo_without_prim_restart(struct pipe_context *context,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect_info)
{
const void *src_map;
struct range_info ranges = {0};
@ -235,8 +237,8 @@ util_draw_vbo_without_prim_restart(struct pipe_context *context,
assert(info->index_size);
assert(info->primitive_restart);
if (info->indirect && info->indirect->buffer) {
indirect = read_indirect_elements(context, info->indirect);
if (indirect_info && indirect_info->buffer) {
indirect = read_indirect_elements(context, indirect_info);
info_count = indirect.count;
info_start = indirect.firstIndex;
info_instance_count = indirect.primCount;
@ -307,13 +309,12 @@ util_draw_vbo_without_prim_restart(struct pipe_context *context,
/* draw ranges between the restart indexes */
new_info = *info;
/* we've effectively remapped this to a direct draw */
new_info.indirect = NULL;
new_info.instance_count = info_instance_count;
new_info.primitive_restart = FALSE;
for (i = 0; i < ranges.count; i++) {
new_info.start = ranges.ranges[i].start;
new_info.count = ranges.ranges[i].count;
context->draw_vbo(context, &new_info);
context->draw_vbo(context, &new_info, NULL);
}
FREE(ranges.ranges);

View File

@ -49,11 +49,13 @@ util_translate_prim_restart_data(unsigned index_size,
enum pipe_error
util_translate_prim_restart_ib(struct pipe_context *context,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
struct pipe_resource **dst_buffer);
enum pipe_error
util_draw_vbo_without_prim_restart(struct pipe_context *context,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
static inline unsigned
util_prim_restart_index_from_size(unsigned index_size)

View File

@ -125,7 +125,6 @@ tc_batch_execute(void *job, UNUSED int thread_index)
/* If at least 2 consecutive draw calls can be merged... */
if (next != last && next->call_id == TC_CALL_draw_vbo &&
first_info->draw.drawid == 0 &&
!first_info->draw.indirect &&
is_next_call_a_mergeable_draw(first_info, next, &next_info)) {
/* Merge up to 256 draw calls. */
struct pipe_draw_start_count multi[256];
@ -151,7 +150,7 @@ tc_batch_execute(void *job, UNUSED int thread_index)
pipe_resource_reference(&next_info->draw.index.resource, NULL);
}
pipe->multi_draw(pipe, &first_info->draw, multi, num_draws);
pipe->multi_draw(pipe, &first_info->draw, NULL, multi, num_draws);
if (first_info->draw.index_size)
pipe_resource_reference(&first_info->draw.index.resource, NULL);
iter = next;
@ -2197,40 +2196,69 @@ tc_call_draw_vbo(struct pipe_context *pipe, union tc_payload *payload)
{
struct tc_full_draw_info *info = (struct tc_full_draw_info*)payload;
pipe->draw_vbo(pipe, &info->draw);
pipe->draw_vbo(pipe, &info->draw, NULL);
if (info->draw.index_size)
pipe_resource_reference(&info->draw.index.resource, NULL);
if (info->draw.indirect) {
pipe_resource_reference(&info->indirect.buffer, NULL);
pipe_resource_reference(&info->indirect.indirect_draw_count, NULL);
pipe_so_target_reference(&info->indirect.count_from_stream_output, NULL);
}
}
static void
tc_call_draw_indirect(struct pipe_context *pipe, union tc_payload *payload)
{
struct tc_full_draw_info *info = (struct tc_full_draw_info*)payload;
pipe->draw_vbo(pipe, &info->draw, &info->indirect);
if (info->draw.index_size)
pipe_resource_reference(&info->draw.index.resource, NULL);
pipe_resource_reference(&info->indirect.buffer, NULL);
pipe_resource_reference(&info->indirect.indirect_draw_count, NULL);
pipe_so_target_reference(&info->indirect.count_from_stream_output, NULL);
}
static struct tc_full_draw_info *
tc_add_draw_vbo(struct pipe_context *_pipe, bool indirect)
{
return (struct tc_full_draw_info*)
tc_add_sized_call(threaded_context(_pipe), TC_CALL_draw_vbo,
indirect ? sizeof(struct tc_full_draw_info) :
sizeof(struct pipe_draw_info));
if (indirect) {
return (struct tc_full_draw_info*)
tc_add_sized_call(threaded_context(_pipe), TC_CALL_draw_indirect,
sizeof(struct tc_full_draw_info));
} else {
return (struct tc_full_draw_info*)
tc_add_sized_call(threaded_context(_pipe), TC_CALL_draw_vbo,
sizeof(struct pipe_draw_info));
}
}
static void
tc_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *info)
tc_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct threaded_context *tc = threaded_context(_pipe);
struct pipe_draw_indirect_info *indirect = info->indirect;
unsigned index_size = info->index_size;
bool has_user_indices = info->has_user_indices;
if (index_size && has_user_indices) {
if (unlikely(indirect)) {
assert(!has_user_indices);
struct tc_full_draw_info *p = tc_add_draw_vbo(_pipe, true);
if (index_size) {
tc_set_resource_reference(&p->draw.index.resource,
info->index.resource);
}
memcpy(&p->draw, info, sizeof(*info));
tc_set_resource_reference(&p->indirect.buffer, indirect->buffer);
tc_set_resource_reference(&p->indirect.indirect_draw_count,
indirect->indirect_draw_count);
p->indirect.count_from_stream_output = NULL;
pipe_so_target_reference(&p->indirect.count_from_stream_output,
indirect->count_from_stream_output);
memcpy(&p->indirect, indirect, sizeof(*indirect));
} else if (index_size && has_user_indices) {
unsigned size = info->count * index_size;
struct pipe_resource *buffer = NULL;
unsigned offset;
tc_assert(!indirect);
/* This must be done before adding draw_vbo, because it could generate
* e.g. transfer_unmap and flush partially-uninitialized draw_vbo
* to the driver if it was done afterwards.
@ -2248,23 +2276,12 @@ tc_draw_vbo(struct pipe_context *_pipe, const struct pipe_draw_info *info)
p->draw.start = offset >> util_logbase2(index_size);
} else {
/* Non-indexed call or indexed with a real index buffer. */
struct tc_full_draw_info *p = tc_add_draw_vbo(_pipe, indirect != NULL);
struct tc_full_draw_info *p = tc_add_draw_vbo(_pipe, false);
if (index_size) {
tc_set_resource_reference(&p->draw.index.resource,
info->index.resource);
}
memcpy(&p->draw, info, sizeof(*info));
if (indirect) {
tc_set_resource_reference(&p->draw.indirect->buffer, indirect->buffer);
tc_set_resource_reference(&p->indirect.indirect_draw_count,
indirect->indirect_draw_count);
p->indirect.count_from_stream_output = NULL;
pipe_so_target_reference(&p->indirect.count_from_stream_output,
indirect->count_from_stream_output);
memcpy(&p->indirect, indirect, sizeof(*indirect));
p->draw.indirect = &p->indirect;
}
}
}

View File

@ -27,6 +27,7 @@ CALL(buffer_subdata)
CALL(texture_subdata)
CALL(emit_string_marker)
CALL(draw_vbo)
CALL(draw_indirect)
CALL(launch_grid)
CALL(resource_copy_region)
CALL(blit)

View File

@ -1257,7 +1257,6 @@ u_vbuf_split_indexed_multidraw(struct u_vbuf *mgr, struct pipe_draw_info *info,
unsigned draw_count)
{
assert(info->index_size);
info->indirect = NULL;
for (unsigned i = 0; i < draw_count; i++) {
unsigned offset = i * stride / 4;
@ -1272,11 +1271,12 @@ u_vbuf_split_indexed_multidraw(struct u_vbuf *mgr, struct pipe_draw_info *info,
info->index_bias = indirect_data[offset + 3];
info->start_instance = indirect_data[offset + 4];
u_vbuf_draw_vbo(mgr, info);
u_vbuf_draw_vbo(mgr, info, NULL);
}
}
void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info)
void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct pipe_context *pipe = mgr->pipe;
int start_vertex;
@ -1299,15 +1299,14 @@ void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info)
u_vbuf_set_driver_vertex_buffers(mgr);
}
pipe->draw_vbo(pipe, info);
pipe->draw_vbo(pipe, info, indirect);
return;
}
new_info = *info;
/* Handle indirect (multi)draws. */
if (new_info.indirect && new_info.indirect->buffer) {
const struct pipe_draw_indirect_info *indirect = new_info.indirect;
if (indirect && indirect->buffer) {
unsigned draw_count = 0;
/* Get the number of draws. */
@ -1487,7 +1486,7 @@ void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info)
* We would have to break this drawing operation into several ones. */
/* Use some heuristic to see if unrolling indices improves
* performance. */
if (!info->indirect &&
if (!indirect &&
!new_info.primitive_restart &&
util_is_vbo_upload_ratio_too_large(new_info.count, num_vertices) &&
!u_vbuf_mapping_vertex_buffer_blocks(mgr)) {
@ -1565,7 +1564,7 @@ void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info)
u_upload_unmap(pipe->stream_uploader);
u_vbuf_set_driver_vertex_buffers(mgr);
pipe->draw_vbo(pipe, &new_info);
pipe->draw_vbo(pipe, &new_info, indirect);
if (mgr->using_translate) {
u_vbuf_translate_end(mgr);

View File

@ -77,7 +77,8 @@ void u_vbuf_unset_vertex_elements(struct u_vbuf *mgr);
void u_vbuf_set_vertex_buffers(struct u_vbuf *mgr,
unsigned start_slot, unsigned count,
const struct pipe_vertex_buffer *bufs);
void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info);
void u_vbuf_draw_vbo(struct u_vbuf *mgr, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
void u_vbuf_get_minmax_index(struct pipe_context *pipe,
const struct pipe_draw_info *info,
unsigned *out_min_index, unsigned *out_max_index);

View File

@ -319,7 +319,8 @@ d3d12_apply_resource_states(struct d3d12_context* ctx);
void
d3d12_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *dinfo);
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *indirect);
void
d3d12_blit(struct pipe_context *pctx,

View File

@ -357,7 +357,7 @@ twoface_emulation(struct d3d12_context *ctx,
{
/* draw backfaces */
ctx->base.bind_rasterizer_state(&ctx->base, rast->twoface_back);
d3d12_draw_vbo(&ctx->base, dinfo);
d3d12_draw_vbo(&ctx->base, dinfo, NULL);
/* restore real state */
ctx->base.bind_rasterizer_state(&ctx->base, rast);
@ -416,7 +416,8 @@ d3d12_last_vertex_stage(struct d3d12_context *ctx)
void
d3d12_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *dinfo)
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *indirect)
{
struct d3d12_context *ctx = d3d12_context(pctx);
struct d3d12_batch *batch;

View File

@ -223,7 +223,8 @@ etna_get_fs(struct etna_context *ctx, struct etna_shader_key key)
}
static void
etna_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
etna_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct etna_context *ctx = etna_context(pctx);
struct etna_screen *screen = ctx->screen;
@ -231,7 +232,7 @@ etna_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
uint32_t draw_mode;
unsigned i;
if (!info->indirect &&
if (!indirect &&
!info->primitive_restart &&
!u_trim_pipe_prim(info->mode, (unsigned*)&info->count))
return;

View File

@ -152,6 +152,7 @@ draw_impl(struct fd_context *ctx, const struct pipe_draw_info *info,
static bool
fd2_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *pinfo,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
if (!ctx->prog.fs || !ctx->prog.vs)

View File

@ -114,6 +114,7 @@ fixup_shader_state(struct fd_context *ctx, struct ir3_shader_key *key)
static bool
fd3_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct fd3_context *fd3_ctx = fd3_context(ctx);
@ -122,6 +123,7 @@ fd3_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
.vtx = &ctx->vtx,
.prog = &ctx->prog,
.info = info,
.indirect = indirect,
.key = {
.color_two_side = ctx->rasterizer->light_twoside,
.vclamp_color = ctx->rasterizer->clamp_vertex_color,

View File

@ -747,7 +747,7 @@ fd3_emit_state(struct fd_context *ctx, struct fd_ringbuffer *ring,
OUT_RING(ring, HLSQ_FLUSH);
if (emit->prog == &ctx->prog) { /* evil hack to deal sanely with clear path */
ir3_emit_vs_consts(vp, ring, ctx, emit->info);
ir3_emit_vs_consts(vp, ring, ctx, emit->info, emit->indirect);
if (!emit->binning_pass)
ir3_emit_fs_consts(fp, ring, ctx);
}

View File

@ -46,6 +46,7 @@ struct fd3_emit {
const struct fd_vertex_state *vtx;
const struct fd_program_stateobj *prog;
const struct pipe_draw_info *info;
const struct pipe_draw_indirect_info *indirect;
bool binning_pass;
struct ir3_shader_key key;
enum fd_dirty_3d_state dirty;

View File

@ -68,7 +68,7 @@ draw_impl(struct fd_context *ctx, struct fd_ringbuffer *ring,
fd4_draw_emit(ctx->batch, ring, primtype,
emit->binning_pass ? IGNORE_VISIBILITY : USE_VISIBILITY,
info, index_offset);
info, emit->indirect, index_offset);
}
/* fixup dirty shader state in case some "unrelated" (from the state-
@ -98,6 +98,7 @@ fixup_shader_state(struct fd_context *ctx, struct ir3_shader_key *key)
static bool
fd4_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct fd4_context *fd4_ctx = fd4_context(ctx);
@ -106,6 +107,7 @@ fd4_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
.vtx = &ctx->vtx,
.prog = &ctx->prog,
.info = info,
.indirect = indirect,
.key = {
.color_two_side = ctx->rasterizer->light_twoside,
.vclamp_color = ctx->rasterizer->clamp_vertex_color,

View File

@ -90,6 +90,7 @@ fd4_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
enum pc_di_primtype primtype,
enum pc_di_vis_cull_mode vismode,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct pipe_resource *idx_buffer = NULL;
@ -97,8 +98,8 @@ fd4_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
enum pc_di_src_sel src_sel;
uint32_t idx_size, idx_offset;
if (info->indirect && info->indirect->buffer) {
struct fd_resource *ind = fd_resource(info->indirect->buffer);
if (indirect && indirect->buffer) {
struct fd_resource *ind = fd_resource(indirect->buffer);
emit_marker(ring, 7);
@ -112,12 +113,12 @@ fd4_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
OUT_RELOC(ring, fd_resource(idx)->bo, index_offset, 0, 0);
OUT_RING(ring, A4XX_CP_DRAW_INDX_INDIRECT_2_INDX_SIZE(
idx->width0 - index_offset));
OUT_RELOC(ring, ind->bo, info->indirect->offset, 0, 0);
OUT_RELOC(ring, ind->bo, indirect->offset, 0, 0);
} else {
OUT_PKT3(ring, CP_DRAW_INDIRECT, 2);
OUT_RINGP(ring, DRAW4(primtype, DI_SRC_SEL_AUTO_INDEX, 0, 0),
&batch->draw_patches);
OUT_RELOC(ring, ind->bo, info->indirect->offset, 0, 0);
OUT_RELOC(ring, ind->bo, indirect->offset, 0, 0);
}
emit_marker(ring, 7);

View File

@ -700,7 +700,7 @@ fd4_emit_state(struct fd_context *ctx, struct fd_ringbuffer *ring,
}
if (emit->prog == &ctx->prog) { /* evil hack to deal sanely with clear path */
ir3_emit_vs_consts(vp, ring, ctx, emit->info);
ir3_emit_vs_consts(vp, ring, ctx, emit->info, emit->indirect);
if (!emit->binning_pass)
ir3_emit_fs_consts(fp, ring, ctx);
}

View File

@ -45,6 +45,7 @@ struct fd4_emit {
const struct fd_vertex_state *vtx;
const struct fd_program_stateobj *prog;
const struct pipe_draw_info *info;
const struct pipe_draw_indirect_info *indirect;
bool binning_pass;
struct ir3_shader_key key;
enum fd_dirty_3d_state dirty;

View File

@ -63,7 +63,7 @@ draw_impl(struct fd_context *ctx, struct fd_ringbuffer *ring,
fd5_emit_render_cntl(ctx, false, emit->binning_pass);
fd5_draw_emit(ctx->batch, ring, primtype,
emit->binning_pass ? IGNORE_VISIBILITY : USE_VISIBILITY,
info, index_offset);
info, emit->indirect, index_offset);
}
/* fixup dirty shader state in case some "unrelated" (from the state-
@ -93,6 +93,7 @@ fixup_shader_state(struct fd_context *ctx, struct ir3_shader_key *key)
static bool
fd5_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct fd5_context *fd5_ctx = fd5_context(ctx);
@ -101,6 +102,7 @@ fd5_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
.vtx = &ctx->vtx,
.prog = &ctx->prog,
.info = info,
.indirect = indirect,
.key = {
.color_two_side = ctx->rasterizer->light_twoside,
.vclamp_color = ctx->rasterizer->clamp_vertex_color,

View File

@ -84,6 +84,7 @@ fd5_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
enum pc_di_primtype primtype,
enum pc_di_vis_cull_mode vismode,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct pipe_resource *idx_buffer = NULL;
@ -91,8 +92,8 @@ fd5_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
enum pc_di_src_sel src_sel;
uint32_t max_indices, idx_offset;
if (info->indirect && info->indirect->buffer) {
struct fd_resource *ind = fd_resource(info->indirect->buffer);
if (indirect && indirect->buffer) {
struct fd_resource *ind = fd_resource(indirect->buffer);
emit_marker5(ring, 7);
@ -107,12 +108,12 @@ fd5_draw_emit(struct fd_batch *batch, struct fd_ringbuffer *ring,
OUT_RELOC(ring, fd_resource(idx)->bo,
index_offset, 0, 0);
OUT_RING(ring, A5XX_CP_DRAW_INDX_INDIRECT_3_MAX_INDICES(max_indices));
OUT_RELOC(ring, ind->bo, info->indirect->offset, 0, 0);
OUT_RELOC(ring, ind->bo, indirect->offset, 0, 0);
} else {
OUT_PKT7(ring, CP_DRAW_INDIRECT, 3);
OUT_RINGP(ring, DRAW4(primtype, DI_SRC_SEL_AUTO_INDEX, 0, 0),
&batch->draw_patches);
OUT_RELOC(ring, ind->bo, info->indirect->offset, 0, 0);
OUT_RELOC(ring, ind->bo, indirect->offset, 0, 0);
}
emit_marker5(ring, 7);

View File

@ -707,7 +707,7 @@ fd5_emit_state(struct fd_context *ctx, struct fd_ringbuffer *ring,
A5XX_SP_FS_OUTPUT_CNTL_SAMPLEMASK_REGID(regid(63, 0)));
}
ir3_emit_vs_consts(vp, ring, ctx, emit->info);
ir3_emit_vs_consts(vp, ring, ctx, emit->info, emit->indirect);
if (!emit->binning_pass)
ir3_emit_fs_consts(fp, ring, ctx);

View File

@ -45,6 +45,7 @@ struct fd5_emit {
const struct fd_vertex_state *vtx;
const struct fd_program_stateobj *prog;
const struct pipe_draw_info *info;
const struct pipe_draw_indirect_info *indirect;
bool binning_pass;
struct ir3_shader_key key;
enum fd_dirty_3d_state dirty;

View File

@ -359,7 +359,7 @@ fd6_emit_consts(struct fd6_emit *emit)
if (ir3_needs_vs_driver_params(vs)) {
struct fd_ringbuffer *dpconstobj = fd_submit_new_ringbuffer(
ctx->batch->submit, IR3_DP_VS_COUNT * 4, FD_RINGBUFFER_STREAMING);
ir3_emit_vs_driver_params(vs, dpconstobj, ctx, emit->info);
ir3_emit_vs_driver_params(vs, dpconstobj, ctx, emit->info, emit->indirect);
fd6_emit_take_group(emit, dpconstobj, FD6_GROUP_VS_DRIVER_PARAMS, ENABLE_ALL);
fd6_ctx->has_dp_state = true;
} else if (fd6_ctx->has_dp_state) {

View File

@ -47,9 +47,10 @@ static void
draw_emit_indirect(struct fd_ringbuffer *ring,
struct CP_DRAW_INDX_OFFSET_0 *draw0,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct fd_resource *ind = fd_resource(info->indirect->buffer);
struct fd_resource *ind = fd_resource(indirect->buffer);
if (info->index_size) {
struct pipe_resource *idx = info->index.resource;
@ -61,13 +62,13 @@ draw_emit_indirect(struct fd_ringbuffer *ring,
fd_resource(idx)->bo, index_offset),
A5XX_CP_DRAW_INDX_INDIRECT_3(.max_indices = max_indices),
A5XX_CP_DRAW_INDX_INDIRECT_INDIRECT(
ind->bo, info->indirect->offset)
ind->bo, indirect->offset)
);
} else {
OUT_PKT(ring, CP_DRAW_INDIRECT,
pack_CP_DRAW_INDX_OFFSET_0(*draw0),
A5XX_CP_DRAW_INDIRECT_INDIRECT(
ind->bo, info->indirect->offset)
ind->bo, indirect->offset)
);
}
}
@ -140,6 +141,7 @@ fixup_draw_state(struct fd_context *ctx, struct fd6_emit *emit)
static bool
fd6_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset)
{
struct fd6_context *fd6_ctx = fd6_context(ctx);
@ -148,6 +150,7 @@ fd6_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
.ctx = ctx,
.vtx = &ctx->vtx,
.info = info,
.indirect = indirect,
.key = {
.vs = ctx->prog.vs,
.gs = ctx->prog.gs,
@ -195,7 +198,7 @@ fd6_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
if (emit.key.gs)
emit.key.key.has_gs = true;
if (!(emit.key.hs || emit.key.ds || emit.key.gs || (info->indirect && info->indirect->buffer)))
if (!(emit.key.hs || emit.key.ds || emit.key.gs || (indirect && indirect->buffer)))
fd6_vsc_update_sizes(ctx->batch, info);
fixup_shader_state(ctx, &emit.key.key);
@ -315,8 +318,8 @@ fd6_draw_vbo(struct fd_context *ctx, const struct pipe_draw_info *info,
*/
emit_marker6(ring, 7);
if (info->indirect && info->indirect->buffer) {
draw_emit_indirect(ring, &draw0, info, index_offset);
if (indirect && indirect->buffer) {
draw_emit_indirect(ring, &draw0, info, indirect, index_offset);
} else {
draw_emit(ring, &draw0, info, index_offset);
}

View File

@ -86,6 +86,7 @@ struct fd6_emit {
struct fd_context *ctx;
const struct fd_vertex_state *vtx;
const struct pipe_draw_info *info;
const struct pipe_draw_indirect_info *indirect;
struct ir3_cache_key key;
enum fd_dirty_3d_state dirty;

View File

@ -238,7 +238,7 @@ fd_blitter_clear(struct pipe_context *pctx, unsigned buffers,
.max_index = 1,
.instance_count = 1,
};
pctx->draw_vbo(pctx, &info);
pctx->draw_vbo(pctx, &info, NULL);
/* We expect that this should not have triggered a change in pfb: */
assert(util_framebuffer_state_equal(pfb, &ctx->framebuffer));

View File

@ -390,6 +390,7 @@ struct fd_context {
/* draw: */
bool (*draw_vbo)(struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
unsigned index_offset);
bool (*clear)(struct fd_context *ctx, unsigned buffers,
const union pipe_color_union *color, double depth, unsigned stencil);

View File

@ -59,7 +59,8 @@ resource_written(struct fd_batch *batch, struct pipe_resource *prsc)
}
static void
batch_draw_tracking(struct fd_batch *batch, const struct pipe_draw_info *info)
batch_draw_tracking(struct fd_batch *batch, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct fd_context *ctx = batch->ctx;
struct pipe_framebuffer_state *pfb = &batch->framebuffer;
@ -175,8 +176,8 @@ batch_draw_tracking(struct fd_batch *batch, const struct pipe_draw_info *info)
resource_read(batch, info->index.resource);
/* Mark indirect draw buffer as being read */
if (info->indirect && info->indirect->buffer)
resource_read(batch, info->indirect->buffer);
if (indirect && indirect->buffer)
resource_read(batch, indirect->buffer);
/* Mark textures as being read */
if (ctx->dirty_shader[PIPE_SHADER_VERTEX] & FD_DIRTY_SHADER_TEX) {
@ -210,7 +211,8 @@ batch_draw_tracking(struct fd_batch *batch, const struct pipe_draw_info *info)
}
static void
fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct fd_context *ctx = fd_context(pctx);
@ -218,13 +220,13 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
* to be able to emulate it, to determine if game is feeding us
* bogus data:
*/
if (info->indirect && info->indirect->buffer && (fd_mesa_debug & FD_DBG_NOINDR)) {
util_draw_indirect(pctx, info);
if (indirect && indirect->buffer && (fd_mesa_debug & FD_DBG_NOINDR)) {
util_draw_indirect(pctx, info, indirect);
return;
}
if (info->mode != PIPE_PRIM_MAX &&
!info->indirect &&
!indirect &&
!info->primitive_restart &&
!u_trim_pipe_prim(info->mode, (unsigned*)&info->count))
return;
@ -266,7 +268,7 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
fd_context_all_dirty(ctx);
}
batch_draw_tracking(batch, info);
batch_draw_tracking(batch, info, indirect);
while (unlikely(!fd_batch_lock_submit(batch))) {
/* The current batch was flushed in batch_draw_tracking()
@ -275,7 +277,7 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
*/
fd_batch_reference(&batch, NULL);
batch = fd_context_batch(ctx);
batch_draw_tracking(batch, info);
batch_draw_tracking(batch, info, indirect);
assert(ctx->batch == batch);
}
@ -318,7 +320,7 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
util_format_short_name(pipe_surface_format(pfb->cbufs[0])),
util_format_short_name(pipe_surface_format(pfb->zsbuf)));
if (ctx->draw_vbo(ctx, info, index_offset))
if (ctx->draw_vbo(ctx, info, indirect, index_offset))
batch->needs_flush = true;
batch->num_vertices += info->count * info->instance_count;

View File

@ -513,8 +513,9 @@ ir3_needs_vs_driver_params(const struct ir3_shader_variant *v)
static inline void
ir3_emit_vs_driver_params(const struct ir3_shader_variant *v,
struct fd_ringbuffer *ring, struct fd_context *ctx,
const struct pipe_draw_info *info)
struct fd_ringbuffer *ring, struct fd_context *ctx,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
debug_assert(ir3_needs_vs_driver_params(v));
@ -555,13 +556,12 @@ ir3_emit_vs_driver_params(const struct ir3_shader_variant *v,
* and means we can't easily emit these consts in cmd
* stream so need to copy them to bo.
*/
if (info->indirect && needs_vtxid_base) {
struct pipe_draw_indirect_info *indirect = info->indirect;
if (indirect && needs_vtxid_base) {
struct pipe_resource *vertex_params_rsc =
pipe_buffer_create(&ctx->screen->base,
PIPE_BIND_CONSTANT_BUFFER, PIPE_USAGE_STREAM,
vertex_params_size * 4);
unsigned src_off = info->indirect->offset;;
unsigned src_off = indirect->offset;;
void *ptr;
ptr = fd_bo_map(fd_resource(vertex_params_rsc)->bo);
@ -596,7 +596,8 @@ ir3_emit_vs_driver_params(const struct ir3_shader_variant *v,
static inline void
ir3_emit_vs_consts(const struct ir3_shader_variant *v, struct fd_ringbuffer *ring,
struct fd_context *ctx, const struct pipe_draw_info *info)
struct fd_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
debug_assert(v->type == MESA_SHADER_VERTEX);
@ -605,7 +606,7 @@ ir3_emit_vs_consts(const struct ir3_shader_variant *v, struct fd_ringbuffer *rin
/* emit driver params every time: */
if (info && ir3_needs_vs_driver_params(v)) {
ring_wfi(ctx->batch, ring);
ir3_emit_vs_driver_params(v, ring, ctx, info);
ir3_emit_vs_driver_params(v, ring, ctx, info, indirect);
}
}
@ -621,7 +622,7 @@ ir3_emit_fs_consts(const struct ir3_shader_variant *v, struct fd_ringbuffer *rin
/* emit compute-shader consts: */
static inline void
ir3_emit_cs_consts(const struct ir3_shader_variant *v, struct fd_ringbuffer *ring,
struct fd_context *ctx, const struct pipe_grid_info *info)
struct fd_context *ctx, const struct pipe_grid_info *info)
{
debug_assert(gl_shader_stage_is_compute(v->type));

View File

@ -51,7 +51,8 @@ DEBUG_GET_ONCE_BOOL_OPTION(i915_no_vbuf, "I915_NO_VBUF", FALSE)
static void
i915_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
i915_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct i915_context *i915 = i915_context(pipe);
struct draw_context *draw = i915->draw;
@ -109,7 +110,7 @@ i915_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
/*
* Do the drawing
*/
draw_vbo(i915->draw, info);
draw_vbo(i915->draw, info, NULL);
/*
* unmap vertex/index buffers

View File

@ -822,7 +822,8 @@ void iris_copy_region(struct blorp_context *blorp,
/* iris_draw.c */
void iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info);
void iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
void iris_launch_grid(struct pipe_context *, const struct pipe_grid_info *);
/* iris_pipe_control.c */

View File

@ -111,17 +111,18 @@ iris_update_draw_info(struct iris_context *ice,
*/
static void
iris_update_draw_parameters(struct iris_context *ice,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
bool changed = false;
if (ice->state.vs_uses_draw_params) {
struct iris_state_ref *draw_params = &ice->draw.draw_params;
if (info->indirect && info->indirect->buffer) {
pipe_resource_reference(&draw_params->res, info->indirect->buffer);
if (indirect && indirect->buffer) {
pipe_resource_reference(&draw_params->res, indirect->buffer);
draw_params->offset =
info->indirect->offset + (info->index_size ? 12 : 8);
indirect->offset + (info->index_size ? 12 : 8);
changed = true;
ice->draw.params_valid = false;
@ -171,12 +172,14 @@ iris_update_draw_parameters(struct iris_context *ice,
static void
iris_indirect_draw_vbo(struct iris_context *ice,
const struct pipe_draw_info *dinfo)
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *dindirect)
{
struct iris_batch *batch = &ice->batches[IRIS_BATCH_RENDER];
struct pipe_draw_info info = *dinfo;
struct pipe_draw_indirect_info indirect = *dindirect;
if (info.indirect->indirect_draw_count &&
if (indirect.indirect_draw_count &&
ice->state.predicate == IRIS_PREDICATE_STATE_USE_BIT) {
/* Upload MI_PREDICATE_RESULT to GPR15.*/
batch->screen->vtbl.load_register_reg64(batch, CS_GPR(15), MI_PREDICATE_RESULT);
@ -185,22 +188,22 @@ iris_indirect_draw_vbo(struct iris_context *ice,
const uint64_t orig_dirty = ice->state.dirty;
const uint64_t orig_stage_dirty = ice->state.stage_dirty;
for (int i = 0; i < info.indirect->draw_count; i++) {
for (int i = 0; i < indirect.draw_count; i++) {
info.drawid = i;
iris_batch_maybe_flush(batch, 1500);
iris_update_draw_parameters(ice, &info);
iris_update_draw_parameters(ice, &info, &indirect);
batch->screen->vtbl.upload_render_state(ice, batch, &info, info.indirect);
batch->screen->vtbl.upload_render_state(ice, batch, &info, &indirect);
ice->state.dirty &= ~IRIS_ALL_DIRTY_FOR_RENDER;
ice->state.stage_dirty &= ~IRIS_ALL_STAGE_DIRTY_FOR_RENDER;
info.indirect->offset += info.indirect->stride;
indirect.offset += indirect.stride;
}
if (info.indirect->indirect_draw_count &&
if (indirect.indirect_draw_count &&
ice->state.predicate == IRIS_PREDICATE_STATE_USE_BIT) {
/* Restore MI_PREDICATE_RESULT. */
batch->screen->vtbl.load_register_reg64(batch, MI_PREDICATE_RESULT, CS_GPR(15));
@ -213,28 +216,29 @@ iris_indirect_draw_vbo(struct iris_context *ice,
static void
iris_simple_draw_vbo(struct iris_context *ice,
const struct pipe_draw_info *draw)
const struct pipe_draw_info *draw,
const struct pipe_draw_indirect_info *indirect)
{
struct iris_batch *batch = &ice->batches[IRIS_BATCH_RENDER];
iris_batch_maybe_flush(batch, 1500);
iris_update_draw_parameters(ice, draw);
iris_update_draw_parameters(ice, draw, indirect);
batch->screen->vtbl.upload_render_state(ice, batch, draw, draw->indirect);
batch->screen->vtbl.upload_render_state(ice, batch, draw, indirect);
}
/**
* The pipe->draw_vbo() driver hook. Performs a draw on the GPU.
*/
void
iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct iris_context *ice = (struct iris_context *) ctx;
struct iris_screen *screen = (struct iris_screen*)ice->ctx.screen;
const struct gen_device_info *devinfo = &screen->devinfo;
struct iris_batch *batch = &ice->batches[IRIS_BATCH_RENDER];
struct pipe_draw_indirect_info *indirect = info->indirect;
if (ice->state.predicate == IRIS_PREDICATE_STATE_DONT_RENDER)
return;
@ -271,9 +275,9 @@ iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
iris_handle_always_flush_cache(batch);
if (indirect && indirect->buffer)
iris_indirect_draw_vbo(ice, info);
iris_indirect_draw_vbo(ice, info, indirect);
else
iris_simple_draw_vbo(ice, info);
iris_simple_draw_vbo(ice, info, indirect);
iris_handle_always_flush_cache(batch);

View File

@ -1121,7 +1121,8 @@ lima_draw_vbo_count(struct pipe_context *pctx,
static void
lima_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
/* check if draw mode and vertex/index count match,
* otherwise gp will hang */

View File

@ -51,7 +51,8 @@
* the drawing to the 'draw' module.
*/
static void
llvmpipe_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
llvmpipe_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct llvmpipe_context *lp = llvmpipe_context(pipe);
struct draw_context *draw = lp->draw;
@ -61,8 +62,8 @@ llvmpipe_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
if (!llvmpipe_check_render_cond(lp))
return;
if (info->indirect && info->indirect->buffer) {
util_draw_indirect(pipe, info);
if (indirect && indirect->buffer) {
util_draw_indirect(pipe, info, indirect);
return;
}
@ -139,7 +140,7 @@ llvmpipe_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
!lp->queries_disabled);
/* draw! */
draw_vbo(draw, info);
draw_vbo(draw, info, indirect);
/*
* unmap vertex/index buffers

View File

@ -443,7 +443,7 @@ nv30_render_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
draw_set_indexes(draw, NULL, 0, 0);
}
draw_vbo(draw, info);
draw_vbo(draw, info, NULL);
draw_flush(draw);
if (info->index_size && transferi)

View File

@ -544,7 +544,8 @@ nv30_draw_elements(struct nv30_context *nv30, bool shorten,
}
static void
nv30_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
nv30_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nv30_context *nv30 = nv30_context(pipe);
struct nouveau_pushbuf *push = nv30->base.pushbuf;

View File

@ -291,7 +291,8 @@ nv50_cb_push(struct nouveau_context *nv,
unsigned offset, unsigned words, const uint32_t *data);
/* nv50_vbo.c */
void nv50_draw_vbo(struct pipe_context *, const struct pipe_draw_info *);
void nv50_draw_vbo(struct pipe_context *, const struct pipe_draw_info *,
const struct pipe_draw_indirect_info *indirect);
void *
nv50_vertex_state_create(struct pipe_context *pipe,
@ -303,7 +304,8 @@ nv50_vertex_state_delete(struct pipe_context *pipe, void *hwcso);
void nv50_vertex_arrays_validate(struct nv50_context *nv50);
/* nv50_push.c */
void nv50_push_vbo(struct nv50_context *, const struct pipe_draw_info *);
void nv50_push_vbo(struct nv50_context *, const struct pipe_draw_info *,
const struct pipe_draw_indirect_info *indirect);
/* nv84_video.c */
struct pipe_video_codec *

View File

@ -238,7 +238,8 @@ nv50_prim_gl(unsigned prim)
}
void
nv50_push_vbo(struct nv50_context *nv50, const struct pipe_draw_info *info)
nv50_push_vbo(struct nv50_context *nv50, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct push_context ctx;
unsigned i, index_size;
@ -292,10 +293,10 @@ nv50_push_vbo(struct nv50_context *nv50, const struct pipe_draw_info *info)
ctx.primitive_restart = info->primitive_restart;
ctx.restart_index = info->restart_index;
} else {
if (unlikely(info->indirect && info->indirect->count_from_stream_output)) {
if (unlikely(indirect && indirect->count_from_stream_output)) {
struct pipe_context *pipe = &nv50->base.pipe;
struct nv50_so_target *targ;
targ = nv50_so_target(info->indirect->count_from_stream_output);
targ = nv50_so_target(indirect->count_from_stream_output);
if (!targ->pq) {
NOUVEAU_ERR("draw_stream_output not supported on pre-NVA0 cards\n");
return;

View File

@ -699,10 +699,11 @@ nv50_draw_elements(struct nv50_context *nv50, bool shorten,
static void
nva0_draw_stream_output(struct nv50_context *nv50,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nouveau_pushbuf *push = nv50->base.pushbuf;
struct nv50_so_target *so = nv50_so_target(info->indirect->count_from_stream_output);
struct nv50_so_target *so = nv50_so_target(indirect->count_from_stream_output);
struct nv04_resource *res = nv04_resource(so->pipe.buffer);
unsigned num_instances = info->instance_count;
unsigned mode = nv50_prim_gl(info->mode);
@ -753,7 +754,8 @@ nv50_draw_vbo_kick_notify(struct nouveau_pushbuf *chan)
}
void
nv50_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
nv50_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nv50_context *nv50 = nv50_context(pipe);
struct nouveau_pushbuf *push = nv50->base.pushbuf;
@ -826,7 +828,7 @@ nv50_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
}
if (nv50->vbo_fifo) {
nv50_push_vbo(nv50, info);
nv50_push_vbo(nv50, info, indirect);
goto cleanup;
}
@ -874,8 +876,8 @@ nv50_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
info->mode, info->start, info->count,
info->instance_count, info->index_bias, info->index_size);
} else
if (unlikely(info->indirect && info->indirect->count_from_stream_output)) {
nva0_draw_stream_output(nv50, info);
if (unlikely(indirect && indirect->count_from_stream_output)) {
nva0_draw_stream_output(nv50, info, indirect);
} else {
nv50_draw_arrays(nv50,
info->mode, info->start, info->count,

View File

@ -413,7 +413,8 @@ nvc0_cb_bo_push(struct nouveau_context *,
unsigned offset, unsigned words, const uint32_t *data);
/* nvc0_vbo.c */
void nvc0_draw_vbo(struct pipe_context *, const struct pipe_draw_info *);
void nvc0_draw_vbo(struct pipe_context *, const struct pipe_draw_info *,
const struct pipe_draw_indirect_info *indirect);
void *
nvc0_vertex_state_create(struct pipe_context *pipe,
@ -436,8 +437,10 @@ nvc0_video_buffer_create(struct pipe_context *pipe,
const struct pipe_video_buffer *templat);
/* nvc0_push.c */
void nvc0_push_vbo(struct nvc0_context *, const struct pipe_draw_info *);
void nvc0_push_vbo_indirect(struct nvc0_context *, const struct pipe_draw_info *);
void nvc0_push_vbo(struct nvc0_context *, const struct pipe_draw_info *,
const struct pipe_draw_indirect_info *indirect);
void nvc0_push_vbo_indirect(struct nvc0_context *, const struct pipe_draw_info *,
const struct pipe_draw_indirect_info *indirect);
/* nve4_compute.c */
void nve4_launch_grid(struct pipe_context *, const struct pipe_grid_info *);

View File

@ -766,10 +766,11 @@ nvc0_draw_elements(struct nvc0_context *nvc0, bool shorten,
static void
nvc0_draw_stream_output(struct nvc0_context *nvc0,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nouveau_pushbuf *push = nvc0->base.pushbuf;
struct nvc0_so_target *so = nvc0_so_target(info->indirect->count_from_stream_output);
struct nvc0_so_target *so = nvc0_so_target(indirect->count_from_stream_output);
struct nv04_resource *res = nv04_resource(so->pipe.buffer);
unsigned mode = nvc0_prim_gl(info->mode);
unsigned num_instances = info->instance_count;
@ -802,13 +803,14 @@ nvc0_draw_stream_output(struct nvc0_context *nvc0,
}
static void
nvc0_draw_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
nvc0_draw_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nouveau_pushbuf *push = nvc0->base.pushbuf;
struct nv04_resource *buf = nv04_resource(info->indirect->buffer);
struct nv04_resource *buf_count = nv04_resource(info->indirect->indirect_draw_count);
unsigned size, macro, count = info->indirect->draw_count, drawid = info->drawid;
uint32_t offset = buf->offset + info->indirect->offset;
struct nv04_resource *buf = nv04_resource(indirect->buffer);
struct nv04_resource *buf_count = nv04_resource(indirect->indirect_draw_count);
unsigned size, macro, count = indirect->draw_count, drawid = info->drawid;
uint32_t offset = buf->offset + indirect->offset;
struct nvc0_screen *screen = nvc0->screen;
PUSH_SPACE(push, 7);
@ -857,7 +859,7 @@ nvc0_draw_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
*/
while (count) {
unsigned draws = count, pushes, i;
if (info->indirect->stride == size * 4) {
if (indirect->stride == size * 4) {
draws = MIN2(draws, (NV04_PFIFO_MAX_PACKET_LEN - 4) / size);
pushes = 1;
} else {
@ -877,20 +879,20 @@ nvc0_draw_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
if (buf_count) {
nouveau_pushbuf_data(push,
buf_count->bo,
buf_count->offset + info->indirect->indirect_draw_count_offset,
buf_count->offset + indirect->indirect_draw_count_offset,
NVC0_IB_ENTRY_1_NO_PREFETCH | 4);
}
if (pushes == 1) {
nouveau_pushbuf_data(push,
buf->bo, offset,
NVC0_IB_ENTRY_1_NO_PREFETCH | (size * 4 * draws));
offset += draws * info->indirect->stride;
offset += draws * indirect->stride;
} else {
for (i = 0; i < pushes; i++) {
nouveau_pushbuf_data(push,
buf->bo, offset,
NVC0_IB_ENTRY_1_NO_PREFETCH | (size * 4));
offset += info->indirect->stride;
offset += indirect->stride;
}
}
count -= draws;
@ -920,7 +922,8 @@ nvc0_update_prim_restart(struct nvc0_context *nvc0, bool en, uint32_t index)
}
void
nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct nvc0_context *nvc0 = nvc0_context(pipe);
struct nouveau_pushbuf *push = nvc0->base.pushbuf;
@ -938,7 +941,7 @@ nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
* if index count is larger and we expect repeated vertices, suggest upload.
*/
nvc0->vbo_push_hint =
(!info->indirect || info->indirect->count_from_stream_output) && info->index_size &&
(!indirect || indirect->count_from_stream_output) && info->index_size &&
(nvc0->vb_elt_limit >= (info->count * 2));
/* Check whether we want to switch vertex-submission mode. */
@ -1005,7 +1008,7 @@ nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
nvc0_state_validate_3d(nvc0, ~0);
if (nvc0->vertprog->vp.need_draw_parameters && (!info->indirect || info->indirect->count_from_stream_output)) {
if (nvc0->vertprog->vp.need_draw_parameters && (!indirect || indirect->count_from_stream_output)) {
PUSH_SPACE(push, 9);
BEGIN_NVC0(push, NVC0_3D(CB_SIZE), 3);
PUSH_DATA (push, NVC0_CB_AUX_SIZE);
@ -1057,10 +1060,10 @@ nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
}
if (nvc0->state.vbo_mode) {
if (info->indirect && info->indirect->buffer)
nvc0_push_vbo_indirect(nvc0, info);
if (indirect && indirect->buffer)
nvc0_push_vbo_indirect(nvc0, info, indirect);
else
nvc0_push_vbo(nvc0, info);
nvc0_push_vbo(nvc0, info, indirect);
goto cleanup;
}
@ -1088,11 +1091,11 @@ nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
nvc0->base.vbo_dirty = false;
}
if (unlikely(info->indirect && info->indirect->buffer)) {
nvc0_draw_indirect(nvc0, info);
if (unlikely(indirect && indirect->buffer)) {
nvc0_draw_indirect(nvc0, info, indirect);
} else
if (unlikely(info->indirect && info->indirect->count_from_stream_output)) {
nvc0_draw_stream_output(nvc0, info);
if (unlikely(indirect && indirect->count_from_stream_output)) {
nvc0_draw_stream_output(nvc0, info, indirect);
} else
if (info->index_size) {
bool shorten = info->max_index <= 65535;

View File

@ -490,7 +490,8 @@ typedef struct {
} DrawElementsIndirectCommand;
void
nvc0_push_vbo_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
nvc0_push_vbo_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
/* The strategy here is to just read the commands from the indirect buffer
* and do the draws. This is suboptimal, but will only happen in the case
@ -498,23 +499,22 @@ nvc0_push_vbo_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *i
*/
struct nvc0_screen *screen = nvc0->screen;
struct nouveau_pushbuf *push = nvc0->base.pushbuf;
struct nv04_resource *buf = nv04_resource(info->indirect->buffer);
struct nv04_resource *buf_count = nv04_resource(info->indirect->indirect_draw_count);
struct nv04_resource *buf = nv04_resource(indirect->buffer);
struct nv04_resource *buf_count = nv04_resource(indirect->indirect_draw_count);
unsigned i;
unsigned draw_count = info->indirect->draw_count;
unsigned draw_count = indirect->draw_count;
if (buf_count) {
uint32_t *count = nouveau_resource_map_offset(
&nvc0->base, buf_count, info->indirect->indirect_draw_count_offset,
&nvc0->base, buf_count, indirect->indirect_draw_count_offset,
NOUVEAU_BO_RD);
draw_count = *count;
}
uint8_t *buf_data = nouveau_resource_map_offset(
&nvc0->base, buf, info->indirect->offset, NOUVEAU_BO_RD);
&nvc0->base, buf, indirect->offset, NOUVEAU_BO_RD);
struct pipe_draw_info single = *info;
single.indirect = NULL;
for (i = 0; i < draw_count; i++, buf_data += info->indirect->stride) {
for (i = 0; i < draw_count; i++, buf_data += indirect->stride) {
if (info->index_size) {
DrawElementsIndirectCommand *cmd = (void *)buf_data;
single.start = info->start + cmd->firstIndex;
@ -543,7 +543,7 @@ nvc0_push_vbo_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *i
PUSH_DATA (push, single.drawid + i);
}
nvc0_push_vbo(nvc0, &single);
nvc0_push_vbo(nvc0, &single, NULL);
}
nouveau_resource_unmap(buf);
@ -552,7 +552,8 @@ nvc0_push_vbo_indirect(struct nvc0_context *nvc0, const struct pipe_draw_info *i
}
void
nvc0_push_vbo(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
nvc0_push_vbo(struct nvc0_context *nvc0, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct push_context ctx;
unsigned i, index_size;
@ -596,10 +597,10 @@ nvc0_push_vbo(struct nvc0_context *nvc0, const struct pipe_draw_info *info)
nvc0_push_map_idxbuf(&ctx, nvc0, info);
index_size = info->index_size;
} else {
if (unlikely(info->indirect && info->indirect->count_from_stream_output)) {
if (unlikely(indirect && indirect->count_from_stream_output)) {
struct pipe_context *pipe = &nvc0->base.pipe;
struct nvc0_so_target *targ;
targ = nvc0_so_target(info->indirect->count_from_stream_output);
targ = nvc0_so_target(indirect->count_from_stream_output);
pipe->get_query_result(pipe, targ->pq, true, (void *)&vert_count);
vert_count /= targ->stride;
}

View File

@ -330,6 +330,7 @@ panfrost_emit_primitive_size(struct panfrost_context *ctx,
static void
panfrost_draw_emit_tiler(struct panfrost_batch *batch,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
void *invocation_template,
mali_ptr shared_mem, mali_ptr indices,
mali_ptr fs_vary, mali_ptr varyings,
@ -363,8 +364,8 @@ panfrost_draw_emit_tiler(struct panfrost_batch *batch,
cfg.base_vertex_offset = info->index_bias - ctx->offset_start;
cfg.index_count = info->count;
} else {
cfg.index_count = info->indirect && info->indirect->count_from_stream_output ?
pan_so_target(info->indirect->count_from_stream_output)->offset :
cfg.index_count = indirect && indirect->count_from_stream_output ?
pan_so_target(indirect->count_from_stream_output)->offset :
ctx->vertex_count;
}
}
@ -422,7 +423,8 @@ panfrost_draw_emit_tiler(struct panfrost_batch *batch,
static void
panfrost_draw_vbo(
struct pipe_context *pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct panfrost_context *ctx = pan_context(pipe);
struct panfrost_device *device = pan_device(ctx->base.screen);
@ -441,7 +443,7 @@ panfrost_draw_vbo(
if (info->primitive_restart && info->index_size
&& info->restart_index != primitive_index) {
util_draw_vbo_without_prim_restart(pipe, info);
util_draw_vbo_without_prim_restart(pipe, info, indirect);
return;
}
@ -527,7 +529,7 @@ panfrost_draw_vbo(
/* Fire off the draw itself */
panfrost_draw_emit_vertex(batch, info, &invocation, shared_mem,
vs_vary, varyings, vertex.cpu);
panfrost_draw_emit_tiler(batch, info, &invocation, shared_mem, indices,
panfrost_draw_emit_tiler(batch, info, indirect, &invocation, shared_mem, indices,
fs_vary, varyings, pos, psiz, tiler.cpu);
panfrost_emit_vertex_tiler_jobs(batch, &vertex, &tiler);

View File

@ -780,7 +780,8 @@ static unsigned r300_max_vertex_count(struct r300_context *r300)
static void r300_draw_vbo(struct pipe_context* pipe,
const struct pipe_draw_info *dinfo)
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *indirect)
{
struct r300_context* r300 = r300_context(pipe);
struct pipe_draw_info info = *dinfo;
@ -838,7 +839,8 @@ static void r300_draw_vbo(struct pipe_context* pipe,
/* SW TCL elements, using Draw. */
static void r300_swtcl_draw_vbo(struct pipe_context* pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct r300_context* r300 = r300_context(pipe);
@ -859,7 +861,7 @@ static void r300_swtcl_draw_vbo(struct pipe_context* pipe,
r300_update_derived_state(r300);
draw_vbo(r300->draw, info);
draw_vbo(r300->draw, info, NULL);
draw_flush(r300->draw);
}

View File

@ -35,7 +35,8 @@
struct r300_stencilref_context {
void (*draw_vbo)(struct pipe_context *pipe,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
uint32_t rs_cull_mode;
uint32_t zb_stencilrefmask;
@ -101,18 +102,19 @@ static void r300_stencilref_end(struct r300_context *r300)
}
static void r300_stencilref_draw_vbo(struct pipe_context *pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct r300_context *r300 = r300_context(pipe);
struct r300_stencilref_context *sr = r300->stencilref_fallback;
if (!r300_stencilref_needed(r300)) {
sr->draw_vbo(pipe, info);
sr->draw_vbo(pipe, info, NULL);
} else {
r300_stencilref_begin(r300);
sr->draw_vbo(pipe, info);
sr->draw_vbo(pipe, info, NULL);
r300_stencilref_switch_side(r300);
sr->draw_vbo(pipe, info);
sr->draw_vbo(pipe, info, NULL);
r300_stencilref_end(r300);
}
}

View File

@ -2052,7 +2052,8 @@ static inline void r600_emit_rasterizer_prim_state(struct r600_context *rctx)
rctx->last_rast_prim = rast_prim;
}
static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct r600_context *rctx = (struct r600_context *)ctx;
struct pipe_resource *indexbuf = info->has_user_indices ? NULL : info->index.resource;
@ -2065,7 +2066,6 @@ static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info
int index_bias;
struct r600_shader_atomic combined_atomics[8];
uint8_t atomic_used_mask = 0;
struct pipe_draw_indirect_info *indirect = info->indirect;
struct pipe_stream_output_target *count_from_so = NULL;
if (indirect && indirect->count_from_stream_output) {

View File

@ -1000,7 +1000,7 @@ si_prepare_prim_discard_or_split_draw(struct si_context *sctx, const struct pipe
for (unsigned i = 0; i < num_draws; i++) {
if (count && count + draws[i].count > vert_count_per_subdraw) {
/* Submit previous draws. */
sctx->b.multi_draw(&sctx->b, info, draws + first_draw, num_draws_split);
sctx->b.multi_draw(&sctx->b, info, NULL, draws + first_draw, num_draws_split);
count = 0;
first_draw = i;
num_draws_split = 0;
@ -1008,7 +1008,7 @@ si_prepare_prim_discard_or_split_draw(struct si_context *sctx, const struct pipe
if (draws[i].count > vert_count_per_subdraw) {
/* Submit just 1 draw. It will be split. */
sctx->b.multi_draw(&sctx->b, info, draws + i, 1);
sctx->b.multi_draw(&sctx->b, info, NULL, draws + i, 1);
assert(count == 0);
assert(first_draw == i);
assert(num_draws_split == 0);
@ -1036,7 +1036,7 @@ si_prepare_prim_discard_or_split_draw(struct si_context *sctx, const struct pipe
split_draw_range.start = base_start + start;
split_draw_range.count = MIN2(count - start, vert_count_per_subdraw);
sctx->b.multi_draw(&sctx->b, &split_draw, &split_draw_range, 1);
sctx->b.multi_draw(&sctx->b, &split_draw, NULL, &split_draw_range, 1);
}
} else if (prim == PIPE_PRIM_TRIANGLE_STRIP) {
/* No primitive pair can be split, because strips reverse orientation
@ -1047,7 +1047,7 @@ si_prepare_prim_discard_or_split_draw(struct si_context *sctx, const struct pipe
split_draw_range.start = base_start + start;
split_draw_range.count = MIN2(count - start, vert_count_per_subdraw + 2);
sctx->b.multi_draw(&sctx->b, &split_draw, &split_draw_range, 1);
sctx->b.multi_draw(&sctx->b, &split_draw, NULL, &split_draw_range, 1);
if (start == 0 && primitive_restart &&
sctx->cs_prim_discard_state.current->key.opt.cs_need_correct_orientation)

View File

@ -496,11 +496,11 @@ static bool num_instanced_prims_less_than(const struct pipe_draw_info *info,
ALWAYS_INLINE
static unsigned si_get_ia_multi_vgt_param(struct si_context *sctx,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
enum pipe_prim_type prim, unsigned num_patches,
unsigned instance_count, bool primitive_restart,
unsigned min_vertex_count)
{
const struct pipe_draw_indirect_info *indirect = info->indirect;
union si_vgt_param_key key = sctx->ia_multi_vgt_param_key;
unsigned primgroup_size;
unsigned ia_multi_vgt_param;
@ -657,6 +657,7 @@ static bool si_prim_restart_index_changed(struct si_context *sctx, bool primitiv
ALWAYS_INLINE
static void si_emit_ia_multi_vgt_param(struct si_context *sctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
enum pipe_prim_type prim, unsigned num_patches,
unsigned instance_count, bool primitive_restart,
unsigned min_vertex_count)
@ -665,8 +666,8 @@ static void si_emit_ia_multi_vgt_param(struct si_context *sctx, const struct pip
unsigned ia_multi_vgt_param;
ia_multi_vgt_param =
si_get_ia_multi_vgt_param(sctx, info, prim, num_patches, instance_count, primitive_restart,
min_vertex_count);
si_get_ia_multi_vgt_param(sctx, info, indirect, prim, num_patches, instance_count,
primitive_restart, min_vertex_count);
/* Draw state. */
if (ia_multi_vgt_param != sctx->last_multi_vgt_param) {
@ -729,6 +730,7 @@ static void gfx10_emit_ge_cntl(struct si_context *sctx, unsigned num_patches)
ALWAYS_INLINE
static void si_emit_draw_registers(struct si_context *sctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
enum pipe_prim_type prim, unsigned num_patches,
unsigned instance_count, bool primitive_restart,
unsigned min_vertex_count)
@ -739,8 +741,8 @@ static void si_emit_draw_registers(struct si_context *sctx, const struct pipe_dr
if (sctx->chip_class >= GFX10)
gfx10_emit_ge_cntl(sctx, num_patches);
else
si_emit_ia_multi_vgt_param(sctx, info, prim, num_patches, instance_count, primitive_restart,
min_vertex_count);
si_emit_ia_multi_vgt_param(sctx, info, indirect, prim, num_patches, instance_count,
primitive_restart, min_vertex_count);
if (vgt_prim != sctx->last_prim) {
if (sctx->chip_class >= GFX10)
@ -770,13 +772,13 @@ static void si_emit_draw_registers(struct si_context *sctx, const struct pipe_dr
}
static void si_emit_draw_packets(struct si_context *sctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
const struct pipe_draw_start_count *draws,
unsigned num_draws,
struct pipe_resource *indexbuf, unsigned index_size,
unsigned index_offset, unsigned instance_count,
bool dispatch_prim_discard_cs, unsigned original_index_size)
{
struct pipe_draw_indirect_info *indirect = info->indirect;
struct radeon_cmdbuf *cs = sctx->gfx_cs;
unsigned sh_base_reg = sctx->shader_pointers.sh_base[PIPE_SHADER_VERTEX];
bool render_cond_bit = sctx->render_cond && !sctx->render_cond_force_off;
@ -1570,11 +1572,10 @@ static bool si_upload_vertex_buffer_descriptors(struct si_context *sctx)
}
static void si_get_draw_start_count(struct si_context *sctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
const struct pipe_draw_start_count *draws,
unsigned num_draws, unsigned *start, unsigned *count)
{
struct pipe_draw_indirect_info *indirect = info->indirect;
if (indirect && !indirect->count_from_stream_output) {
unsigned indirect_count;
struct pipe_transfer *transfer;
@ -1641,6 +1642,7 @@ static void si_get_draw_start_count(struct si_context *sctx, const struct pipe_d
}
static void si_emit_all_states(struct si_context *sctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
enum pipe_prim_type prim, unsigned instance_count,
unsigned min_vertex_count, bool primitive_restart,
unsigned skip_atom_mask)
@ -1674,8 +1676,8 @@ static void si_emit_all_states(struct si_context *sctx, const struct pipe_draw_i
/* Emit draw states. */
si_emit_vs_state(sctx, info);
si_emit_draw_registers(sctx, info, prim, num_patches, instance_count, primitive_restart,
min_vertex_count);
si_emit_draw_registers(sctx, info, indirect, prim, num_patches, instance_count,
primitive_restart, min_vertex_count);
}
static bool si_all_vs_resources_read_only(struct si_context *sctx, struct pipe_resource *indexbuf)
@ -1768,12 +1770,12 @@ static ALWAYS_INLINE bool pd_msg(const char *s)
static void si_multi_draw_vbo(struct pipe_context *ctx,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
struct si_context *sctx = (struct si_context *)ctx;
struct si_state_rasterizer *rs = sctx->queued.named.rasterizer;
struct pipe_draw_indirect_info *indirect = info->indirect;
struct pipe_resource *indexbuf = info->index.resource;
unsigned dirty_tex_counter, dirty_buf_counter;
enum pipe_prim_type rast_prim, prim = info->mode;
@ -1887,7 +1889,7 @@ static void si_multi_draw_vbo(struct pipe_context *ctx,
unsigned start, count, start_offset, size, offset;
void *ptr;
si_get_draw_start_count(sctx, info, draws, num_draws, &start, &count);
si_get_draw_start_count(sctx, info, indirect, draws, num_draws, &start, &count);
start_offset = start * 2;
size = count * 2;
@ -2155,7 +2157,7 @@ static void si_multi_draw_vbo(struct pipe_context *ctx,
masked_atoms |= si_get_atom_bit(sctx, &sctx->atoms.s.render_cond);
/* Emit all states except possibly render condition. */
si_emit_all_states(sctx, info, prim, instance_count, min_direct_count,
si_emit_all_states(sctx, info, indirect, prim, instance_count, min_direct_count,
primitive_restart, masked_atoms);
sctx->emit_cache_flush(sctx);
/* <-- CUs are idle here. */
@ -2172,7 +2174,7 @@ static void si_multi_draw_vbo(struct pipe_context *ctx,
}
assert(sctx->dirty_atoms == 0);
si_emit_draw_packets(sctx, info, draws, num_draws,
si_emit_draw_packets(sctx, info, indirect, draws, num_draws,
indexbuf, index_size, index_offset, instance_count,
dispatch_prim_discard_cs, original_index_size);
/* <-- CUs are busy here. */
@ -2193,7 +2195,7 @@ static void si_multi_draw_vbo(struct pipe_context *ctx,
if (sctx->chip_class >= GFX7 && sctx->prefetch_L2_mask)
cik_emit_prefetch_L2(sctx, true);
si_emit_all_states(sctx, info, prim, instance_count, min_direct_count,
si_emit_all_states(sctx, info, indirect, prim, instance_count, min_direct_count,
primitive_restart, masked_atoms);
if (gfx9_scissor_bug &&
@ -2203,7 +2205,7 @@ static void si_multi_draw_vbo(struct pipe_context *ctx,
}
assert(sctx->dirty_atoms == 0);
si_emit_draw_packets(sctx, info, draws, num_draws,
si_emit_draw_packets(sctx, info, indirect, draws, num_draws,
indexbuf, index_size, index_offset, instance_count,
dispatch_prim_discard_cs, original_index_size);
@ -2246,11 +2248,12 @@ return_cleanup:
}
static void si_draw_vbo(struct pipe_context *ctx,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct pipe_draw_start_count draw = {info->start, info->count};
si_multi_draw_vbo(ctx, info, &draw, 1);
si_multi_draw_vbo(ctx, info, indirect, &draw, 1);
}
static void si_draw_rectangle(struct blitter_context *blitter, void *vertex_elements_cso,
@ -2289,7 +2292,7 @@ static void si_draw_rectangle(struct blitter_context *blitter, void *vertex_elem
sctx->vertex_buffer_pointer_dirty = false;
sctx->vertex_buffer_user_sgprs_dirty = false;
si_draw_vbo(pipe, &info);
si_draw_vbo(pipe, &info, NULL);
}
void si_trace_emit(struct si_context *sctx)

View File

@ -59,7 +59,8 @@
*/
void
softpipe_draw_vbo(struct pipe_context *pipe,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct softpipe_context *sp = softpipe_context(pipe);
struct draw_context *draw = sp->draw;
@ -69,8 +70,8 @@ softpipe_draw_vbo(struct pipe_context *pipe,
if (!softpipe_check_render_cond(sp))
return;
if (info->indirect && info->indirect->buffer) {
util_draw_indirect(pipe, info);
if (indirect && indirect->buffer) {
util_draw_indirect(pipe, info, indirect);
return;
}
@ -129,7 +130,7 @@ softpipe_draw_vbo(struct pipe_context *pipe,
sp->active_statistics_queries > 0);
/* draw! */
draw_vbo(draw, info);
draw_vbo(draw, info, indirect);
/* unmap vertex/index buffers - will cause draw module to flush */
for (i = 0; i < sp->num_vertex_buffers; i++) {

View File

@ -180,7 +180,8 @@ softpipe_set_sampler_views(struct pipe_context *pipe,
void
softpipe_draw_vbo(struct pipe_context *pipe,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
void
softpipe_map_texture_surfaces(struct softpipe_context *sp);

View File

@ -80,10 +80,11 @@ retry_draw_arrays( struct svga_context *svga,
*/
static enum pipe_error
retry_draw_auto(struct svga_context *svga,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
assert(svga_have_sm5(svga));
assert(info->indirect->count_from_stream_output);
assert(indirect->count_from_stream_output);
assert(info->instance_count == 1);
/* SO drawing implies core profile and none of these prim types */
assert(info->mode != PIPE_PRIM_QUADS &&
@ -117,7 +118,7 @@ retry_draw_auto(struct svga_context *svga,
0, /* start instance */
1, /* only 1 instance supported */
NULL, /* indirect drawing info */
info->indirect->count_from_stream_output));
indirect->count_from_stream_output));
return PIPE_OK;
}
@ -129,10 +130,11 @@ retry_draw_auto(struct svga_context *svga,
*/
static enum pipe_error
retry_draw_indirect(struct svga_context *svga,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
assert(svga_have_sm5(svga));
assert(info->indirect && info->indirect->buffer);
assert(indirect && indirect->buffer);
/* indirect drawing implies core profile and none of these prim types */
assert(info->mode != PIPE_PRIM_QUADS &&
info->mode != PIPE_PRIM_QUAD_STRIP &&
@ -140,7 +142,7 @@ retry_draw_indirect(struct svga_context *svga,
if (info->mode == PIPE_PRIM_LINE_LOOP) {
/* need to do a fallback */
util_draw_indirect(&svga->pipe, info);
util_draw_indirect(&svga->pipe, info, indirect);
return PIPE_OK;
}
else {
@ -164,7 +166,7 @@ retry_draw_indirect(struct svga_context *svga,
info->index.resource,
info->start_instance,
0, /* don't know instance count */
info->indirect,
indirect,
NULL)); /* SO vertex count */
return PIPE_OK;
@ -214,7 +216,8 @@ get_vcount_from_stream_output(struct svga_context *svga,
static void
svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct svga_context *svga = svga_context(pipe);
enum pipe_prim_type reduced_prim = u_reduced_prim(info->mode);
@ -267,13 +270,13 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
if (need_fallback_prim_restart(svga, info)) {
enum pipe_error r;
r = util_draw_vbo_without_prim_restart(pipe, info);
r = util_draw_vbo_without_prim_restart(pipe, info, indirect);
assert(r == PIPE_OK);
(void) r;
goto done;
}
if (!info->indirect && !u_trim_pipe_prim(info->mode, &count))
if (!indirect && !u_trim_pipe_prim(info->mode, &count))
goto done;
needed_swtnl = svga->state.sw.need_swtnl;
@ -296,7 +299,7 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
/* Avoid leaking the previous hwtnl bias to swtnl */
svga_hwtnl_set_index_bias(svga->hwtnl, 0);
ret = svga_swtnl_draw_vbo(svga, info);
ret = svga_swtnl_draw_vbo(svga, info, indirect);
}
else {
if (!svga_update_state_retry(svga, SVGA_STATE_HW_DRAW)) {
@ -317,7 +320,7 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
svga_is_using_flat_shading(svga),
svga->curr.rast->templ.flatshade_first);
if (info->indirect && info->indirect->count_from_stream_output) {
if (indirect && indirect->count_from_stream_output) {
unsigned stream = 0;
assert(count == 0);
@ -331,7 +334,7 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
/* Check the stream index of the specified stream output target */
for (unsigned i = 0; i < ARRAY_SIZE(svga->so_targets); i++) {
if (svga->vcount_so_targets[i] == info->indirect->count_from_stream_output) {
if (svga->vcount_so_targets[i] == indirect->count_from_stream_output) {
stream = (svga->vcount_buffer_stream >> (i * 4)) & 0xf;
break;
}
@ -341,11 +344,11 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
}
}
if (info->indirect && info->indirect->count_from_stream_output && count == 0) {
ret = retry_draw_auto(svga, info);
if (indirect && indirect->count_from_stream_output && count == 0) {
ret = retry_draw_auto(svga, info, indirect);
}
else if (info->indirect && info->indirect->buffer) {
ret = retry_draw_indirect(svga, info);
else if (indirect && indirect->buffer) {
ret = retry_draw_indirect(svga, info, indirect);
}
else if (info->index_size) {
ret = retry_draw_range_elements(svga, info, count);

View File

@ -39,7 +39,8 @@ void svga_destroy_swtnl( struct svga_context *svga );
enum pipe_error
svga_swtnl_draw_vbo(struct svga_context *svga,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
#endif

View File

@ -38,7 +38,8 @@
enum pipe_error
svga_swtnl_draw_vbo(struct svga_context *svga,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct pipe_transfer *vb_transfer[PIPE_MAX_ATTRIBS] = { 0 };
struct pipe_transfer *ib_transfer = NULL;
@ -112,7 +113,7 @@ svga_swtnl_draw_vbo(struct svga_context *svga,
svga->curr.constbufs[PIPE_SHADER_VERTEX][i].buffer->width0);
}
draw_vbo(draw, info);
draw_vbo(draw, info, indirect);
draw_flush(svga->swtnl.draw);

View File

@ -37,11 +37,12 @@
* Draw vertex arrays, with optional indexing, optional instancing.
*/
static void
swr_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
swr_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct swr_context *ctx = swr_context(pipe);
if (!info->indirect &&
if (!indirect &&
!info->primitive_restart &&
!u_trim_pipe_prim(info->mode, (unsigned*)&info->count))
return;
@ -49,8 +50,8 @@ swr_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
if (!swr_check_render_cond(pipe))
return;
if (info->indirect && info->indirect->buffer) {
util_draw_indirect(pipe, info);
if (indirect && indirect->buffer) {
util_draw_indirect(pipe, info, indirect);
return;
}
@ -66,13 +67,13 @@ swr_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
struct pipe_draw_info resolved_info;
/* DrawTransformFeedback */
if (info->indirect && info->indirect->count_from_stream_output) {
if (indirect && indirect->count_from_stream_output) {
// trick copied from softpipe to modify const struct *info
memcpy(&resolved_info, (void*)info, sizeof(struct pipe_draw_info));
resolved_info.count = ctx->so_primCounter * resolved_info.vertices_per_patch;
resolved_info.max_index = resolved_info.count - 1;
resolved_info.indirect = NULL;
info = &resolved_info;
indirect = NULL;
}
if (ctx->vs->pipe.stream_output.num_outputs) {

View File

@ -46,28 +46,29 @@ tegra_destroy(struct pipe_context *pcontext)
static void
tegra_draw_vbo(struct pipe_context *pcontext,
const struct pipe_draw_info *pinfo)
const struct pipe_draw_info *pinfo,
const struct pipe_draw_indirect_info *pindirect)
{
struct tegra_context *context = to_tegra_context(pcontext);
struct pipe_draw_indirect_info indirect;
struct pipe_draw_info info;
if (pinfo && ((pinfo->indirect && pinfo->indirect->buffer) || pinfo->index_size)) {
if (pinfo && ((pindirect && pindirect->buffer) || pinfo->index_size)) {
memcpy(&info, pinfo, sizeof(info));
if (pinfo->indirect && pinfo->indirect->buffer) {
memcpy(&indirect, pinfo->indirect, sizeof(indirect));
indirect.buffer = tegra_resource_unwrap(info.indirect->buffer);
info.indirect = &indirect;
if (pindirect && pindirect->buffer) {
memcpy(&indirect, pindirect, sizeof(indirect));
indirect.buffer = tegra_resource_unwrap(pindirect->buffer);
}
if (pinfo->index_size && !pinfo->has_user_indices)
info.index.resource = tegra_resource_unwrap(info.index.resource);
pinfo = &info;
pindirect = &indirect;
}
context->gpu->draw_vbo(context->gpu, pinfo);
context->gpu->draw_vbo(context->gpu, pinfo, pindirect);
}
static void

View File

@ -1084,11 +1084,12 @@ v3d_check_compiled_shaders(struct v3d_context *v3d)
}
static void
v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct v3d_context *v3d = v3d_context(pctx);
if (!info->indirect &&
if (!indirect &&
!info->primitive_restart &&
!u_trim_pipe_prim(info->mode, (unsigned*)&info->count))
return;
@ -1108,7 +1109,7 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
}
if (info->restart_index != mask) {
util_draw_vbo_without_prim_restart(pctx, info);
util_draw_vbo_without_prim_restart(pctx, info, indirect);
return;
}
}
@ -1127,8 +1128,8 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
for (int s = 0; s < PIPE_SHADER_COMPUTE; s++)
v3d_predraw_check_stage_inputs(pctx, s);
if (info->indirect && info->indirect->buffer) {
v3d_flush_jobs_writing_resource(v3d, info->indirect->buffer,
if (indirect && indirect->buffer) {
v3d_flush_jobs_writing_resource(v3d, indirect->buffer,
V3D_FLUSH_DEFAULT, false);
}
@ -1155,7 +1156,7 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
* on the last submitted render, rather than tracking the last
* rendering to each texture's BO.
*/
if (v3d->tex[PIPE_SHADER_VERTEX].num_textures || (info->indirect && info->indirect->buffer)) {
if (v3d->tex[PIPE_SHADER_VERTEX].num_textures || (indirect && indirect->buffer)) {
perf_debug("Blocking binner on last render "
"due to vertex texturing or indirect drawing.\n");
job->submit.in_sync_bcl = v3d->out_sync;
@ -1284,7 +1285,7 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
}
#endif
if (info->indirect && info->indirect->buffer) {
if (indirect && indirect->buffer) {
cl_emit(&job->bcl, INDIRECT_INDEXED_INSTANCED_PRIM_LIST, prim) {
prim.index_type = ffs(info->index_size) - 1;
#if V3D_VERSION < 40
@ -1294,11 +1295,11 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
prim.mode = hw_prim_type | prim_tf_enable;
prim.enable_primitive_restarts = info->primitive_restart;
prim.number_of_draw_indirect_indexed_records = info->indirect->draw_count;
prim.number_of_draw_indirect_indexed_records = indirect->draw_count;
prim.stride_in_multiples_of_4_bytes = info->indirect->stride >> 2;
prim.address = cl_address(v3d_resource(info->indirect->buffer)->bo,
info->indirect->offset);
prim.stride_in_multiples_of_4_bytes = indirect->stride >> 2;
prim.address = cl_address(v3d_resource(indirect->buffer)->bo,
indirect->offset);
}
} else if (info->instance_count > 1) {
cl_emit(&job->bcl, INDEXED_INSTANCED_PRIM_LIST, prim) {
@ -1335,19 +1336,19 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
if (info->has_user_indices)
pipe_resource_reference(&prsc, NULL);
} else {
if (info->indirect && info->indirect->buffer) {
if (indirect && indirect->buffer) {
cl_emit(&job->bcl, INDIRECT_VERTEX_ARRAY_INSTANCED_PRIMS, prim) {
prim.mode = hw_prim_type | prim_tf_enable;
prim.number_of_draw_indirect_array_records = info->indirect->draw_count;
prim.number_of_draw_indirect_array_records = indirect->draw_count;
prim.stride_in_multiples_of_4_bytes = info->indirect->stride >> 2;
prim.address = cl_address(v3d_resource(info->indirect->buffer)->bo,
info->indirect->offset);
prim.stride_in_multiples_of_4_bytes = indirect->stride >> 2;
prim.address = cl_address(v3d_resource(indirect->buffer)->bo,
indirect->offset);
}
} else if (info->instance_count > 1) {
struct pipe_stream_output_target *so =
info->indirect && info->indirect->count_from_stream_output ?
info->indirect->count_from_stream_output : NULL;
indirect && indirect->count_from_stream_output ?
indirect->count_from_stream_output : NULL;
uint32_t vert_count = so ?
v3d_stream_output_target_get_vertex_count(so) :
info->count;
@ -1359,8 +1360,8 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
}
} else {
struct pipe_stream_output_target *so =
info->indirect && info->indirect->count_from_stream_output ?
info->indirect->count_from_stream_output : NULL;
indirect && indirect->count_from_stream_output ?
indirect->count_from_stream_output : NULL;
uint32_t vert_count = so ?
v3d_stream_output_target_get_vertex_count(so) :
info->count;

View File

@ -286,12 +286,13 @@ vc4_hw_2116_workaround(struct pipe_context *pctx, int vert_count)
}
static void
vc4_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
vc4_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
struct vc4_context *vc4 = vc4_context(pctx);
struct pipe_draw_info local_info;
if (!info->indirect &&
if (!indirect &&
!info->primitive_restart &&
!u_trim_pipe_prim(info->mode, (unsigned*)&info->count))
return;

View File

@ -848,14 +848,15 @@ static void virgl_clear_texture(struct pipe_context *ctx,
}
static void virgl_draw_vbo(struct pipe_context *ctx,
const struct pipe_draw_info *dinfo)
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *indirect)
{
struct virgl_context *vctx = virgl_context(ctx);
struct virgl_screen *rs = virgl_screen(ctx->screen);
struct virgl_indexbuf ib = {};
struct pipe_draw_info info = *dinfo;
if (!dinfo->indirect &&
if (!indirect &&
!dinfo->primitive_restart &&
!u_trim_pipe_prim(dinfo->mode, (unsigned*)&dinfo->count))
return;
@ -886,7 +887,7 @@ static void virgl_draw_vbo(struct pipe_context *ctx,
if (info.index_size)
virgl_hw_set_index_buffer(vctx, &ib);
virgl_encoder_draw_vbo(vctx, &info);
virgl_encoder_draw_vbo(vctx, &info, indirect);
pipe_resource_reference(&ib.buffer, NULL);

View File

@ -707,12 +707,13 @@ int virgl_encoder_set_index_buffer(struct virgl_context *ctx,
}
int virgl_encoder_draw_vbo(struct virgl_context *ctx,
const struct pipe_draw_info *info)
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect)
{
uint32_t length = VIRGL_DRAW_VBO_SIZE;
if (info->mode == PIPE_PRIM_PATCHES)
length = VIRGL_DRAW_VBO_SIZE_TESS;
if (info->indirect && info->indirect->buffer)
if (indirect && indirect->buffer)
length = VIRGL_DRAW_VBO_SIZE_INDIRECT;
virgl_encoder_write_cmd_dword(ctx, VIRGL_CMD0(VIRGL_CCMD_DRAW_VBO, 0, length));
virgl_encoder_write_dword(ctx->cbuf, info->start);
@ -726,8 +727,8 @@ int virgl_encoder_draw_vbo(struct virgl_context *ctx,
virgl_encoder_write_dword(ctx->cbuf, info->restart_index);
virgl_encoder_write_dword(ctx->cbuf, info->min_index);
virgl_encoder_write_dword(ctx->cbuf, info->max_index);
if (info->indirect && info->indirect->count_from_stream_output)
virgl_encoder_write_dword(ctx->cbuf, info->indirect->count_from_stream_output->buffer_size);
if (indirect && indirect->count_from_stream_output)
virgl_encoder_write_dword(ctx->cbuf, indirect->count_from_stream_output->buffer_size);
else
virgl_encoder_write_dword(ctx->cbuf, 0);
if (length >= VIRGL_DRAW_VBO_SIZE_TESS) {
@ -735,13 +736,13 @@ int virgl_encoder_draw_vbo(struct virgl_context *ctx,
virgl_encoder_write_dword(ctx->cbuf, info->drawid); /* drawid */
}
if (length == VIRGL_DRAW_VBO_SIZE_INDIRECT) {
virgl_encoder_write_res(ctx, virgl_resource(info->indirect->buffer));
virgl_encoder_write_dword(ctx->cbuf, info->indirect->offset);
virgl_encoder_write_dword(ctx->cbuf, info->indirect->stride); /* indirect stride */
virgl_encoder_write_dword(ctx->cbuf, info->indirect->draw_count); /* indirect draw count */
virgl_encoder_write_dword(ctx->cbuf, info->indirect->indirect_draw_count_offset); /* indirect draw count offset */
if (info->indirect->indirect_draw_count)
virgl_encoder_write_res(ctx, virgl_resource(info->indirect->indirect_draw_count));
virgl_encoder_write_res(ctx, virgl_resource(indirect->buffer));
virgl_encoder_write_dword(ctx->cbuf, indirect->offset);
virgl_encoder_write_dword(ctx->cbuf, indirect->stride); /* indirect stride */
virgl_encoder_write_dword(ctx->cbuf, indirect->draw_count); /* indirect draw count */
virgl_encoder_write_dword(ctx->cbuf, indirect->indirect_draw_count_offset); /* indirect draw count offset */
if (indirect->indirect_draw_count)
virgl_encoder_write_res(ctx, virgl_resource(indirect->indirect_draw_count));
else
virgl_encoder_write_dword(ctx->cbuf, 0); /* indirect draw count handle */
}

View File

@ -135,7 +135,8 @@ int virgl_encoder_set_viewport_states(struct virgl_context *ctx,
const struct pipe_viewport_state *states);
int virgl_encoder_draw_vbo(struct virgl_context *ctx,
const struct pipe_draw_info *info);
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
int virgl_encoder_create_surface(struct virgl_context *ctx,

View File

@ -187,6 +187,7 @@ zink_blit(struct pipe_context *pctx,
void
zink_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *dinfo);
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *indirect);
#endif

View File

@ -208,22 +208,23 @@ restart_supported(enum pipe_prim_type mode)
void
zink_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *dinfo)
const struct pipe_draw_info *dinfo,
const struct pipe_draw_indirect_info *dindirect)
{
struct zink_context *ctx = zink_context(pctx);
struct zink_screen *screen = zink_screen(pctx->screen);
struct zink_rasterizer_state *rast_state = ctx->rast_state;
struct zink_depth_stencil_alpha_state *dsa_state = ctx->dsa_state;
struct zink_so_target *so_target =
dinfo->indirect && dinfo->indirect->count_from_stream_output ?
zink_so_target(dinfo->indirect->count_from_stream_output) : NULL;
dindirect && dindirect->count_from_stream_output ?
zink_so_target(dindirect->count_from_stream_output) : NULL;
VkBuffer counter_buffers[PIPE_MAX_SO_OUTPUTS];
VkDeviceSize counter_buffer_offsets[PIPE_MAX_SO_OUTPUTS] = {};
bool need_index_buffer_unref = false;
if (dinfo->primitive_restart && !restart_supported(dinfo->mode)) {
util_draw_vbo_without_prim_restart(pctx, dinfo);
util_draw_vbo_without_prim_restart(pctx, dinfo, dindirect);
return;
}
if (dinfo->mode == PIPE_PRIM_QUADS ||
@ -277,7 +278,7 @@ zink_draw_vbo(struct pipe_context *pctx,
uint32_t restart_index = util_prim_restart_index_from_size(dinfo->index_size);
if ((dinfo->primitive_restart && (dinfo->restart_index != restart_index)) ||
(!screen->info.have_EXT_index_type_uint8 && dinfo->index_size == 8)) {
util_translate_prim_restart_ib(pctx, dinfo, &index_buffer);
util_translate_prim_restart_ib(pctx, dinfo, dindirect, &index_buffer);
need_index_buffer_unref = true;
} else {
if (dinfo->has_user_indices) {
@ -516,10 +517,10 @@ zink_draw_vbo(struct pipe_context *pctx,
struct zink_resource *res = zink_resource(index_buffer);
vkCmdBindIndexBuffer(batch->cmdbuf, res->buffer, index_offset, index_type);
zink_batch_reference_resource_rw(batch, res, false);
if (dinfo->indirect && dinfo->indirect->buffer) {
struct zink_resource *indirect = zink_resource(dinfo->indirect->buffer);
if (dindirect && dindirect->buffer) {
struct zink_resource *indirect = zink_resource(dindirect->buffer);
zink_batch_reference_resource_rw(batch, indirect, false);
vkCmdDrawIndexedIndirect(batch->cmdbuf, indirect->buffer, dinfo->indirect->offset, dinfo->indirect->draw_count, dinfo->indirect->stride);
vkCmdDrawIndexedIndirect(batch->cmdbuf, indirect->buffer, dindirect->offset, dindirect->draw_count, dindirect->stride);
} else
vkCmdDrawIndexed(batch->cmdbuf,
dinfo->count, dinfo->instance_count,
@ -530,10 +531,10 @@ zink_draw_vbo(struct pipe_context *pctx,
screen->vk_CmdDrawIndirectByteCountEXT(batch->cmdbuf, dinfo->instance_count, dinfo->start_instance,
zink_resource(so_target->counter_buffer)->buffer, so_target->counter_buffer_offset, 0,
MIN2(so_target->stride, screen->info.tf_props.maxTransformFeedbackBufferDataStride));
} else if (dinfo->indirect && dinfo->indirect->buffer) {
struct zink_resource *indirect = zink_resource(dinfo->indirect->buffer);
} else if (dindirect && dindirect->buffer) {
struct zink_resource *indirect = zink_resource(dindirect->buffer);
zink_batch_reference_resource_rw(batch, indirect, false);
vkCmdDrawIndirect(batch->cmdbuf, indirect->buffer, dinfo->indirect->offset, dinfo->indirect->draw_count, dinfo->indirect->stride);
vkCmdDrawIndirect(batch->cmdbuf, indirect->buffer, dindirect->offset, dindirect->draw_count, dindirect->stride);
} else
vkCmdDraw(batch->cmdbuf, dinfo->count, dinfo->instance_count, dinfo->start, dinfo->start_instance);
}

View File

@ -1301,13 +1301,12 @@ static void handle_draw(struct lvp_cmd_buffer_entry *cmd,
struct rendering_state *state)
{
state->info.index_size = 0;
state->info.indirect = NULL;
state->info.index.resource = NULL;
state->info.start = cmd->u.draw.first_vertex;
state->info.count = cmd->u.draw.vertex_count;
state->info.start_instance = cmd->u.draw.first_instance;
state->info.instance_count = cmd->u.draw.instance_count;
state->pctx->draw_vbo(state->pctx, &state->info);
state->pctx->draw_vbo(state->pctx, &state->info, NULL);
}
static void handle_set_viewport(struct lvp_cmd_buffer_entry *cmd,
@ -1841,7 +1840,6 @@ static void handle_update_buffer(struct lvp_cmd_buffer_entry *cmd,
static void handle_draw_indexed(struct lvp_cmd_buffer_entry *cmd,
struct rendering_state *state)
{
state->info.indirect = NULL;
state->info.min_index = 0;
state->info.max_index = ~0;
state->info.index_size = state->index_size;
@ -1859,7 +1857,7 @@ static void handle_draw_indexed(struct lvp_cmd_buffer_entry *cmd,
state->info.restart_index = 0xffff;
}
state->pctx->draw_vbo(state->pctx, &state->info);
state->pctx->draw_vbo(state->pctx, &state->info, NULL);
}
static void handle_draw_indirect(struct lvp_cmd_buffer_entry *cmd,
@ -1875,8 +1873,7 @@ static void handle_draw_indirect(struct lvp_cmd_buffer_entry *cmd,
state->indirect_info.stride = cmd->u.draw_indirect.stride;
state->indirect_info.draw_count = cmd->u.draw_indirect.draw_count;
state->indirect_info.buffer = cmd->u.draw_indirect.buffer->bo;
state->info.indirect = &state->indirect_info;
state->pctx->draw_vbo(state->pctx, &state->info);
state->pctx->draw_vbo(state->pctx, &state->info, &state->indirect_info);
}
static void handle_index_buffer(struct lvp_cmd_buffer_entry *cmd,

View File

@ -3174,7 +3174,6 @@ NineDevice9_ProcessVertices( struct NineDevice9 *This,
draw.start_instance = 0;
draw.primitive_restart = FALSE;
draw.restart_index = 0;
draw.indirect = NULL;
draw.instance_count = 1;
draw.index_size = 0;
draw.start = 0;
@ -3185,7 +3184,7 @@ NineDevice9_ProcessVertices( struct NineDevice9 *This,
pipe_sw->set_stream_output_targets(pipe_sw, 1, &target, offsets);
pipe_sw->draw_vbo(pipe_sw, &draw);
pipe_sw->draw_vbo(pipe_sw, &draw, NULL);
pipe_sw->set_stream_output_targets(pipe_sw, 0, NULL, 0);
pipe_sw->stream_output_target_destroy(pipe_sw, target);

View File

@ -2318,7 +2318,6 @@ init_draw_info(struct pipe_draw_info *info,
info->primitive_restart = FALSE;
info->has_user_indices = FALSE;
info->restart_index = 0;
info->indirect = NULL;
}
CSMT_ITEM_NO_WAIT(nine_context_draw_primitive,
@ -2339,7 +2338,7 @@ CSMT_ITEM_NO_WAIT(nine_context_draw_primitive,
info.max_index = info.count - 1;
info.index.resource = NULL;
context->pipe->draw_vbo(context->pipe, &info);
context->pipe->draw_vbo(context->pipe, &info, NULL);
}
CSMT_ITEM_NO_WAIT(nine_context_draw_indexed_primitive,
@ -2364,7 +2363,7 @@ CSMT_ITEM_NO_WAIT(nine_context_draw_indexed_primitive,
info.max_index = MinVertexIndex + NumVertices - 1;
info.index.resource = context->idxbuf;
context->pipe->draw_vbo(context->pipe, &info);
context->pipe->draw_vbo(context->pipe, &info, NULL);
}
CSMT_ITEM_NO_WAIT(nine_context_draw_primitive_from_vtxbuf,
@ -2387,7 +2386,7 @@ CSMT_ITEM_NO_WAIT(nine_context_draw_primitive_from_vtxbuf,
context->pipe->set_vertex_buffers(context->pipe, 0, 1, vtxbuf);
context->pipe->draw_vbo(context->pipe, &info);
context->pipe->draw_vbo(context->pipe, &info, NULL);
}
CSMT_ITEM_NO_WAIT(nine_context_draw_indexed_primitive_from_vtxbuf_idxbuf,
@ -2420,7 +2419,7 @@ CSMT_ITEM_NO_WAIT(nine_context_draw_indexed_primitive_from_vtxbuf_idxbuf,
context->pipe->set_vertex_buffers(context->pipe, 0, 1, vbuf);
context->pipe->draw_vbo(context->pipe, &info);
context->pipe->draw_vbo(context->pipe, &info, NULL);
}
CSMT_ITEM_NO_WAIT(nine_context_resource_copy_region,

View File

@ -49,6 +49,7 @@ struct pipe_debug_callback;
struct pipe_depth_stencil_alpha_state;
struct pipe_device_reset_callback;
struct pipe_draw_info;
struct pipe_draw_indirect_info;
struct pipe_draw_start_count;
struct pipe_grid_info;
struct pipe_fence_handle;
@ -107,8 +108,9 @@ struct pipe_context {
* VBO drawing
*/
/*@{*/
void (*draw_vbo)( struct pipe_context *pipe,
const struct pipe_draw_info *info );
void (*draw_vbo)(struct pipe_context *pipe,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect);
/**
* Direct multi draw specifying "start" and "count" for each draw.
@ -142,6 +144,7 @@ struct pipe_context {
*/
void (*multi_draw)(struct pipe_context *pipe,
const struct pipe_draw_info *info,
const struct pipe_draw_indirect_info *indirect,
const struct pipe_draw_start_count *draws,
unsigned num_draws);
/*@}*/

View File

@ -793,8 +793,6 @@ struct pipe_draw_info
struct pipe_resource *resource; /**< real buffer */
const void *user; /**< pointer to a user buffer */
} index;
struct pipe_draw_indirect_info *indirect; /**< Indirect draw. */
};

View File

@ -209,7 +209,7 @@ static void draw( void )
indices);
}
ctx->draw_vbo(ctx, &info);
ctx->draw_vbo(ctx, &info, NULL);
pipe_resource_reference(&info.index.resource, NULL);

View File

@ -176,7 +176,6 @@ st_draw_vbo(struct gl_context *ctx,
/* Initialize pipe_draw_info. */
info.primitive_restart = false;
info.vertices_per_patch = ctx->TessCtrlProgram.patch_vertices;
info.indirect = NULL;
info.restart_index = 0;
info.start_instance = base_instance;
info.instance_count = num_instances;
@ -246,7 +245,7 @@ st_draw_vbo(struct gl_context *ctx,
}
/* Don't call u_trim_pipe_prim. Drivers should do it if they need it. */
cso_draw_vbo(st->cso_context, &info);
cso_draw_vbo(st->cso_context, &info, NULL);
}
}
@ -289,7 +288,6 @@ st_indirect_draw_vbo(struct gl_context *ctx,
info.mode = translate_prim(ctx, mode);
info.vertices_per_patch = ctx->TessCtrlProgram.patch_vertices;
info.indirect = &indirect;
indirect.buffer = st_buffer_object(indirect_data)->buffer;
indirect.offset = indirect_offset;
@ -307,7 +305,7 @@ st_indirect_draw_vbo(struct gl_context *ctx,
indirect.draw_count = 1;
for (i = 0; i < draw_count; i++) {
info.drawid = i;
cso_draw_vbo(st->cso_context, &info);
cso_draw_vbo(st->cso_context, &info, &indirect);
indirect.offset += stride;
}
} else {
@ -318,7 +316,7 @@ st_indirect_draw_vbo(struct gl_context *ctx,
st_buffer_object(indirect_draw_count)->buffer;
indirect.indirect_draw_count_offset = indirect_draw_count_offset;
}
cso_draw_vbo(st->cso_context, &info);
cso_draw_vbo(st->cso_context, &info, &indirect);
}
}
@ -340,7 +338,6 @@ st_draw_transform_feedback(struct gl_context *ctx, GLenum mode,
info.mode = translate_prim(ctx, mode);
info.vertices_per_patch = ctx->TessCtrlProgram.patch_vertices;
info.instance_count = num_instances;
info.indirect = &indirect;
if (ST_DEBUG & DEBUG_DRAW) {
debug_printf("st/draw transform feedback: mode %s\n",
@ -352,7 +349,7 @@ st_draw_transform_feedback(struct gl_context *ctx, GLenum mode,
if (!st_transform_feedback_draw_init(tfb_vertcount, stream, &indirect))
return;
cso_draw_vbo(st->cso_context, &info);
cso_draw_vbo(st->cso_context, &info, &indirect);
}
void

View File

@ -123,7 +123,6 @@ st_feedback_draw_vbo(struct gl_context *ctx,
/* Initialize pipe_draw_info. */
info.primitive_restart = false;
info.vertices_per_patch = ctx->TessCtrlProgram.patch_vertices;
info.indirect = NULL;
info.restart_index = 0;
st_flush_bitmap_cache(st);
@ -437,7 +436,7 @@ st_feedback_draw_vbo(struct gl_context *ctx,
info.max_index = info.start + info.count - 1;
}
draw_vbo(draw, &info);
draw_vbo(draw, &info, NULL);
}
/* unmap images */