Commit 05f35a50 authored by Marek Olšák's avatar Marek Olšák

gallium: remove and emulate PIPE_CAP_MULTI_DRAW

To remove PIPE_CAP checking in the common code.

It's better if drivers lower multi draws even if the hardware doesn't
support it beause the multi draw loop can be moved deeper into the driver
to remove more overhead.
Reviewed-by: Pierre-Eric Pelloux-Prayer's avatarPierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer@amd.com>
Part-of: <!7679>
parent 87b57aa3
......@@ -232,7 +232,6 @@ The integer capabilities:
* ``PIPE_CAP_DRAW_INDIRECT``: Whether the driver supports taking draw arguments
{ count, instance_count, start, index_bias } from a PIPE_BUFFER resource.
See pipe_draw_info.
* ``PIPE_CAP_MULTI_DRAW``: Whether the driver supports direct multi draws.
* ``PIPE_CAP_MULTI_DRAW_INDIRECT``: Whether the driver supports
pipe_draw_info::indirect_stride and ::indirect_count
* ``PIPE_CAP_MULTI_DRAW_INDIRECT_PARAMS``: Whether the driver supports
......
......@@ -229,7 +229,6 @@ u_pipe_screen_get_param_defaults(struct pipe_screen *pscreen,
case PIPE_CAP_CLEAR_SCISSORED:
case PIPE_CAP_DRAW_PARAMETERS:
case PIPE_CAP_TGSI_PACK_HALF_FLOAT:
case PIPE_CAP_MULTI_DRAW:
case PIPE_CAP_MULTI_DRAW_INDIRECT:
case PIPE_CAP_MULTI_DRAW_INDIRECT_PARAMS:
case PIPE_CAP_TGSI_FS_POSITION_IS_SYSVAL:
......
......@@ -145,8 +145,6 @@
* another resource's backing storage. The threaded context uses it to
* implement buffer invalidation. This call is always queued.
*
* PIPE_CAP_MULTI_DRAW must be supported.
*
*
* Performance gotchas
* -------------------
......
......@@ -426,6 +426,17 @@ d3d12_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *dinfo;
for (unsigned i = 0; i < num_draws; i++) {
d3d12_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct d3d12_context *ctx = d3d12_context(pctx);
struct d3d12_batch *batch;
struct pipe_resource *index_buffer = NULL;
......
......@@ -228,6 +228,17 @@ etna_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
etna_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct etna_context *ctx = etna_context(pctx);
struct etna_screen *screen = ctx->screen;
struct pipe_framebuffer_state *pfb = &ctx->framebuffer_s;
......
......@@ -216,6 +216,17 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
fd_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct fd_context *ctx = fd_context(pctx);
/* for debugging problems with indirect draw, it is convenient
......
......@@ -56,6 +56,17 @@ i915_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
i915_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct i915_context *i915 = i915_context(pipe);
struct draw_context *draw = i915->draw;
const void *mapped_indices = NULL;
......
......@@ -240,6 +240,17 @@ iris_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
iris_draw_vbo(ctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
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;
......
......@@ -1133,6 +1133,17 @@ lima_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
lima_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
/* check if draw mode and vertex/index count match,
* otherwise gp will hang */
if (!u_trim_pipe_prim(info->mode, (unsigned*)&draws[0].count)) {
......
......@@ -56,6 +56,17 @@ llvmpipe_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
llvmpipe_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct llvmpipe_context *lp = llvmpipe_context(pipe);
struct draw_context *draw = lp->draw;
const void *mapped_indices = NULL;
......
......@@ -549,6 +549,17 @@ nv30_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
nv30_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct nv30_context *nv30 = nv30_context(pipe);
struct nouveau_pushbuf *push = nv30->base.pushbuf;
int i;
......
......@@ -759,6 +759,17 @@ nv50_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
nv50_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct nv50_context *nv50 = nv50_context(pipe);
struct nouveau_pushbuf *push = nv50->base.pushbuf;
bool tex_dirty = false;
......
......@@ -927,6 +927,17 @@ nvc0_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
nvc0_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct nvc0_context *nvc0 = nvc0_context(pipe);
struct nouveau_pushbuf *push = nvc0->base.pushbuf;
struct nvc0_screen *screen = nvc0->screen;
......
......@@ -457,6 +457,17 @@ panfrost_draw_vbo(
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
panfrost_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct panfrost_context *ctx = pan_context(pipe);
struct panfrost_device *device = pan_device(ctx->base.screen);
......
......@@ -791,6 +791,17 @@ static void r300_draw_vbo(struct pipe_context* pipe,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *dinfo;
for (unsigned i = 0; i < num_draws; i++) {
r300_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct r300_context* r300 = r300_context(pipe);
struct pipe_draw_info info = *dinfo;
struct pipe_draw_start_count draw = draws[0];
......@@ -853,6 +864,17 @@ static void r300_swtcl_draw_vbo(struct pipe_context* pipe,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
r300_swtcl_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct r300_context* r300 = r300_context(pipe);
struct pipe_draw_start_count draw = draws[0];
......
......@@ -2057,6 +2057,17 @@ static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
r600_draw_vbo(ctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct r600_context *rctx = (struct r600_context *)ctx;
struct pipe_resource *indexbuf = info->has_user_indices ? NULL : info->index.resource;
struct radeon_cmdbuf *cs = &rctx->b.gfx.cs;
......
......@@ -164,7 +164,6 @@ static int si_get_param(struct pipe_screen *pscreen, enum pipe_cap param)
case PIPE_CAP_SHADER_ATOMIC_INT64:
case PIPE_CAP_FRONTEND_NOOP:
case PIPE_CAP_DEMOTE_TO_HELPER_INVOCATION:
case PIPE_CAP_MULTI_DRAW:
case PIPE_CAP_PREFER_REAL_BUFFER_IN_CONSTBUF0:
case PIPE_CAP_COMPUTE_SHADER_DERIVATIVES:
return 1;
......
......@@ -64,6 +64,17 @@ softpipe_draw_vbo(struct pipe_context *pipe,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
softpipe_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct softpipe_context *sp = softpipe_context(pipe);
struct draw_context *draw = sp->draw;
const void *mapped_indices = NULL;
......
......@@ -222,6 +222,17 @@ svga_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
svga_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct svga_context *svga = svga_context(pipe);
enum pipe_prim_type reduced_prim = u_reduced_prim(info->mode);
unsigned count = draws[0].count;
......
......@@ -42,6 +42,17 @@ swr_draw_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
swr_draw_vbo(pipe, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct swr_context *ctx = swr_context(pipe);
if (!indirect &&
......
......@@ -51,6 +51,17 @@ tegra_draw_vbo(struct pipe_context *pcontext,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *pinfo;
for (unsigned i = 0; i < num_draws; i++) {
tegra_draw_vbo(pcontext, &tmp_info, pindirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct tegra_context *context = to_tegra_context(pcontext);
struct pipe_draw_indirect_info indirect;
struct pipe_draw_info info;
......
......@@ -1097,6 +1097,17 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
v3d_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct v3d_context *v3d = v3d_context(pctx);
if (!indirect &&
......
......@@ -291,6 +291,17 @@ vc4_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *info;
for (unsigned i = 0; i < num_draws; i++) {
vc4_draw_vbo(pctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct vc4_context *vc4 = vc4_context(pctx);
struct pipe_draw_info local_info;
......
......@@ -853,6 +853,17 @@ static void virgl_draw_vbo(struct pipe_context *ctx,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *dinfo;
for (unsigned i = 0; i < num_draws; i++) {
virgl_draw_vbo(ctx, &tmp_info, indirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct virgl_context *vctx = virgl_context(ctx);
struct virgl_screen *rs = virgl_screen(ctx->screen);
struct virgl_indexbuf ib = {};
......
......@@ -213,6 +213,17 @@ zink_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_start_count *draws,
unsigned num_draws)
{
if (num_draws > 1) {
struct pipe_draw_info tmp_info = *dinfo;
for (unsigned i = 0; i < num_draws; i++) {
zink_draw_vbo(pctx, &tmp_info, dindirect, &draws[i], 1);
if (tmp_info.increment_draw_id)
tmp_info.drawid++;
}
return;
}
struct zink_context *ctx = zink_context(pctx);
struct zink_screen *screen = zink_screen(pctx->screen);
struct zink_rasterizer_state *rast_state = ctx->rast_state;
......
......@@ -115,7 +115,7 @@ struct pipe_context {
* is used instead.
*
* Caps:
* - PIPE_CAP_MULTI_DRAW: Direct multi draws
* - Always supported: Direct multi draws
* - PIPE_CAP_MULTI_DRAW_INDIRECT: Indirect multi draws
* - PIPE_CAP_MULTI_DRAW_INDIRECT_PARAMS: Indirect draw count
*
......
......@@ -842,7 +842,6 @@ enum pipe_cap
PIPE_CAP_CLEAR_SCISSORED,
PIPE_CAP_DRAW_PARAMETERS,
PIPE_CAP_TGSI_PACK_HALF_FLOAT,
PIPE_CAP_MULTI_DRAW,
PIPE_CAP_MULTI_DRAW_INDIRECT,
PIPE_CAP_MULTI_DRAW_INDIRECT_PARAMS,
PIPE_CAP_TGSI_FS_POSITION_IS_SYSVAL,
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment